Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .Rbuildignore
Original file line number Diff line number Diff line change
Expand Up @@ -9,3 +9,4 @@ air.toml
^_pkgdown\.yml$
^docs$
^pkgdown$
^.devcontainer$
19 changes: 19 additions & 0 deletions .devcontainer/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
FROM --platform=linux/amd64 ghcr.io/mmyrte/evoland:latest
LABEL authors="Carlson Büth, Jan Hartman" \
version="8.3" \
description="Docker image for Dinamica EGO."

# Vignettes are being built with quarto
RUN /rocker_scripts/install_quarto.sh

# Hand-knitted dependency discovery from DESCRIPTION avoids cache invalidation versus a
# remotes::install_deps based solution.
WORKDIR /builddir
COPY DESCRIPTION /builddir/DESCRIPTION
COPY .devcontainer/install_pkg_deps.r /builddir/install_pkg_deps.r
RUN /builddir/install_pkg_deps.r && rm -r /builddir
WORKDIR /

# Install development dependencies for vscode-style development.
COPY .devcontainer/install_vscode_devtools.sh /rocker_scripts/install_vscode_devtools.sh
RUN /rocker_scripts/install_vscode_devtools.sh
40 changes: 40 additions & 0 deletions .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
// For format details, see https://aka.ms/devcontainer.json. For config options, see the README at:
// https://github.com/microsoft/vscode-dev-containers/tree/v0.191.1/containers/debian
{
"name": "evoland-devcontainer",
"build": {
"dockerfile": "Dockerfile",
"context": "..",
"args": {
"platform": "linux/amd64"
}
},
"mounts": [
{
"source": "${localEnv:EVOLAND_CACHEDIR}",
"target": "/mnt/evoland-cache",
"type": "bind"
}
],
"containerEnv": {
"EVOLAND_CACHEDIR": "/mnt/evoland-cache"
},
"customizations": {
"vscode": {
"settings": {
"git.path": "/usr/bin/git",
"r.rterm.linux": "/usr/local/bin/radian",
"shellcheck.executablePath": "/usr/bin/shellcheck",
"r.plot.useHttpgd": true,
"r.bracketedPaste": true,
"rewrap.wrappingColumn": 88
},
"extensions": [
"RDebugger.r-debugger",
"REditorSupport.r",
"quarto.quarto",
"timonwong.shellcheck"
]
}
}
}
19 changes: 19 additions & 0 deletions .devcontainer/install_pkg_deps.r
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
#!/usr/bin/env Rscript

# Reusing logic from remotes::local_package_deps
# MIT licensed, source at https://github.com/r-lib/remotes/

desc <- remotes:::read_dcf("DESCRIPTION")

dependencies <- c("Depends", "Imports", "LinkingTo", "Suggests")
dependencies <- intersect(dependencies, names(desc))
pkg_deps <-
lapply(desc[dependencies], remotes:::parse_deps) |>
lapply(`[[`, "name") |>
unlist(use.names = FALSE)

pkgs_to_install <- setdiff(pkg_deps, installed.packages()[, 1])
install.packages(
pkgs_to_install,
Ncpus = max(1L, parallel::detectCores())
)
36 changes: 36 additions & 0 deletions .devcontainer/install_vscode_devtools.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
#!/usr/bin/env bash

# Abort script if any command exits with non-zero status. Not foolproof.
set -e

NCPUS=${NCPUS:-"-1"}

apt-get update -qq
apt-get -y --no-install-recommends install \
git \
htop \
libfontconfig1-dev \
libfribidi-dev \
libgit2-dev \
libharfbuzz-dev \
pipx \
shellcheck

rm -rf /var/lib/apt/lists/*

PIPX_BIN_DIR=/usr/local/bin pipx install radian

install2.r --error --skipinstalled -n $NCPUS \
covr \
devtools \
languageserver \
lobstr \
microbenchmark \
profvis \
quarto \
rlang

# httpgd is currently off of CRAN because of c++ compiler conflicts
# https://github.com/nx10/httpgd/issues/218

R -e "remotes::install_github('nx10/httpgd')"
56 changes: 56 additions & 0 deletions .github/workflows/R-CMD-check.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
# 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:
branches: [main, master]
workflow_dispatch:

name: R-CMD-check.yaml

permissions: read-all

jobs:
R-CMD-check:
runs-on: ${{ matrix.config.os }}

name: ${{ matrix.config.os }} (${{ matrix.config.r }})

strategy:
fail-fast: false
matrix:
config:
- { os: macos-latest, r: "release" }
# - {os: windows-latest, r: 'release'}
# - {os: ubuntu-latest, r: 'devel', http-user-agent: 'release'}
- { os: ubuntu-latest, r: "release" }
# - { os: ubuntu-24.04-arm, r: "release" }
# - {os: ubuntu-latest, r: 'oldrel-1'}

env:
GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }}
R_KEEP_PKG_SOURCE: yes

steps:
- uses: actions/checkout@v4

- uses: r-lib/actions/setup-pandoc@v2

- uses: r-lib/actions/setup-r@v2
with:
r-version: ${{ matrix.config.r }}
http-user-agent: ${{ matrix.config.http-user-agent }}
use-public-rspm: true

- name: Install macOS system dependencies
if: runner.os == 'macos'
run: brew install gdal proj

- uses: r-lib/actions/setup-r-dependencies@v2
with:
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")'
1 change: 0 additions & 1 deletion .github/workflows/pkgdown.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
on:
push:
branches: [main, master]
pull_request:
release:
types: [published]
workflow_dispatch:
Expand Down
8 changes: 8 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -56,3 +56,11 @@ docs

# generally ignore databases, like .evolanddb, .duckdb, anything.db
*db

# IDE specific artefacts
*compile_commands*
*cobertura*
.cache/

# ignore drafts
*suddel*
14 changes: 8 additions & 6 deletions DESCRIPTION
Original file line number Diff line number Diff line change
Expand Up @@ -10,28 +10,28 @@ URL: https://ethzplus.github.io/evoland-plus, https://github.com/ethzplus/evolan
BugReports: https://github.com/ethzplus/evoland-plus/issues
Encoding: UTF-8
Roxygen: list(markdown = TRUE)
RoxygenNote: 7.3.2
RoxygenNote: 7.3.3
Depends:
R (>= 4.2)
Imports:
curl,
data.table,
DBI,
duckdb,
duckdb (>= 1.4.3),
glue,
purrr,
qs2,
R6,
Rcpp,
rlang,
stringi,
terra
Suggests:
base64enc,
butcher,
pROC,
tinytest,
processx,
quarto,
ranger
ranger,
tinytest
VignetteBuilder: quarto
Config/testthat/edition: 3
LinkingTo:
Expand All @@ -56,11 +56,13 @@ Collate:
'periods_t.R'
'pred_data_t.R'
'pred_meta_t.R'
'reporting_t.R'
'trans_meta_t.R'
'trans_models_glm.R'
'trans_models_rf.R'
'trans_models_t.R'
'trans_preds_t.R'
'util.R'
'util_dinamica.r'
'util_download.R'
'util_terra.R'
4 changes: 4 additions & 0 deletions NAMESPACE
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ S3method(validate,pred_data_t_bool)
S3method(validate,pred_data_t_float)
S3method(validate,pred_data_t_int)
S3method(validate,pred_meta_t)
S3method(validate,reporting_t)
S3method(validate,trans_meta_t)
S3method(validate,trans_models_t)
S3method(validate,trans_preds_t)
Expand All @@ -43,6 +44,7 @@ export(as_neighbors_t)
export(as_periods_t)
export(as_pred_data_t)
export(as_pred_meta_t)
export(as_reporting_t)
export(as_trans_meta_t)
export(as_trans_models_t)
export(as_trans_preds_t)
Expand All @@ -57,6 +59,7 @@ export(create_pred_meta_t)
export(create_trans_meta_t)
export(download_and_verify)
export(evoland_db)
export(exec_dinamica)
export(extract_using_coords_t)
export(fit_glm)
export(fit_ranger)
Expand All @@ -65,6 +68,7 @@ export(gof_ranger)
export(grrf_filter)
export(parquet_duckdb)
export(print_rowwise_yaml)
export(run_evoland_dinamica_sim)
export(validate)
importFrom(Rcpp,sourceCpp)
importFrom(data.table,":=")
Expand Down
6 changes: 4 additions & 2 deletions R/coords_t.R
Original file line number Diff line number Diff line change
Expand Up @@ -91,10 +91,12 @@ print.coords_t <- function(x, nrow = 10, ...) {
#' @describeIn coords_t Create a set of square coordinates
#' @export
create_coords_t_square <- function(epsg, extent, resolution, ...) {
if (!rlang::is_scalar_integerish(epsg)) {
if (
!(length(epsg) == 1L && (is.integer(epsg) || (is.numeric(epsg) && epsg == as.integer(epsg))))
) {
stop("epsg must be scalar integerish")
}
if (!rlang::is_scalar_double(resolution)) {
if (!(length(resolution) == 1L && is.double(resolution))) {
stop("resolution must be scalar double")
}
if (!inherits(extent, "SpatExtent")) {
Expand Down
58 changes: 2 additions & 56 deletions R/evoland_db.R
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
#'
#' @description
#' An R6 class that provides an interface to a folder-based data storage system
#' for the evoland package. Each table is stored as a parquet (or CSV) file.
#' for the evoland package. Each table is stored as a parquet (or JSON) file.
#' This class uses DuckDB for in-memory SQL operations while persisting data
#' to disk in parquet format for better compression.
#'
Expand All @@ -27,20 +27,16 @@ evoland_db <- R6::R6Class(
#' @description
#' Initialize a new evoland_db object
#' @param path Character string. Path to the data folder.
#' @param default_format Character. Default file format ("parquet" or "csv").
#' Default is "parquet".
#' @param ... passed on to `set_report`
#'
#' @return A new `evoland_db` object
initialize = function(
path,
default_format = c("parquet", "csv"),
...
) {
# Initialize parent class with spatial extension
super$initialize(
path = path,
default_format = default_format,
extensions = "spatial"
)

Expand All @@ -50,63 +46,13 @@ evoland_db <- R6::R6Class(
invisible(self)
},

#' @description
#' Fetch data from storage with evoland-specific view support
#' @param table_name Character string. Name of the table to query.
#' @param where Character string. Optional WHERE clause for the SQL query.
#' @param limit integerish, limit the amount of rows to return
#'
#' @return A data.table
fetch = function(table_name, where = NULL, limit = NULL) {
# Check if this is a view (active binding)
if (
# TODO these should probably not be active bindings, but instead methods with
# predefined query parameters
table_name %in%
c("lulc_meta_long_v", "pred_sources_v", "transitions_v", "extent", "coords_minimal")
) {
return(self[[table_name]])
}

file_info <- private$get_file_path(table_name)

if (!file_info$exists) {
stop("Table `", table_name, "` does not exist")
}

super$fetch(table_name, where, limit)
},

### Setter methods ----
#' @description
#' Set reporting metadata
#' @param ... each named argument is entered into the table with the argument name
#' as its key
set_report = function(...) {
params <- list(...)
if (self$row_count("reporting_t") == 0L) {
# only upsert if these values are missing upon DB init
params[["report_name"]] <-
params[["report_name"]] %||% "evoland_scenario"
params[["report_name_pretty"]] <-
params[["report_name_pretty"]] %||% "Default Evoland Scenario"
params[["report_include_date"]] <-
params[["report_include_date"]] %||% "TRUE"
params[["creator_username"]] <-
params[["creator_username"]] %||% Sys.getenv("USER", unset = "unknown")
}
params[["last_opened"]] <- format(Sys.time(), "%Y-%m-%dT%H:%M:%SZ", tz = "UTC")
params[["last_opened_username"]] <- Sys.getenv("USER", unset = "unknown")

self$commit(
data.table::as.data.table(list(
key = names(params), # cannot name a column "key" in data.table()
value = unlist(params)
)),
table_name = "reporting_t",
key_cols = "key",
method = "upsert"
)
db_set_report(self, ...)
},

#' @description
Expand Down
2 changes: 1 addition & 1 deletion R/evoland_db_neighbors.R
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ evoland_db$set("public", "generate_neighbor_predictors", function() {
}"
)
self$execute(
"create or replace view pred_meta_upsert_v as
"create or replace view pred_meta_upsert_v as
select name, pretty_name, description, orig_format, sources, unit, factor_levels
from pred_meta_neighbors_t"
)
Expand Down
Loading