Skip to contents

Create a model factory function

Usage

base_model(
  fields = list(),
  ...,
  .model_pre_init = NULL,
  .model_post_init = NULL,
  .validators_before = list(),
  .validators_after = list(),
  .strict_args_order = FALSE,
  .allow_na = FALSE,
  .extra = c("ignore", "allow", "forbid")
)

Arguments

fields

A named list of field definitions.

...

Named arguments of field definitions. Normally either fields or ... is supplied.

.model_pre_init

A callback function that is executed before the type checks.

.model_post_init

A callback function that is executed after the type checks.

.validators_before

A named list of field validators that are executed before the type checks.

.validators_after

A named list of field validators that are executed after the type checks.

.strict_args_order

If set to TRUE, the .x parameter of the returned model factory function will be the last function argument. This is useful if you want to pass the arguments unnamed.

.allow_na

Whether to allow NA values for all fields.

.extra

Whether to allow extra fields without type check.

Value

A model factory function.

Examples

# ---
# Models
my_model <- base_model(
  a = is.integer,
  b = is.integer,
  txt = is.character
)

# Succeeds
my_model(a = 1L, b = 2L, txt = "My awesome model")
#> $a
#> [1] 1
#> 
#> $b
#> [1] 2
#> 
#> $txt
#> [1] "My awesome model"
#> 

# Fails
try(my_model(a = 1, b = 2L, txt = "My awesome model"))
#> Error in my_model(a = 1, b = 2L, txt = "My awesome model") : 
#>   Type check(s) failed
#> ---
#> Type check failed for 'a'
#> value:  num 1
#> type: double
#> class: numeric
#> length: 1
#> expected: .Primitive("is.integer")

# ---
# Functions
f <- function(a, b) {
  check_args(a = is.integer, b = is.integer)
  a + b
}

# Succeeds
f(4L, 5L)
#> [1] 9

# Fails
try(f(4, 5))
#> Error in base_model(fields)(.x = func_env) : Type check(s) failed
#> ---
#> Type check failed for 'a'
#> value:  num 4
#> type: double
#> class: numeric
#> length: 1
#> expected: .Primitive("is.integer")
#> ---
#> Type check failed for 'b'
#> value:  num 5
#> type: double
#> class: numeric
#> length: 1
#> expected: .Primitive("is.integer")

# ---
# Data frames
df <- data.frame(
  id = 1:2,
  name = c("Donald", "Lee"),
  surname = c("Byrd", "Morgan")
)

df_model <- base_model(
  id = is.integer,
  name = is.character,
  surname = is.character,
  full_name = is.character,
  .model_pre_init = function(obj) {
    obj$full_name <- paste(obj$name, obj$surname)
    return(obj)
  }
)

# Succeeds
df_model(.x = df)
#>   id   name surname   full_name
#> 1  1 Donald    Byrd Donald Byrd
#> 2  2    Lee  Morgan  Lee Morgan

# Fails
df$id <- NULL
try(df_model(.x = df))
#> Error in df_model(.x = df) : Type check(s) failed
#> ---
#> Type check failed for 'id'
#> value:  NULL
#> type: NULL
#> class: NULL
#> length: 0
#> expected: .Primitive("is.integer")