Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add capability to version cases #105

Merged
merged 4 commits into from
Jun 15, 2022

Conversation

alistaire47
Copy link
Contributor

Successor to #104; closes #101. This PR inserts versioning for cases into params via a benchmark-configurable function that takes a case (a named list of params) and returns an integer version.

There are a couple important questions here:

  1. Should version be inserted as a param in the JSON (and therefore in conbench)? We're already inserting a lot of stuff into params that's arguably metadata (cpu_count, lib_path, a dataframe of packages); at some point we should move this stuff to a metadata section.
  2. What should the default behavior be? This sets everything to version 1L, but I haven't quite figured out yet whether this will break all the histories in conbench. If so, it's probably better to change it to default to not setting it.

@alistaire47 alistaire47 self-assigned this Jun 8, 2022
@alistaire47
Copy link
Contributor Author

Regarding 2, what exactly does create a history discontinuity in conbench? @austin3dickey have you happened to learn this yet?

@jonkeane
Copy link
Contributor

jonkeane commented Jun 8, 2022

Regarding 2, what exactly does create a history discontinuity in conbench? @austin3dickey have you happened to learn this yet?

We should document this since it comes up frequently, but:

Differences in:

  • case values "tags"
  • contexts
  • hardware (though not all values in a hardware are taken into account, the additional info, for example is allowed to vary)

https://github.com/conbench/conbench/blob/a3073041f702a4da8ad708afa776be6d7ab0ca72/conbench/entities/history.py#L35-L68

@jonkeane
Copy link
Contributor

jonkeane commented Jun 8, 2022

  1. What should the default behavior be? This sets everything to version 1L, but I haven't quite figured out yet whether this will break all the histories in conbench. If so, it's probably better to change it to default to not setting it.

We definitely shouldn't break history — we could either migrate and add 1s in everywhere or we could have a special case in conbench history where for version NULL == 1

tests/testthat/test-run.R Outdated Show resolved Hide resolved
@jonkeane
Copy link
Contributor

jonkeane commented Jun 8, 2022

  1. Should version be inserted as a param in the JSON (and therefore in conbench)? We're already inserting a lot of stuff into params that's arguably metadata (cpu_count, lib_path, a dataframe of packages); at some point we should move this stuff to a metadata section.

Hmm, yeah I think this is ok. It is like many of the other variables that defines a case (at least on the conbench side)...

@alistaire47
Copy link
Contributor Author

Differences in:

* case values "tags"

* contexts

* hardware (though not _all_ values in a hardware are taken into account, the additional info, for example is allowed to vary)

Hm, so we are writing most params (currently including case_version on this branch) to tags. I think the simplest approach is to default to not writing it then (but do write it when it's explicitly set!); otherwise we'll need special-casing elsewhere

@@ -93,6 +98,8 @@ Benchmark <- function(name,
after_each = TRUE,
teardown = TRUE,
valid_params = function(params) params,
case_version = function(params) NULL,
packages_used = function(params) "arrow",
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added this because it's already called, but previously we were relying on every benchmark adding it in the same way though .... I'm now leaning more towards R6-ifying this class

Copy link
Collaborator

@boshek boshek left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not a ton to say other than that it feels like until we actually need a version change we should stick with the NULL == 1 situation.

@alistaire47
Copy link
Contributor Author

Not a ton to say other than that it feels like until we actually need a version change we should stick with the NULL == 1 situation.

Right now NULL != 1, because when it's NULL it won't add case_version to tags, but when it's 1 it will (and therefore will break history). Dunno if that's good, really, but it's easiest, as if we start defaulting everything to 1 it will break all the histories unless we go adjust everything

Copy link
Contributor

@jonkeane jonkeane left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is looking good — thanks! A few comments that might be quick to fix or a longer thread to unravel.

bm_versioned <- Benchmark(
"versioned",
setup = function(x = c('foo', 'bar')) cat(x),
case_version = function(params) c("foo" = 1L, "bar" = 2L)[params$x]
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can and will look at the code, but we should also test what happens if foo is not mentioned here? Is that possible?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because of how I constructed this example, if params were list(x = "baz") (or any novel value), it will return NA, which will get written to the tags as "tags": {..., "case_version": null}, which I think may break history in conbench (though I'm not 💯).

R/run.R Outdated
@@ -186,6 +186,8 @@ run_bm <- function(bm, ..., n_iter = 1, profiling = FALSE, global_params = list(
defaults <- lapply(get_default_args(bm$setup), head, 1)
defaults$cpu_count <- parallel::detectCores()
params <- modifyList(defaults, list(...))
params$case_version <- bm$case_version(params)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm looks like my question in the tests below: I think this would return NA? Would it be possible to wrap this such that if something isn't defined in the function it'll return NULL?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yep, that's what I'm thinking; we should either do stopifnot(is.na(case_version)) or automatically replace it with NULL (with a warning, probably?). I'm leaning towards erroring—we should see this when adjusting benchmarks (presuming we run them with all arg combinations), and we don't want to accidentally switch back to not versioning without noticing.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, put in a stopifnot() and a test for it

@alistaire47
Copy link
Contributor Author

ah crap my git branches got conflated! sorry, fixing

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Store a marker for benchmark versions
3 participants