Skip to content

Decay curve 2 - #392

Merged
d-morrison merged 55 commits into
mainfrom
decay-curve-2
Jul 25, 2026
Merged

Decay curve 2#392
d-morrison merged 55 commits into
mainfrom
decay-curve-2

Conversation

@d-morrison

@d-morrison d-morrison commented Feb 18, 2025

Copy link
Copy Markdown
Member

This pull request introduces a new interactive Shiny application for visualizing antigen-antibody kinetics models, along with several supporting functions and package infrastructure updates. It also adds new plotting and mathematical functions for decay curves, exposes additional functions to users, and improves error messaging. The changes enhance the package's interactivity, usability, and extensibility for modeling and visualization.

Major feature: Interactive Shiny app for kinetics modeling

  • Added a new Shiny app (curve_app) for interactively exploring antigen-antibody kinetics, with UI (curve_app_ui), server logic (curve_app_server), and a new launch script (app.R). The app allows users to adjust model parameters via sliders and view real-time plots and derived values. [1] [2] [3] [4]

New modeling and plotting utilities

  • Added antibody_decay_curve and pathogen_decay_curve functions for simulating and plotting antibody and pathogen decay over time. [1] [2]
  • Added plot_decay_curve for easy plotting of decay functions using ggplot2.
  • Introduced helper functions t1f (time to end of active infection) and y1f (peak antibody concentration). [1] [2]

Package infrastructure and configuration

  • Updated .Rbuildignore and added .rscignore to exclude app and deployment files from builds; incremented package version to 1.4.0.9004. [1] [2] [3] [4]
  • Added app_config.R for app-specific configuration and file access helpers.
  • Registered new functions for export and updated NAMESPACE and import statements to support the Shiny app and plotting features. [1] [2] [3] [4] [5] [6] [7] [8] [9]

Error handling improvements

  • Improved error messages in autoplot.seroincidence and autoplot.seroincidence.by to use cli::cli_abort for clearer and more informative errors. [1] [2]

Miscellaneous

  • Added a script to disable shiny autoload in certain contexts (_disable_autoload.R).
  • Minor README and documentation tweaks. [1] [2]

These changes significantly expand the package's capabilities for modeling, visualization, and interactive exploration of serological data.

@codecov

codecov Bot commented Feb 18, 2025

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 36.20072% with 178 lines in your changes missing coverage. Please review.
✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
R/curve_app_ui.R 0.00% 94 Missing ⚠️
R/curve_app_server.R 0.00% 80 Missing ⚠️
R/curve_app.R 0.00% 4 Missing ⚠️
Files with missing lines Coverage Δ
R/antibody_decay_curve.R 100.00% <100.00%> (ø)
R/autoplot.seroincidence.R 100.00% <100.00%> (+69.23%) ⬆️
R/pathogen_decay_curve.R 100.00% <100.00%> (ø)
R/plot_decay_curve.R 100.00% <100.00%> (ø)
R/t1f.R 100.00% <100.00%> (ø)
R/validate_decay_params.R 100.00% <100.00%> (ø)
R/y1f.R 100.00% <100.00%> (ø)
R/curve_app.R 0.00% <0.00%> (ø)
R/curve_app_server.R 0.00% <0.00%> (ø)
R/curve_app_ui.R 0.00% <0.00%> (ø)

@d-morrison

Copy link
Copy Markdown
Member Author

@copilot rebase on main; resolve merge conflicts

Copilot AI commented Jan 20, 2026

Copy link
Copy Markdown
Contributor

@d-morrison I've opened a new pull request, #486, to work on those changes. Once the pull request is ready, I'll request review from you.

Copilot AI and others added 5 commits January 20, 2026 20:47
Co-authored-by: d-morrison <2474437+d-morrison@users.noreply.github.com>
Co-authored-by: d-morrison <2474437+d-morrison@users.noreply.github.com>
Co-authored-by: d-morrison <2474437+d-morrison@users.noreply.github.com>
Co-authored-by: d-morrison <2474437+d-morrison@users.noreply.github.com>

Copy link
Copy Markdown
Member Author

ARD summary — round pushed as 6662946

The last round's two NEWS fixes were staged in a session that ended before pushing, so they're redone here and batched with the merge and the lint fix, per the plan in my earlier comment.

# Finding Disposition What changed
1 NEWS.md:74-75 — bullet claims a spurious and entry was removed from Imports; false on every count Address Bullet deleted. and is real (and::or() at R/check_strata.R:45) and still in Imports; the diff only reordered it.
2 Missing NEWS bullet for the cli::cli_abort() change Address Added, scoped to autoplot.seroincidence() only — see the correction below.
3 codecov/patch 33.68% vs 84.80% target Defer Tracked in #560 per your call; the Shiny UI/reactive code is inherently hard to unit-test and the decay-curve math is covered.
4 lint-changed-files red (7 indentation_linter findings) Address See below.
5 Branch conflicted with main (mergeable_state: dirty) Address See below.

Correction to the PR description

The description claims the cli::cli_abort() improvement covers both autoplot.seroincidence() and autoplot.seroincidence.by(). Only the first is true — this PR's sole change to R/autoplot.seroincidence.by.R is a brace-style fix (now reverted, see below). The NEWS bullet is worded to match what the diff actually does.

That file's own cli::cli_abort() call, which is main's content and not this PR's, turns out to be broken: it passes two positional strings the way stop() would, but cli_abort() forwards its ... to rlang::abort(), whose second positional parameter is class — so the half of the message naming build_graph never renders and a sentence becomes the condition class. Filed as #606 rather than fixed here, since the fix belongs on main.

Merge with main

main had moved 164 commits ahead, including the pkgdown → altdoc migration (#504) that deleted pkgdown/_pkgdown.yml. Conflicts resolved as:

  • DESCRIPTION — took main's version line, bumped to 1.4.1.9016 so version-check still sees the branch ahead.
  • pkgdown/_pkgdown.yml — accepted the deletion, and moved this PR's six new reference entries into the replacement index, altdoc/reference.qmd, under the same "Visualize data" section they occupied. Taking the deletion alone would have quietly dropped the new functions off the documentation site.

Lint

#558 has since been resolved: it wasn't a lintr regression, it's that the package uses the 4-space double indent the tidyverse style guide dropped, and the decision was to migrate incrementally, with #392's own new files named as a follow-up. So:

  • Reindented the six new decay-curve signatures to the 2-space single indent, with ) { on its own line. man/ needs no regeneration — roxygen already emits that shape in \usage{} regardless of source formatting.
  • Reverted four out-of-scope drive-by edits (R/autoplot.seroincidence.by.R, R/plot_curve_params_one_ab.R, R/stratify_data.R, R/summary.seroincidence.R). They were comment removals and a brace fix, and one deleted a genuinely useful reference — the delta-method citation next to SE = se_log_lambda * incidence.rate. Reverting also takes those legacy files out of the changed-file set, so their untouched 4-space code stops being linted, which is exactly the incremental approach Migrate to tidyverse 2-space function-arg indentation incrementally (lintr 3.4.0) #558 settled on.

A local lintr::lint_package() over the PR's full changed-file set now reports zero lints.

Two more things found on the way


Generated by Claude Code

claude added 2 commits July 25, 2026 06:54
main advanced 164 commits since this branch last synced, including the
pkgdown -> altdoc documentation migration (#504) that deleted
`pkgdown/_pkgdown.yml`. Conflicts resolved as:

- `DESCRIPTION`: keep main's version line and bump to 1.4.1.9016, so
  `version-check` still sees the branch ahead of main.
- `pkgdown/_pkgdown.yml`: accept main's deletion, and move this PR's six
  new reference entries (`antibody_decay_curve()`, `pathogen_decay_curve()`,
  `plot_decay_curve()`, `curve_app()`, `t1f()`, `y1f()`) into the
  replacement index, `altdoc/reference.qmd`, under "Visualize data" --
  the section they occupied in the pkgdown config. Dropping them with the
  file would have left the new functions off the documentation site.

Also applies the two NEWS.md fixes from the last review round: delete the
bullet claiming a spurious `and` entry was removed from `Imports` (`and`
is a real dependency, called at `R/check_strata.R:45`, and was never
removed), and add the missing bullet for the `cli::cli_abort()` change in
`autoplot.seroincidence()`.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32
Two changes, both aimed at getting `lint-changed-files` green without
reformatting code this PR has no business touching.

Reindent the six new decay-curve function signatures from the package's
older 4-space double indent to the 2-space single indent lintr 3.4.0's
`indentation_linter` now requires, closing the "reindent new/edited
function defs as PRs touch them" follow-up #558 assigned to this PR.
Closing `) {` moves to its own line, matching what roxygen already emits
in the generated `\usage{}` blocks, so `man/` needs no regeneration.

Revert four out-of-scope drive-by edits to files this PR otherwise has no
reason to change: `R/autoplot.seroincidence.by.R`,
`R/plot_curve_params_one_ab.R`, `R/stratify_data.R`, and
`R/summary.seroincidence.R`. These were comment removals and a brace-style
fix, and one of them deleted a useful citation (the delta-method reference
next to `SE = se_log_lambda * incidence.rate`). Reverting them also takes
those four legacy files out of the changed-file set, so
`lint-changed-files` no longer lints their untouched 4-space code -- the
incremental-migration approach #558 settled on.

Also wraps two over-length lines in the new
`tests/testthat/test-validate_decay_params.R`. CI never flagged these
because `lint-changed-files` reads only the first 30 files of the PR's
file list (#608); a local `lint_package()` over the full changed-file set
now reports zero lints.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32
`lint-changed-lines` flags `app.R:5`'s `library(serocalculator)` under
`undesirable_function_linter`, which the repo's `.lintr.R` configures to
steer callers toward `::` rather than modifying the global search path.

The call was already redundant: the next line invokes
`serocalculator::curve_app()` namespace-qualified, so nothing depended on
the package being attached. Deployment is unaffected too --- rsconnect
discovers dependencies via `renv::dependencies()`, which detects `pkg::fn()`
usage as well as `library(pkg)`.

`lint-changed-files` never caught this because `lintr::lint_package()`
scans `R/`, `tests/`, `inst/`, `vignettes/`, `data-raw/`, and `demo/`, not
repository-root scripts. `lint-changed-lines` works from the diff, so it
sees `app.R` --- an independent reason to prefer it over the file-based
check, on top of the 30-file pagination cutoff in #608.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32

Copy link
Copy Markdown
Member Author

lint / lint-changed-lines came back red on one finding, now fixed in c254aba.

app.R:5's library(serocalculator) trips undesirable_function_linter, which this repo's .lintr.R configures to steer callers toward ::. The call was already dead weight — the very next line calls serocalculator::curve_app() namespace-qualified, so nothing relied on the package being attached. Deployment is unaffected: rsconnect resolves dependencies through renv::dependencies(), which detects pkg::fn() as readily as library(pkg).

Worth noting why this one only surfaced now, since it's a second independent gap in lint-changed-files on top of the pagination cutoff in #608: lintr::lint_package() scans R/, tests/, inst/, vignettes/, data-raw/, and demo/ — not repository-root scripts. So app.R was invisible to the file-based check no matter how the exclusion list came out. lint-changed-lines works from the diff and sees it. That's a good argument for the branch-protection switch #558 already has queued up.

(The two commits before this were also force-pushed once, to correct their author identity. Trees and parentage are byte-identical to what was reviewed above — no content changed.)


Generated by Claude Code

Codecov flags 187 uncovered lines in the diff. 178 of them are the Shiny
app (`curve_app_ui`, `curve_app_server`, `curve_app`), deferred to #560 per
maintainer direction. The remaining 9 are not Shiny code and are worth
covering here:

`R/autoplot.seroincidence.R` (8 lines) is the `cli::cli_abort()` branch this
PR added, which had no test at all --- so the NEWS bullet describing the new
message was unverified by anything. The new test asserts the rendered error
actually contains `build_graph`, rather than merely that it errors: a
first-clause-only assertion would still pass under the `cli_abort()`
misuse in #606, where the half of the message naming the fix is silently
dropped. A companion case covers the success path and `log_x = TRUE`.

`R/antibody_decay_function.R` (1 line) is the `rho < 1` guard. Its sibling
`alpha < 0` guard was already tested; this one was not.

Both files are lint-clean, but the container running this has no testthat
or package dependencies installed, so CI is their first execution.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32

Copy link
Copy Markdown
Member Author

Codecov round — 17c7496

codecov/patch reports 187 uncovered lines. Splitting them rather than writing the whole check off as the known Shiny gap:

File Missing Disposition
R/curve_app_ui.R 94 Defer#560
R/curve_app_server.R 80 Defer#560
R/curve_app.R 4 Defer#560
R/autoplot.seroincidence.R 8 Address
R/antibody_decay_function.R 1 Address

178 of the 187 are the Shiny app, which is exactly what #560 defers per your earlier call — unchanged, no action.

The other 9 aren't Shiny code and aren't in #560's scope:

  • R/autoplot.seroincidence.R (22.22%, -8.55%) — these 8 lines are the cli::cli_abort() branch this PR added. It had no test at all, which also means the NEWS bullet I added last round described behavior nothing verified. Added tests/testthat/test-autoplot.seroincidence.R. It asserts the rendered message actually contains build_graph, not merely that the call errors — deliberately, because a first-clause-only assertion would still pass under the cli_abort() misuse in autoplot.seroincidence.by()'s "graphs cannot be extracted" error drops half its message #606, where the half of the message naming the fix is silently dropped. A companion case covers the success path and log_x = TRUE.
  • R/antibody_decay_function.R (97.05%) — the one missing line is the rho < 1 guard. Its sibling alpha < 0 guard was already tested; this one wasn't.

Both files are lint-clean, but this session's container has no testthat or package dependencies installed, so CI is their first actual execution — worth a look at the R-CMD-check results rather than taking my word for it.

Note this push cancels the claude-review run that was in flight for c254aba. That run was reviewing a diff these tests have since changed, so its verdict would have been stale either way; the re-run against 17c7496 reviews the real thing.

Also green since the last round

lint / lint-changed-lines, lint-changed-files, docs-check, Spellcheck, version-check, test-coverage, check / Check Changelog Action, and R-CMD-check on macOS and ubuntu-release all passed on c254aba. docs-check passing is the one that confirms the 2-space signature reindent didn't desync man/.


Generated by Claude Code

The altdoc site keeps its reference topics in two independent places:
`altdoc/reference.qmd` (the "Package index" page) and the `Reference`
section of `altdoc/quarto_website.yml` (the sidebar navigation). Porting
this PR's six new topics off the deleted `pkgdown/_pkgdown.yml` updated only
the first, which would have listed them on the index page while leaving them
absent from the sidebar.

Adds all six to the sidebar's "Visualize data" section, matching their
placement on the index page and the section they occupied in the old pkgdown
config.

A mechanical cross-check of the two lists now shows 42 topics each, with an
empty symmetric difference and a backing `man/*.Rd` for every entry.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32
Comment thread R/pathogen_decay_curve.R
@claude

claude Bot commented Jul 25, 2026

Copy link
Copy Markdown
Contributor

Code review

Re-reviewed the current diff (head 17c7496f). The previous verdict was Ready for merge (comment), and I re-verified all three earlier findings are still fixed: NEWS.md's development-version section has no duplicate/empty headers, inst/examples/ab-decay-model.Rmd's sliderInput() calls all use value =, and app.R has no leftover commented-out pkgload::load_all().

Four parallel review passes (2× CLAUDE.md compliance, 2× bug/logic scan) turned up one new, validated finding — posted inline:

  • R/antigen_decay_curve.R, R/antibody_decay_function.R, R/t1.R, R/y1.R — none of these new files' names match the exported function they define (e.g. antigen_decay_curve.R defines pathogen_decay_curve()), violating the "File name should match the function name" rule in .github/copilot-instructions.md (marked CRITICAL, applies to new code). See inline comment for details.

A second candidate finding (missing test coverage for the new curve_app()/curve_app_ui()/curve_app_server() Shiny code) was considered but not raised — Shiny reactive code isn't meaningfully unit-testable without shinytest2 (not a current dependency), and the codebase doesn't otherwise enforce 100% test-file coverage, so this reads as a defensible trade-off rather than a clear rule violation.

No bugs, security issues, or logic errors were found in the introduced decay-curve math (antibody_decay_curve(), pathogen_decay_curve(), t1f(), y1f(), .validate_decay_params()) or the Shiny app wiring — two independent Opus passes traced the vectorization, branch conditions, and guard logic and found nothing input-independent that's wrong.

Verdict

Needs more work — one file-naming convention issue to address before merge; everything else checks out.

@github-actions

Copy link
Copy Markdown
Contributor

Claude finished reviewView run


gh pr comment 392 --repo UCD-SERG/serocalculator --body "$(cat <<'EOF'

Code review

Re-reviewed the current diff (head 17c7496f). The previous verdict was Ready for merge (comment), and I re-verified all three earlier findings are still fixed: NEWS.md's development-version section has no duplicate/empty headers, inst/examples/ab-decay-model.Rmd's sliderInput() calls all use value =, and app.R has no leftover commented-out pkgload::load_all().

Four parallel review passes (2× CLAUDE.md compliance, 2× bug/logic scan) turned up one new, validated finding — posted inline:

  • R/antigen_decay_curve.R, R/antibody_decay_function.R, R/t1.R, R/y1.R — none of these new files' names match the exported function they define (e.g. antigen_decay_curve.R defines pathogen_decay_curve()), violating the "File name should match the function name" rule in .github/copilot-instructions.md (marked CRITICAL, applies to new code). See inline comment for details.

A second candidate finding (missing test coverage for the new curve_app()/curve_app_ui()/curve_app_server() Shiny code) was considered but not raised — Shiny reactive code isn't meaningfully unit-testable without shinytest2 (not a current dependency), and the codebase doesn't otherwise enforce 100% test-file coverage, so this reads as a defensible trade-off rather than a clear rule violation.

No bugs, security issues, or logic errors were found in the introduced decay-curve math (antibody_decay_curve(), pathogen_decay_curve(), t1f(), y1f(), .validate_decay_params()) or the Shiny app wiring — two independent Opus passes traced the vectorization, branch conditions, and guard logic and found nothing input-independent that's wrong.

Verdict

Needs more work — one file-naming convention issue to address before merge; everything else checks out.
EOF
)"

@github-actions

Copy link
Copy Markdown
Contributor

💰 Cost: $5.5553 (review) — run

`.github/copilot-instructions.md` (the source of truth root `CLAUDE.md`
defers to) marks "File name should match the function name" as CRITICAL for
all new code. Four files this PR adds broke it:

  R/antibody_decay_function.R -> R/antibody_decay_curve.R
  R/antigen_decay_curve.R     -> R/pathogen_decay_curve.R
  R/t1.R                      -> R/t1f.R
  R/y1.R                      -> R/y1f.R

The `antigen_decay_curve.R` / `pathogen_decay_curve()` pair was the worst of
the four: the file and the function named different biological entities, so
grepping for either name found only half the story.

Test files are renamed to match, keeping testthat's `test-<source>.R`
pairing intact. Each affected `man/*.Rd` gets its `% Please edit
documentation in R/<file>.R` header updated to the new path, which is what
`devtools::document()` would have written; no other generated content
changes, since roxygen derives everything else from the source rather than
the filename. `DESCRIPTION` has no `Collate` field, and neither the renamed
sources nor their tests are referenced by path anywhere else in the repo, so
nothing else needed updating.

Verified mechanically rather than by eye: every `R/` file this PR touches
now defines a top-level function whose name matches its filename, with
`.validate_decay_params()` in `validate_decay_params.R` following the
documented internal-helper convention.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32

Copy link
Copy Markdown
Member Author

ARD summary — round pushed as d785029

# Finding Source Disposition
1 Four new files' names don't match the function they define claude-review (inline) Addressd785029
2 Shiny app lacks test coverage claude-review (considered, not raised) Defer#560, already tracked
3 Six new topics missing from the docs sidebar self-review Address4defddc

1. File naming — Addressed

Verified and correct; renames in d785029, details in the inline reply. Thread resolved.

2. Shiny coverage — Defer

The review raised and self-dismissed this one; agreed, and it's already tracked in #560. Worth noting the coverage picture improved this round: R/autoplot.seroincidence.R went 22.22% → 100% (+69.23%) and R/antibody_decay_function.R 97.05% → 100%, so all 178 remaining uncovered lines are now the three Shiny files and nothing else.

3. Sidebar — Addressed (found by self-review, not the bot)

The altdoc site keeps reference topics in two independent hand-maintained lists: altdoc/reference.qmd (the index page) and the Reference section of altdoc/quarto_website.yml (the sidebar). Porting this PR's six new entries off the deleted pkgdown/_pkgdown.yml updated only the first.

Confirmed against the actual deployed preview rather than by reading the config — reading pr-preview/pr-392/reference.html off the gh-pages branch and counting occurrences:

Topic Occurrences
autoplot.pop_data, graph_loglik, log_likelihood, est_seroincidence_by (established) 3 each
the six new decay-curve topics 2 each

Established topics appear three times — sidebar entry, index link, index text. The six new ones appeared twice: index only. Cross-checked on the link itself (man/log_likelihood.html twice, man/antibody_decay_curve.html once).

So this would have shipped six functions listed on the package index but unreachable from site navigation, with both lists rendering cleanly and no check catching it. Fixed in 4defddc; the two lists now agree at 42 topics each with an empty symmetric difference and a backing man/*.Rd for every entry. The next preview build should show 3 occurrences each — checkable the same way.

Filed #610 proposing this cross-check as CI, since it's three assertions over two files and passes on main today.

Also filed this session

#606 (cli_abort() misuse in autoplot.seroincidence.by() drops half its message — main's code, not this PR's), #607 (.gitignore shadows the tracked altdoc/ directory), #608 (lint-changed-files only reads the first 30 changed files), #609 (eight helpers carry both @noRd and @keywords internal).


Generated by Claude Code

@github-actions

Copy link
Copy Markdown
Contributor

Claude finished reviewView run


Code Review Summary — PR #392 (Decay curve 2)

This is a confirming review; no --comment flag was supplied, so I'm reporting findings here rather than posting to GitHub.

Prior verdict: The most recent claude-authored review (comment) was Needs more work, flagging one issue: four new files (R/antigen_decay_curve.R, R/antibody_decay_function.R, R/t1.R, R/y1.R) whose names didn't match the exported function they defined, violating the CRITICAL "file name should match function name" rule in .github/copilot-instructions.md.

Verification against the current diff (head d785029): I fetched the full PR diff directly (gh pr diff 392) and confirmed:

  • File naming — fixed. The four files are now correctly renamed: R/antibody_decay_curve.R defines antibody_decay_curve(), R/pathogen_decay_curve.R defines pathogen_decay_curve(), R/t1f.R defines t1f(), R/y1f.R defines y1f(). No Collate field exists in DESCRIPTION, so no update was needed there.
  • All earlier-round findings remain fixed: NEWS.md has no duplicate/empty headers and no false "and"-removal bullet; a correct NEWS bullet exists for the cli::cli_abort() change; inst/examples/ab-decay-model.Rmd's sliderInput() calls all use value =; app.R is a clean 5-line launcher with no leftover commented code and no unnecessary library(serocalculator) call.
  • New in this round — altdoc sidebar sync. altdoc/reference.qmd and altdoc/quarto_website.yml (Reference sidebar section) both now list all 6 new topics (antibody_decay_curve, pathogen_decay_curve, plot_decay_curve, curve_app, t1f, y1f), consistent with the author's self-reported fix for the doc-sidebar gap.
  • Reviewed the decay-curve math (antibody_decay_curve(), pathogen_decay_curve(), t1f(), y1f(), .validate_decay_params()), the Shiny reactive wiring (curve_app_server.R/curve_app_ui.R), DESCRIPTION/NAMESPACE sync, and the new test suite (test-antibody_decay_curve.R, test-pathogen_decay_curve.R, test-t1f.R, test-y1f.R, test-validate_decay_params.R, test-plot_decay_curve.R, test-autoplot.seroincidence.R) — all correct, no new bugs or hallucinated APIs found. shiny/plotly dependency additions are justified and correctly scoped (Imports vs. Suggests) given actual usage in R/curve_app*.R and inst/examples/ab-decay-model.Rmd respectively.
  • The .validate_decay_params() @noRd + @keywords internal combination (suppressing its docs) is a pre-existing, already-tracked issue (Eight internal helpers carry both @noRd and @keywords internal; @noRd wins and suppresses their docs #609) the author explicitly deferred as repo-wide — not a new blocking finding for this PR.

No new issues found.

Verdict

Ready for merge — the previously-flagged file-naming violation is confirmed fixed, all earlier-round findings remain resolved, and no new issues were introduced by this round's changes (file renames + doc-sidebar sync).

@github-actions

Copy link
Copy Markdown
Contributor

💰 Cost: $1.5106 (review) — run

Picks up #604/#605 (README docs-link fix and its NEWS wording follow-up).
main reached 1.4.1.9016, the same version this branch carried, so
`version-check` -- which requires the branch to exceed main -- would have
started failing despite the merge itself being conflict-free. Bumped to
1.4.1.9017 in the same commit.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JCwW1H9AFVc8J1eRcobG32

Copy link
Copy Markdown
Member Author

Round complete — clean review, plus one late catch

The review at d785029 returned Ready for merge with no new issues, and every check completed green except the two deferred codecov ones. Full sweep at that head:

✅ Passed (21) ⚠️ Red by prior decision
R-CMD-check ×5 (macOS, Windows, ubuntu release/devel/oldrel-1), test-coverage, docs-check, docs / docs, lint / lint-changed-lines, lint-changed-files, Spellcheck, version-check, Check Changelog, CodeFactor, review / claude-review, review / require-review, gather-context codecov/patch, codecov/project#560

One more fix, pushed as 1d670de

The final mergeability re-check caught something a green run wouldn't have: main advanced 3 commits (#604/#605) and landed on Version: 1.4.1.9016exactly what this branch carried. version-check requires the branch to exceed main, so it would have started failing, even though it passed minutes earlier and the merge itself is conflict-free. Nothing flags this; the check simply goes red once main moves.

Merged main in and bumped to 1.4.1.9017 in the same commit. Re-verified conflict-free against current main afterwards.

Sidebar fix — verified against the rendered artifact

Closing the loop on the earlier prediction. Counting occurrences in the deployed pr-preview/pr-392/reference.html, before the fix vs. after:

Topic Pre-fix Post-fix
all six new decay-curve topics 2 3
log_likelihood, graph_loglik, autoplot.pop_data (controls) 3 3

Three occurrences = sidebar entry + index link + index text, matching every established topic. File size changed (71,540 → 72,784 bytes), confirming a genuinely new build rather than a cached read. So the six functions are now reachable from site navigation, verified in the rendered output rather than only in the config.

Status

CI is re-running against 1d670de. Once it goes green this PR is ready to merge, with codecov/patch / codecov/project red solely on the #560 Shiny deferral — every non-Shiny line in the diff is at 100%.

Not merging; that's your call.


Generated by Claude Code

@claude

claude Bot commented Jul 25, 2026

Copy link
Copy Markdown
Contributor

Code review

Re-reviewed the current diff (head 1d670de). The prior verdict was Ready for merge (comment), confirming that the file-naming CLAUDE.md violation and all earlier-round findings (duplicate NEWS.md headers, sliderInput(val = ...) typo in inst/examples/ab-decay-model.Rmd, leftover commented-out pkgload::load_all() in app.R) were fixed.

The only change since that review is commit 1d670de, which merges main in and bumps DESCRIPTION to 1.4.1.9017 to keep version-check green — a mechanical reconciliation with no functional code changes. I re-diffed the full PR against main and re-verified:

  • All four previously-flagged files remain correctly named (antibody_decay_curve.R, pathogen_decay_curve.R, t1f.R, y1f.R) matching their exported functions.
  • NEWS.md's development-version section has no duplicate/empty headers.
  • inst/examples/ab-decay-model.Rmd's sliderInput() calls all correctly use value =.
  • app.R is a clean launcher with no leftover debug code.
  • The new R/_disable_autoload.R sentinel file is a legitimate, documented shiny::loadSupport() mechanism (not a hallucination) and is used correctly to prevent the package's R/ directory from being double-sourced as Shiny "supporting files" when app.R runs standalone.
  • shiny and plotly are declared appropriately in DESCRIPTION (shiny in Imports since curve_app() requires it at runtime; plotly in Suggests since it's only used in the example Rmd).

No new issues found.

Verdict

Ready for merge

@github-actions

Copy link
Copy Markdown
Contributor

Claude finished reviewView run


Posted the confirming review: #392 (comment)

Summary: The only change since the last full review (d785029, verdict: Ready for merge) is commit 1d670de, a mechanical merge-of-main + version bump with no functional code changes. I re-verified all previously-flagged issues remain fixed (file naming, NEWS.md duplicate headers, sliderInput typo, leftover debug code) and confirmed the new _disable_autoload.R file uses a real, documented shiny mechanism. No new issues found.

Verdict

Ready for merge

@github-actions

Copy link
Copy Markdown
Contributor

💰 Cost: $1.2070 (review) — run

@github-actions

github-actions Bot commented Jul 25, 2026

Copy link
Copy Markdown
Contributor
PR Preview Action v1.8.1
Preview removed because the pull request was closed.
2026-07-25 18:24 UTC

Copy link
Copy Markdown
Member Author

Ready for merge — 1d670de

ARDI complete. Every check has completed green except the two deferred codecov ones, and the external review verdict is clean at the current head.

✅ Passed (19)
R-CMD-check ×5 (macOS, Windows, ubuntu release / devel / oldrel-1) · test-coverage · docs-check · docs / docs · version-check · lint / lint-changed-lines · lint-changed-files · Spellcheck · check / Check Changelog Action · CodeFactor · review / claude-review · review / require-review · review / gather-context
⚠️ Red by prior decision
codecov/patch (36.20%), codecov/project (80.98%) — the Shiny gap tracked in #560, deferred on your call. All 178 uncovered lines are curve_app_ui.R / curve_app_server.R / curve_app.R; every non-Shiny line in the diff is at 100%.

Review: claude-review returned Ready for merge at this head — verdict posted and its check run completed, with require-review green. Copilot has not re-reviewed since January; the clean call rests on claude-review's verdict.

Mergeability, re-verified just now: main ahead by 0, zero conflicts, branch at 1.4.1.9017 vs main's 1.4.1.9016.

What this round fixed

  • Merged 164 commits of main drift, including the pkgdown → altdoc migration that deleted pkgdown/_pkgdown.yml; moved the six new reference entries into altdoc/reference.qmd.
  • Deleted the false NEWS bullet about and being removed from Imports; added the missing cli::cli_abort() bullet, scoped to what the diff actually changes.
  • Reindented six new function signatures to 2-space per Migrate to tidyverse 2-space function-arg indentation incrementally (lintr 3.4.0) #558's incremental migration, and reverted four out-of-scope drive-by edits (one of which had deleted the delta-method citation in summary.seroincidence()).
  • Removed the redundant library() call from app.R.
  • Covered the two non-Shiny uncovered branches: autoplot.seroincidence() 22.22% → 100%, antibody_decay_curve()'s rho < 1 guard → 100%.
  • Renamed four files to match their exported functions, per the review's finding.
  • Added the six new topics to the docs sidebar, which the reference-index port had missed — verified in the rendered preview (2 → 3 occurrences each, controls unchanged).
  • Merged main again at the end and bumped the version, catching a version-check parity failure that would otherwise have surfaced after this PR was reported ready.

Issues filed along the way

#606 (cli_abort() misuse drops half its message — main's code) · #607 (.gitignore shadows tracked altdoc/) · #608 (lint-changed-files reads only the first 30 changed files) · #609 (eight helpers' docs suppressed by @noRd) · #610 (CI cross-check for the two reference lists) · d-morrison/gha#312 (review workflow posted its own gh command instead of the review body)

Not merging — that's your call. Done here; PR is free.


Generated by Claude Code

@d-morrison
d-morrison merged commit 494dcf9 into main Jul 25, 2026
19 of 21 checks passed
@d-morrison
d-morrison deleted the decay-curve-2 branch July 25, 2026 18:24
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.

4 participants