diff --git a/.Rbuildignore b/.Rbuildignore index b8a674fa..bfce554a 100644 --- a/.Rbuildignore +++ b/.Rbuildignore @@ -16,3 +16,4 @@ ^tools/dist$ ^compile_commands\.json$ ^\.cache$ +^docker-compose\.yml$ diff --git a/.github/workflows/check-standard.yaml b/.github/workflows/R-CMD-check.yaml similarity index 54% rename from .github/workflows/check-standard.yaml rename to .github/workflows/R-CMD-check.yaml index b61e50d5..fdaf40b4 100644 --- a/.github/workflows/check-standard.yaml +++ b/.github/workflows/R-CMD-check.yaml @@ -1,4 +1,4 @@ -# Workflow derived from https://github.com/r-lib/actions/tree/master/examples +# Workflow derived from https://github.com/r-lib/actions/tree/v2/examples # Need help debugging build failures? Start at https://github.com/r-lib/actions#where-to-find-help on: push: @@ -8,19 +8,42 @@ on: name: R-CMD-check +permissions: read-all + jobs: + # Check MacOS first before embarking on the full check matrix + test: + runs-on: macos-latest + steps: + - uses: actions/checkout@v4 + - uses: r-lib/actions/setup-r@v2 + - name: Install Abseil (MacOS) + run: brew install abseil + - name: Install minimal dependencies + run: | + R -e 'install.packages(c("wk", "Rcpp", "bit64", "testthat"))' + - name: Install + run: | + R CMD INSTALL . + - name: Test + run: | + R -e 'testthat::test_local()' + R-CMD-check: runs-on: ${{ matrix.config.os }} name: ${{ matrix.config.os }} (${{ matrix.config.r }}) + needs: + - test + strategy: fail-fast: false matrix: config: - - {os: macOS-latest, r: 'release'} # TODO: Solve Abseil linking issue on R 4.0 and R 4.1/Windows # - {os: windows-latest, r: '4.1'} + - {os: macos-latest, r: 'release'} - {os: windows-latest, r: '4.2'} - {os: windows-latest, r: '4.3'} - {os: windows-latest, r: 'release'} @@ -33,7 +56,7 @@ jobs: R_KEEP_PKG_SOURCE: yes steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - uses: r-lib/actions/setup-pandoc@v2 @@ -43,25 +66,27 @@ jobs: http-user-agent: ${{ matrix.config.http-user-agent }} use-public-rspm: true + - name: Install Abseil (MacOS) + if: matrix.config.os == 'macos-latest' + run: | + brew install abseil + + - name: Set Makevars (Ubuntu) + if: matrix.config.os == 'ubuntu-latest' + run: | + mkdir ~/.R && echo "MAKEFLAGS = -j$(nproc)" > ~/.R/Makevars + - uses: r-lib/actions/setup-r-dependencies@v2 with: - extra-packages: rcmdcheck + extra-packages: any::rcmdcheck + needs: check - uses: r-lib/actions/check-r-package@v2 + with: + upload-snapshots: true + build_args: 'c("--no-manual","--compact-vignettes=gs+qpdf")' - name: Show install output if: always() run: find check -name '00install.out*' -exec cat '{}' \; || true shell: bash - - - name: Show testthat output - if: always() - run: find check -name 'testthat.Rout*' -exec cat '{}' \; || true - shell: bash - - - name: Upload check results - if: failure() - uses: actions/upload-artifact@main - with: - name: ${{ runner.os }}-r${{ matrix.config.r }}-results - path: check diff --git a/.github/workflows/pkgdown.yaml b/.github/workflows/pkgdown.yaml index 51b79c18..130d63e3 100644 --- a/.github/workflows/pkgdown.yaml +++ b/.github/workflows/pkgdown.yaml @@ -11,6 +11,8 @@ on: name: pkgdown +permissions: read-all + jobs: pkgdown: runs-on: ubuntu-latest @@ -19,8 +21,10 @@ jobs: group: pkgdown-${{ github.event_name != 'pull_request' || github.run_id }} env: GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} + permissions: + contents: write steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - uses: r-lib/actions/setup-pandoc@v2 @@ -39,7 +43,7 @@ jobs: - name: Deploy to GitHub pages 🚀 if: github.event_name != 'pull_request' - uses: JamesIves/github-pages-deploy-action@4.1.4 + uses: JamesIves/github-pages-deploy-action@v4.5.0 with: clean: false branch: gh-pages diff --git a/.github/workflows/test-coverage.yaml b/.github/workflows/test-coverage.yaml index 4b01af75..e827c42e 100644 --- a/.github/workflows/test-coverage.yaml +++ b/.github/workflows/test-coverage.yaml @@ -1,5 +1,3 @@ -# Workflow derived from https://github.com/r-lib/actions/tree/master/examples -# Need help debugging build failures? Start at https://github.com/r-lib/actions#where-to-find-help on: push: branches: [main, master] @@ -8,6 +6,8 @@ on: name: test-coverage +permissions: read-all + jobs: test-coverage: runs-on: ubuntu-latest @@ -15,12 +15,16 @@ jobs: GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - uses: r-lib/actions/setup-r@v2 with: use-public-rspm: true + - name: Install Abseil (Ubuntu) + run: | + sudo apt-get update && sudo apt-get install -y libabsl-dev + - uses: r-lib/actions/setup-r-dependencies@v2 with: extra-packages: covr diff --git a/DESCRIPTION b/DESCRIPTION index 78bd8a91..249c5b03 100644 --- a/DESCRIPTION +++ b/DESCRIPTION @@ -25,7 +25,7 @@ License: Apache License (== 2.0) Encoding: UTF-8 LazyData: true Roxygen: list(markdown = TRUE) -RoxygenNote: 7.2.3 +RoxygenNote: 7.3.2 SystemRequirements: OpenSSL >= 1.0.1, Abseil >= 20230802.0 LinkingTo: Rcpp, diff --git a/README.Rmd b/README.Rmd index bc16a2f5..f2464791 100644 --- a/README.Rmd +++ b/README.Rmd @@ -16,15 +16,15 @@ knitr::opts_chunk$set( # s2 -![R-CMD-check](https://github.com/r-spatial/s2/workflows/R-CMD-check/badge.svg) -[![codecov](https://codecov.io/gh/r-spatial/s2/branch/master/graph/badge.svg)](https://app.codecov.io/gh/r-spatial/s2) +[![R-CMD-check](https://github.com/r-spatial/s2/actions/workflows/R-CMD-check.yaml/badge.svg)](https://github.com/r-spatial/s2/actions/workflows/R-CMD-check.yaml) +[![codecov](https://codecov.io/gh/r-spatial/s2/branch/main/graph/badge.svg)](https://app.codecov.io/gh/r-spatial/s2) [![CRAN](http://www.r-pkg.org/badges/version/s2)](https://cran.r-project.org/package=s2) [![Downloads](http://cranlogs.r-pkg.org/badges/s2?color=brightgreen)](https://www.r-pkg.org/pkg/s2) The s2 R package provides bindings to Google's [S2Geometry](http://s2geometry.io) library. The package exposes an API similar to Google's [BigQuery Geography API](https://cloud.google.com/bigquery/docs/reference/standard-sql/geography_functions), whose functions also operate on spherical geometries. Package [sf](https://cran.r-project.org/package=sf) uses this package by default for nearly all its geometrical operations on objects with ellipsoidal (unprojected) coordinates; in cases where it doesn't, such as `st_relate()`, it emits a warning. -This package is a complete rewrite of an earlier CRAN package s2 with versions up +This package is a complete rewrite of an earlier CRAN package s2 with versions up to 0.4-2, for which the sources are found [here](https://github.com/spatstat/s2/). ## Installation @@ -42,6 +42,14 @@ And the development version from [GitHub](https://github.com/) with: remotes::install_github("r-spatial/s2") ``` +The S2 package requires [Abseil]() and OpenSSL. You can install these using a system package manager on most platforms: + +- Windows: Both OpenSSL and Abseil are available from RTools since R 4.3 +- MacOS: `brew install openssl abseil` +- Debian/Ubuntu: `apt-get install libssl-dev libabsl-dev` +- Fedora: `dnf install openssl-devel abseil-cpp-devel` +- Alpine: `apk add abseil-cpp` + ## Example The s2 package provides geometry transformers and predicates similar to those found in [GEOS](https://trac.osgeo.org/geos/), except instead of assuming a planar geometry, s2's functions work in latitude and longitude and assume a spherical geometry: @@ -63,9 +71,9 @@ The [sf package](https://r-spatial.github.io/sf/) uses s2 for geographic coordin library(dplyr) library(sf) -nc_s2 <- read_sf(system.file("shape/nc.shp", package = "sf")) %>% - mutate(geometry = as_s2_geography(geometry)) %>% - as_tibble() %>% +nc_s2 <- read_sf(system.file("shape/nc.shp", package = "sf")) %>% + mutate(geometry = as_s2_geography(geometry)) %>% + as_tibble() %>% select(NAME, geometry) nc_s2 @@ -74,7 +82,7 @@ nc_s2 Use accessors to extract information about geometries: ```{r} -nc_s2 %>% +nc_s2 %>% mutate( area = s2_area(geometry), perimeter = s2_perimeter(geometry) @@ -84,29 +92,29 @@ nc_s2 %>% Use predicates to subset vectors: ```{r} -nc_s2 %>% +nc_s2 %>% filter(s2_contains(geometry, "POINT (-80.9313 35.6196)")) ``` Use transformers to create new geometries: ```{r} -nc_s2 %>% +nc_s2 %>% mutate(geometry = s2_boundary(geometry)) ``` Finally, use the WKB or WKT exporters to export to sf or some other package: ```{r} -nc_s2 %>% - mutate(geometry = st_as_sfc(s2_as_binary(geometry))) %>% +nc_s2 %>% + mutate(geometry = st_as_sfc(s2_as_binary(geometry))) %>% st_as_sf() ``` ## Acknowledgment -This project gratefully acknowledges financial [support](https://www.r-consortium.org/projects) from the +This project gratefully acknowledges financial [support](https://www.r-consortium.org/) from the - + diff --git a/README.md b/README.md index 6b958e2a..52d7e2b1 100644 --- a/README.md +++ b/README.md @@ -5,8 +5,8 @@ -![R-CMD-check](https://github.com/r-spatial/s2/workflows/R-CMD-check/badge.svg) -[![codecov](https://codecov.io/gh/r-spatial/s2/branch/master/graph/badge.svg)](https://app.codecov.io/gh/r-spatial/s2) +[![R-CMD-check](https://github.com/r-spatial/s2/actions/workflows/R-CMD-check.yaml/badge.svg)](https://github.com/r-spatial/s2/actions/workflows/R-CMD-check.yaml) +[![codecov](https://codecov.io/gh/r-spatial/s2/branch/main/graph/badge.svg)](https://app.codecov.io/gh/r-spatial/s2) [![CRAN](http://www.r-pkg.org/badges/version/s2)](https://cran.r-project.org/package=s2) [![Downloads](http://cranlogs.r-pkg.org/badges/s2?color=brightgreen)](https://www.r-pkg.org/pkg/s2) @@ -41,6 +41,15 @@ And the development version from [GitHub](https://github.com/) with: remotes::install_github("r-spatial/s2") ``` +The S2 package requires [Abseil]() and OpenSSL. You can install these +using a system package manager on most platforms: + +- Windows: Both OpenSSL and Abseil are available from RTools since R 4.3 +- MacOS: `brew install openssl abseil` +- Debian/Ubuntu: `apt-get install libssl-dev libabsl-dev` +- Fedora: `dnf install openssl-devel abseil-cpp-devel` +- Alpine: `apk add abseil-cpp` + ## Example The s2 package provides geometry transformers and predicates similar to @@ -69,9 +78,9 @@ using `as_s2_geography()`: library(dplyr) library(sf) -nc_s2 <- read_sf(system.file("shape/nc.shp", package = "sf")) %>% - mutate(geometry = as_s2_geography(geometry)) %>% - as_tibble() %>% +nc_s2 <- read_sf(system.file("shape/nc.shp", package = "sf")) %>% + mutate(geometry = as_s2_geography(geometry)) %>% + as_tibble() %>% select(NAME, geometry) nc_s2 @@ -88,13 +97,13 @@ nc_s2 #> 8 Gates POLYGON ((-76.46035 36.3738976, -76.5024643 36.4522858, -76.4983… #> 9 Warren POLYGON ((-78.1347198 36.2365837, -78.1096268 36.2135086, -78.05… #> 10 Stokes POLYGON ((-80.0240555 36.5450249, -80.0480957 36.5471344, -80.43… -#> # … with 90 more rows +#> # ℹ 90 more rows ``` Use accessors to extract information about geometries: ``` r -nc_s2 %>% +nc_s2 %>% mutate( area = s2_area(geometry), perimeter = s2_perimeter(geometry) @@ -112,13 +121,13 @@ nc_s2 %>% #> 8 Gates POLYGON ((-76.46035 36.3738976, -76.5024643 36.… 9.03e8 123170. #> 9 Warren POLYGON ((-78.1347198 36.2365837, -78.1096268 3… 1.18e9 141073. #> 10 Stokes POLYGON ((-80.0240555 36.5450249, -80.0480957 3… 1.23e9 140583. -#> # … with 90 more rows +#> # ℹ 90 more rows ``` Use predicates to subset vectors: ``` r -nc_s2 %>% +nc_s2 %>% filter(s2_contains(geometry, "POINT (-80.9313 35.6196)")) #> # A tibble: 1 × 2 #> NAME geometry @@ -129,7 +138,7 @@ nc_s2 %>% Use transformers to create new geometries: ``` r -nc_s2 %>% +nc_s2 %>% mutate(geometry = s2_boundary(geometry)) #> # A tibble: 100 × 2 #> NAME geometry @@ -144,15 +153,15 @@ nc_s2 %>% #> 8 Gates LINESTRING (-76.46035 36.3738976, -76.5024643 36.4522858, -76.49… #> 9 Warren LINESTRING (-78.1347198 36.2365837, -78.1096268 36.2135086, -78.… #> 10 Stokes LINESTRING (-80.0240555 36.5450249, -80.0480957 36.5471344, -80.… -#> # … with 90 more rows +#> # ℹ 90 more rows ``` Finally, use the WKB or WKT exporters to export to sf or some other package: ``` r -nc_s2 %>% - mutate(geometry = st_as_sfc(s2_as_binary(geometry))) %>% +nc_s2 %>% + mutate(geometry = st_as_sfc(s2_as_binary(geometry))) %>% st_as_sf() #> Simple feature collection with 100 features and 1 field #> Geometry type: GEOMETRY @@ -172,13 +181,13 @@ nc_s2 %>% #> 8 Gates POLYGON ((-76.46035 36.3739, -76.50246 36.45229, -76.49834 36.50… #> 9 Warren POLYGON ((-78.13472 36.23658, -78.10963 36.21351, -78.05835 36.2… #> 10 Stokes POLYGON ((-80.02406 36.54502, -80.0481 36.54713, -80.43531 36.55… -#> # … with 90 more rows +#> # ℹ 90 more rows ``` ## Acknowledgment This project gratefully acknowledges financial -[support](https://www.r-consortium.org/projects) from the +[support](https://www.r-consortium.org/) from the - + diff --git a/_pkgdown.yml b/_pkgdown.yml index 5a84a97a..c92e1ae3 100644 --- a/_pkgdown.yml +++ b/_pkgdown.yml @@ -1,9 +1,8 @@ -url: https://r-spatial.github.io/s2 +url: https://r-spatial.github.io/s2/ development: mode: auto template: bootstrap: 5 - reference: - title: Geography Constructors and Exporters desc: Convert objects to and from geography vectors @@ -18,7 +17,6 @@ reference: - s2_geog_from_wkb - s2_as_text - s2_as_binary - - title: Geography Transformations desc: Functions that operate on geography vectors and return geography vectors contents: @@ -32,7 +30,6 @@ reference: - s2_snap_to_grid - s2_union_agg - s2_centroid_agg - - title: Binary Geography Predicates desc: Functions that operate two geography vectors and return a logical vector contents: @@ -46,9 +43,9 @@ reference: - s2_touches - s2_within - s2_dwithin - - title: Geography Accessors - desc: Functions that operate one or more geography vectors and return a vector of values + desc: Functions that operate one or more geography vectors and return a vector of + values contents: - s2_is_collection - s2_is_empty @@ -63,35 +60,26 @@ reference: - s2_distance - s2_max_distance - s2_bounds_cap - - title: Matrix Functions desc: These functions return various relationships between two geography vectors - contents: - - s2_closest_feature - + contents: s2_closest_feature - title: Linear Referencing - contents: - - s2_interpolate - + contents: s2_interpolate - title: S2 Cell Utilities contents: - s2_cell_union - s2_cell_union_normalize - s2_cell - s2_cell_is_valid - - title: Utility Functions contents: - s2_earth_radius_meters - s2_options - s2_plot - - title: Example Data desc: Useful data for testing and demonstrating s2 functions - contents: - - starts_with("s2_data") - + contents: starts_with("s2_data") - title: Low-level Details desc: Interact with spherical geometry at a low level - contents: - - wk_handle.s2_geography + contents: wk_handle.s2_geography + diff --git a/configure b/configure index c394cf3b..388a0c84 100755 --- a/configure +++ b/configure @@ -1,4 +1,8 @@ -# Anticonf (tm) script by Jeroen Ooms (2020) + +# This configure script finds OpenSSL and Abseil, optionally building +# Abseil if not found. + +# Anticonf (tm) script by Jeroen Ooms (2020) for finding OpenSSL # This script will query 'pkg-config' for the required cflags and ldflags. # If pkg-config is unavailable or does not find the library, try setting # INCLUDE_DIR and LIB_DIR manually via e.g: @@ -8,9 +12,7 @@ PKG_CONFIG_NAME="openssl" PKG_DEB_NAME="libssl-dev" PKG_RPM_NAME="openssl-devel" -PKG_CSW_NAME="libssl_dev" -PKG_BREW_NAME="openssl@1.1" -PKG_TEST_FILE="tools/version.c" +PKG_BREW_NAME="openssl" PKG_LIBS="-lssl -lcrypto" PKG_CFLAGS="" @@ -27,19 +29,9 @@ if [ "$INCLUDE_DIR" ] || [ "$LIB_DIR" ]; then PKG_CFLAGS="-I$INCLUDE_DIR $PKG_CFLAGS" PKG_LIBS="-L$LIB_DIR $PKG_LIBS" elif [ "$PKGCONFIG_CFLAGS" ] || [ "$PKGCONFIG_LIBS" ]; then - echo "Found pkg-config cflags and libs!" + echo "Found OpenSSL pkg-config cflags and libs!" PKG_CFLAGS=${PKGCONFIG_CFLAGS} PKG_LIBS=${PKGCONFIG_LIBS} -elif [ `uname` = "Darwin" ]; then - test ! "$CI" && brew --version 2>/dev/null - if [ $? -eq 0 ]; then - BREWDIR=`brew --prefix` - PKG_CFLAGS="-I$BREWDIR/opt/openssl/include -I$BREWDIR/opt/openssl@1.1/include" - PKG_LIBS="-L$BREWDIR/opt/openssl/lib -L$BREWDIR/opt/openssl@1.1/lib $PKG_LIBS" - else - curl -sfL "https://autobrew.github.io/scripts/$PKG_BREW_NAME" > autobrew - . ./autobrew - fi fi # Find compiler @@ -48,10 +40,10 @@ CFLAGS=`${R_HOME}/bin/R CMD config CFLAGS` CPPFLAGS=`${R_HOME}/bin/R CMD config CPPFLAGS` # For debugging -echo "Testing compiler using PKG_CFLAGS=$PKG_CFLAGS" +echo "Testing compiler OpenSSL configuration using PKG_CFLAGS=$PKG_CFLAGS" # Test configuration -${CC} ${CPPFLAGS} ${PKG_CFLAGS} ${CFLAGS} -E ${PKG_TEST_FILE} >/dev/null 2>configure.log +${CC} ${CPPFLAGS} ${PKG_CFLAGS} ${CFLAGS} -E tools/test_openssl.c >/dev/null 2>configure.log # Customize the error if [ $? -ne 0 ]; then @@ -59,7 +51,6 @@ if [ $? -ne 0 ]; then echo "Configuration failed because $PKG_CONFIG_NAME was not found. Try installing:" echo " * deb: $PKG_DEB_NAME (Debian, Ubuntu, etc)" echo " * rpm: $PKG_RPM_NAME (Fedora, CentOS, RHEL)" - echo " * csw: $PKG_CSW_NAME (Solaris)" echo " * brew: $PKG_BREW_NAME (Mac OSX)" echo "If $PKG_CONFIG_NAME is already installed, check that 'pkg-config' is in your" echo "PATH and PKG_CONFIG_PATH contains a $PKG_CONFIG_NAME.pc file. If pkg-config" @@ -71,45 +62,14 @@ if [ $? -ne 0 ]; then exit 1 fi -# Try to link against the correct OpenSSL version -if [ -z "$AUTOBREW" ]; then -SONAME=`${CC} -E ${PKG_CFLAGS} src/tests/soname.h | sh | xargs` -if [ "$SONAME" ]; then -if [ `uname` = "Darwin" ]; then - PKG_LIBS_VERSIONED=`echo "${PKG_LIBS}" | sed "s/-lssl/-lssl.${SONAME}/" | sed "s/-lcrypto/-lcrypto.${SONAME}/"` -else - PKG_LIBS_VERSIONED=`echo "${PKG_LIBS}" | sed "s/-lssl/-l:libssl.so.${SONAME}/" | sed "s/-lcrypto/-l:libcrypto.so.${SONAME}/"` -fi - -# Test if versioned linking works -${CC} ${PKG_CFLAGS} src/tests/main.c ${PKG_LIBS_VERSIONED} -o src/main.exe 2>/dev/null -if [ $? -eq 0 ]; then PKG_LIBS="${PKG_LIBS_VERSIONED}"; fi -rm src/main.exe || true - -# Suppress opensslv3 warnings for now -if [ "$SONAME" = "3" ]; then -PKG_CFLAGS="$PKG_CFLAGS -DOPENSSL_SUPPRESS_DEPRECATED" -fi - -fi #SONAME -fi #AUTOBREW - -# Check pkg-config for abseil-cpp, but fall back to a cmake build. -# This should possibly be updated to check that the pkg-config detected -# version will actually work; however, the version of abseil that included -# pkg-config files is about the same as the minimum version required here. +# Check pkg-config for abseil-cpp, but fall back to a cmake build +# because a sufficient version of abseil-cpp is not available on +# all platforms (notably, Ubuntu 20.04 and Ubuntu 22.04). export PKG_CONFIG_PATH="${PKG_CONFIG_PATH}:`pwd`/tools/pkgconfig" -# Allow developers to set R_S2_ABSL_HOME in .Renviron to avoid building -# Abseil on every package rebuild. This can be built from this directory using -# tools/build_absl.sh path/to/dir (then R_S2_ABSL_HOME=path/to/dir in .Renviron) -if [ ! -z "${R_S2_ABSL_HOME}" ]; then - export PKG_CONFIG_PATH="{$R_S2_ABSL_HOME}/lib/pkgconfig:${PKG_CONFIG_PATH}" -fi - echo "** Using PKG_CONFIG_PATH=${PKG_CONFIG_PATH}" -if pkg-config absl_s2 --libs 2>/dev/null; then +if pkg-config absl_s2 --libs >/dev/null 2>/dev/null; then echo "** Using abseil-cpp from pkg-config" PKGCONFIG_CFLAGS=`pkg-config --cflags-only-I absl_s2` @@ -135,15 +95,38 @@ else # Clean up build directory rm -rf tools/build + # Depending on the cmake options this can end up in a subdirectory of lib + ABSL_BASE_PC=`find tools/dist -name absl_base.pc` + R_S2_PKG_CONFIG_PATH=`dirname "${ABSL_BASE_PC}"` R_S2_ABSL_HOME="`pwd`/tools/dist" - export PKG_CONFIG_PATH="${R_S2_ABSL_HOME}/lib/pkgconfig:${PKG_CONFIG_PATH}" + export PKG_CONFIG_PATH="${R_S2_PKG_CONFIG_PATH}:${PKG_CONFIG_PATH}" echo "** Using PKG_CONFIG_PATH=${PKG_CONFIG_PATH}" PKGCONFIG_LIBS=`pkg-config --libs absl_s2` + if [ -z "${PKGCONFIG_LIBS}" ]; then + echo "** Failed to resolve built vendored copy of Abseil using pkg-config" + exit 1 + fi PKG_CFLAGS="-I${R_S2_ABSL_HOME}/include ${PKG_CFLAGS}" PKG_LIBS="${PKGCONFIG_LIBS} ${PKG_LIBS}" fi +# Check compile of test file +CXX17="`${R_HOME}/bin/R CMD config CXX17`" +CXX17FLAGS=`"${R_HOME}"/bin/R CMD config CXX17FLAGS` +CXX17STD=`"${R_HOME}"/bin/R CMD config CXX17STD` + +echo "Testing Abseil configuration using PKG_CFLAGS=${PKG_CFLAGS}" + +${CXX17} ${CPPFLAGS} ${PKG_CFLAGS} ${CXX17FLAGS} ${CXX17STD} -E tools/test_absl.cc >/dev/null 2>>configure.log +if [ $? -ne 0 ]; then + echo "Test compile failed!" + echo "------- Error ---------" + cat configure.log + echo "-----------------------" + exit 1 +fi + # From apache/arrow/r/configure: # If on Raspberry Pi, need to manually link against latomic # See: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81358 for similar example diff --git a/docker-compose.yml b/docker-compose.yml new file mode 100644 index 00000000..2babcd90 --- /dev/null +++ b/docker-compose.yml @@ -0,0 +1,91 @@ + +# Docker compose setup for testing s2 package install +# +# The s2 R package requires OpenSSL and Abseil, of which Abseil +# is not trivially installable. Because of this, we have several +# strategies for locating or building a version of it from the +# configure script. This file (and the images it refers to in +# tools/docker) are to make sure that the install works on a +# variety of linux platforms/system Abseil versions. +# +# Usage: +# +# docker compose run --rm ubuntu-20 +# +# ...for the default behaviour (clean + install), or use +# +# docker compose run --rm -it ubuntu-20 bash +# +# ...to open the environment interactively. The build of the image +# should be cached until you explicitly decide to rebuild it using +# `docker compose build ubuntu-20`. +# +# VSCode users can leverage the Remotes extension that allows connecting +# to a running container. This involves opening a separate terminal and +# running `docker compose run --rm -it ubuntu-20 bash` to keep the +# container running (during which time you can connect to it from VSCode). + +services: + ubuntu-20: + build: + context: . + args: + - IMAGE=ubuntu:20.04 + dockerfile: tools/docker/debian.dockerfile + volumes: + - .:/s2 + + ubuntu-22: + build: + context: . + args: + - IMAGE=ubuntu:22.04 + dockerfile: tools/docker/debian.dockerfile + volumes: + - .:/s2 + + ubuntu-24: + build: + context: . + args: + - IMAGE=ubuntu:24.04 + dockerfile: tools/docker/debian.dockerfile + volumes: + - .:/s2 + + # CRAN platform + debian-testing: + build: + context: . + args: + - IMAGE=debian:testing + dockerfile: tools/docker/debian.dockerfile + volumes: + - .:/s2 + + # This is what CRAN runs + fedora-36: + build: + context: . + args: + - IMAGE=fedora:36 + dockerfile: tools/docker/fedora.dockerfile + volumes: + - .:/s2 + + # First version that includes abseil-cpp as a system package + fedora-39: + build: + context: . + args: + - IMAGE=fedora:39 + dockerfile: tools/docker/fedora.dockerfile + volumes: + - .:/s2 + + alpine: + build: + context: . + dockerfile: tools/docker/alpine.dockerfile + volumes: + - .:/s2 diff --git a/src/RcppExports.cpp b/src/RcppExports.cpp index 6350151d..24a5ac1b 100644 --- a/src/RcppExports.cpp +++ b/src/RcppExports.cpp @@ -1344,12 +1344,12 @@ BEGIN_RCPP END_RCPP } -RcppExport SEXP c_s2_geography_writer_new(void *, void *, void *, void *); -RcppExport SEXP c_s2_handle_geography(void *, void *); -RcppExport SEXP c_s2_handle_geography_tessellated(void *, void *); -RcppExport SEXP c_s2_projection_mercator(void *); -RcppExport SEXP c_s2_projection_orthographic(void *); -RcppExport SEXP c_s2_projection_plate_carree(void *); +RcppExport SEXP c_s2_geography_writer_new(SEXP, SEXP, SEXP, SEXP); +RcppExport SEXP c_s2_handle_geography(SEXP, SEXP); +RcppExport SEXP c_s2_handle_geography_tessellated(SEXP, SEXP); +RcppExport SEXP c_s2_projection_mercator(SEXP); +RcppExport SEXP c_s2_projection_orthographic(SEXP); +RcppExport SEXP c_s2_projection_plate_carree(SEXP); RcppExport SEXP c_s2_trans_s2_lnglat_new(void); RcppExport SEXP c_s2_trans_s2_point_new(void); diff --git a/tests/testthat/test-s2-cell.R b/tests/testthat/test-s2-cell.R index 27a938df..fb02b7a0 100644 --- a/tests/testthat/test-s2-cell.R +++ b/tests/testthat/test-s2-cell.R @@ -11,6 +11,8 @@ test_that("s2_cell class works", { }) test_that("s2_cell bit64::integer64 support works", { + skip_if_not_installed("bit64") + cells <- c(as_s2_cell(NA_character_), s2_cell_sentinel()) int64s <- bit64::as.integer64(cells) expect_identical(int64s, bit64::as.integer64(c(NA, -1))) diff --git a/tools/build_absl.sh b/tools/build_absl.sh index 4b237e3b..86f24d25 100755 --- a/tools/build_absl.sh +++ b/tools/build_absl.sh @@ -1,9 +1,19 @@ # https://cran.r-project.org/doc/manuals/r-release/R-exts.html#Using-cmake +: ${R_HOME=`R RHOME`} +if test -z "${R_HOME}"; then + echo "could not determine R_HOME" + exit 1 +fi + +# Do our best to pass on the user MAKEFLAGS. This can result in much faster +# compilation of the vendored library. +MAKEFLAGS=`${R_HOME}/bin/Rscript -e 'readRenviron("~/.R/Makevars"); cat(Sys.getenv("MAKEFLAGS"))'` + if test -z "$MAKE"; then MAKE="`which make`"; fi if ${MAKE} --version ; then - echo "Using MAKE=$MAKE $MAKEVARS" + echo "Using MAKE=$MAKE $MAKEFLAGS" else echo "make not found" exit 1 @@ -13,18 +23,12 @@ if test -z "$CMAKE"; then CMAKE="`which cmake`"; fi if test -z "$CMAKE"; then CMAKE=/Applications/CMake.app/Contents/bin/cmake; fi if "${CMAKE}" --version ; then echo "Using CMAKE=$CMAKE" - echo "Using MAKE=$MAKE $MAKEVARS" + echo "Using MAKE=$MAKE $MAKEFLAGS" else echo "cmake not found" exit 1 fi -: ${R_HOME=`R RHOME`} -if test -z "${R_HOME}"; then - echo "could not determine R_HOME" - exit 1 -fi - CC=`"${R_HOME}/bin/R" CMD config CC` CXX="`${R_HOME}/bin/R CMD config CXX17` `${R_HOME}/bin/R CMD config CXX17STD`" CFLAGS=`"${R_HOME}/bin/R" CMD config CFLAGS` @@ -49,11 +53,10 @@ cd "tools/build/abseil-cpp" -DBUILD_SHARED_LIBS=OFF \ -DCMAKE_POSITION_INDEPENDENT_CODE=ON \ -DCMAKE_INSTALL_PREFIX="${CMAKE_INSTALL_PREFIX}" \ - -DCMAKE_OSX_DEPLOYMENT_TARGET=11.3 \ -DCMAKE_CXX_STANDARD=17 \ -DABSL_PROPAGATE_CXX_STD=ON \ "../../vendor/abseil-cpp" && - ${MAKE} ${MAKEVARS} && + ${MAKE} ${MAKEFLAGS} && "${CMAKE}" --install . cd ../../.. diff --git a/tools/docker/alpine.dockerfile b/tools/docker/alpine.dockerfile new file mode 100644 index 00000000..cbeedb0b --- /dev/null +++ b/tools/docker/alpine.dockerfile @@ -0,0 +1,12 @@ + +ARG IMAGE=alpine:latest + +FROM ${IMAGE} + +RUN apk add bash R R-dev abseil-cpp-dev + +# Make sure we can use all cores to install things +RUN mkdir ~/.R && echo "MAKEFLAGS = -j$(nproc)" > ~/.R/Makevars +RUN R -e 'install.packages(c("wk", "bit64", "Rcpp", "testthat"), repos = "https://cloud.r-project.org")' + +CMD R CMD INSTALL /s2 --preclean && R -e 'testthat::test_local("/s2")' diff --git a/tools/docker/debian.dockerfile b/tools/docker/debian.dockerfile new file mode 100644 index 00000000..0d4e436e --- /dev/null +++ b/tools/docker/debian.dockerfile @@ -0,0 +1,16 @@ + +ARG IMAGE=debian:testing + +FROM ${IMAGE} + +RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y \ + r-base cmake libcurl4-openssl-dev libssl-dev + +# Not all versions of ubuntu/debian have libabsl-dev +RUN apt-get install -y libabsl-dev || true + +# Make sure we can use all cores to install things +RUN mkdir ~/.R && echo "MAKEFLAGS = -j$(nproc)" > ~/.R/Makevars +RUN R -e 'install.packages(c("wk", "bit64", "Rcpp", "testthat"), repos = "https://cloud.r-project.org")' + +CMD R CMD INSTALL /s2 --preclean && R -e 'testthat::test_local("/s2")' diff --git a/tools/docker/fedora.dockerfile b/tools/docker/fedora.dockerfile new file mode 100644 index 00000000..b76573e9 --- /dev/null +++ b/tools/docker/fedora.dockerfile @@ -0,0 +1,12 @@ + +ARG IMAGE=fedora:latest + +FROM ${IMAGE} + +RUN dnf install -y R cmake abseil-cpp-devel openssl-devel + +# Make sure we can use all cores to install things +RUN mkdir ~/.R && echo "MAKEFLAGS = -j$(nproc)" > ~/.R/Makevars +RUN R -e 'install.packages(c("wk", "bit64", "Rcpp", "testthat"), repos = "https://cloud.r-project.org")' + +CMD R CMD INSTALL /s2 --preclean && R -e 'testthat::test_local("/s2")' diff --git a/tools/test_absl.cc b/tools/test_absl.cc new file mode 100644 index 00000000..c460daaf --- /dev/null +++ b/tools/test_absl.cc @@ -0,0 +1,6 @@ + +#include "absl/base/config.h" + +#if defined(ABSL_LTS_RELEASE_VERSION) && ABSL_LTS_RELEASE_VERSION < 20230802L +#error "Abseil C++ version is too old" +#endif diff --git a/tools/version.c b/tools/test_openssl.c similarity index 100% rename from tools/version.c rename to tools/test_openssl.c