The hardware and bandwidth for this mirror is donated by METANET, the Webhosting and Full Service-Cloud Provider.
If you wish to report a bug, or if you are interested in having us mirror your free-software or open-source project, please feel free to contact us at mirror[@]metanet.ch.

tsahr 0.2.8.17

HKSJ early-look caveat is now a warning(), matching the target_HR-near-1 caveat

tsahr 0.2.8.16

HKSJ early-look caveat: spaced out and highlighted

tsahr 0.2.8.15

Shortened a summary-table row label

tsahr 0.2.8.14

Test fix only (no code changes)

tsahr 0.2.8.13

Fixes to the 0.2.8.12 HKSJ-caveat placement and plotted Z-curve

tsahr 0.2.8.12

HKSJ early-look caveat, NA’d first-look Z, and a readable summary table

tsahr 0.2.8.11

New argument re_inference: standard, HKSJ and ad hoc HKSJ inference

tsahr 0.2.8.10

Release hygiene: NAMESPACE, roxygen tags, and a stricter zero-event test

tsahr 0.2.8.9

Design route: DARIS position at the historical rate in the printed output

tsahr 0.2.8.8

Analysis route: clearer naming of the historical-rate projection

tsahr 0.2.8.7

Analysis route now mirrors the design route for projections

tsahr 0.2.8.6

Design-route projection output, plot and options

tsahr 0.2.8.5

Changed: additional events are projected from information per event, not from whole studies

tsahr 0.2.8.4

New: retrospective “estimated additional studies/events” projection

tsahr 0.2.8.3

plot(): analysis-route endpoint marker missing when the endpoint is beyond DARIS

tsahr 0.2.8.2

Validation against RTSA reference engines

The alpha- and beta-boundary engines were independently validated against the corresponding RTSA implementations.

For the reference validation design:

In the reference test, cumulative and incremental beta spending agreed with RTSA to a tolerance of 1e-12, and the finite beta boundaries agreed numerically at all monitored looks (n=40).

These tests establish numerical equivalence of the tsahr alpha- and beta-engine calculations with the corresponding RTSA reference implementation for the validated configuration. They should not be interpreted as a formal proof of equivalence for every possible parameter combination.

tsahr 0.2.8.1

CRAN --as-cran check fixes

tsahr 0.2.8

Pooled-effect line in the TSA plot subtitle, configurable endpoint label, new example datasets

tsahr 0.2.7.22

Fixes the spend == beta knife-edge (low-information designs), relicenses as GPL (>= 2) with RTSA credited, and small fixes

tsahr 0.2.7.21

Measured accuracy of the 0.2.7.19 legacy fix; corrections to its documentation; regression test

Documentation and test release for the LEGACY fallback engine. The default compiled paths are untouched, and no shipped code path changes.

tsahr 0.2.7.20

Finishes the 0.2.7.19 test fixes that R CMD check caught as incomplete

0.2.7.19’s production fix (.rtsa_beta_boundary() recomputing the true, schedule-dependent final efficacy boundary via .obf_alpha_boundary() instead of assuming qnorm(1-alpha/2)) was correct, but two tests that still encoded the old assumption were not actually updated in the uploaded package, and a real R CMD check run caught both:

Two more tests were fixed for correctness even though R CMD check did not flag them as failing, because they were passing for the wrong reason: .rtsa_beta_boundary()’s own defensive pmin(boundary, c_vec_alpha) safeguard clips its (now correct, and therefore LARGER) recomputed final boundary back down to whatever c_vec_alpha’s own last entry says, so a test that still supplied the stale, smaller qnorm(1-alpha/2) as c_vec_alpha’s last entry got that same stale value back out of ans$boundary – appearing to confirm the old convention while actually only exercising the safety clip, not the recomputation the test’s own comment claimed to check:

Both now derive their expected final value from .obf_alpha_boundary() directly, matching the pattern the two already-fixed 0.2.7.19 tests (“RTSA retrospective inner-wedge engine has definitive alpha boundary” and “RTSA over-powered analysis uses the true (recursion-based) definitive boundary”) already established. One further qnorm(1-alpha/2) occurrence, in “0.2.7.5: a single-look schedule (DARIS already reached at the first study) does not error”, was checked and left as-is: with a single look, RTSA’s discretised recursion collapses to the ordinary fixed-sample critical value, so qnorm(1-alpha/2) genuinely is the correct value there (verified directly against the compiled engine), not an unfixed instance of the bug. .rtsa_beta_boundary_analysis()’s own, separately-disclosed use of the same constant (its harder design_R-endpoint case) is unaffected, as previously noted.

tsahr 0.2.7.19

Legacy engine bug fix: .rtsa_beta_boundary()’s final efficacy boundary was approximated, not computed

A live RTSA cross-check caught a real bug in the LEGACY, R-only fallback engine (.rtsa_beta_boundary() in R/obf_boundaries.R, used only when legacy_fallback = TRUE and the compiled engine fails – the default, compiled boundary_route = "design"/"analysis" paths are NOT affected).

tsahr 0.2.7.18

Wording and provenance corrections (no numerical change)

Documentation/diagnostic-text release following the 0.2.7.17 assessment. No boundary value, root, test reference or code path changes.

tsahr 0.2.7.17

Frozen live-RTSA reference: the compiled engine is compared with RTSA 0.2.2’s own output

The open item from 0.2.7.12 onward is closed for the case supplied. Numbers printed by RTSA 0.2.2 itself (RTSA::boundaries(), timing 0.25/0.50/0.75/1.00, alpha 0.05, beta 0.20, side 2, non-binding, esOF) are frozen in inst/extdata/rtsa_0.2.2_reference.R (provenance and call shapes documented in the file) and tested in tests/testthat/test-rtsa-live-reference.R, which does not need RTSA to be installed.

tsahr 0.2.7.16

Exact reachability test for beta searches; finite-input checks; sentinel and threshold documentation; the random-schedule check is now shipped

Hardening release. The alpha/beta mathematics and every pinned reference value are unchanged (the compiled core still agrees with the Python port to ~1e-14 and all schedules in tools/cpp_vs_py.py give the same roots).

tsahr 0.2.7.15

Fixes a regression in 0.2.7.13/14 (design-route calibration failing on many schedules), adds regression tests and a look-spacing diagnostic, and separates current from historical documentation

tsahr 0.2.7.14

Definitive-look decision fields, DARIS vs analysis-route endpoint, fallback bookkeeping, and a separate reversed-grid diagnostic

Implements four items from the 0.2.7.13 audit. The alpha/beta mathematics is untouched: the compiled engine still agrees with the Python port (tools/cpp_vs_py.py) to ~1e-14 and reproduces the same reference vectors.

tsahr 0.2.7.13

Acted on the 0.2.7.12 audit: strict search convergence, a grid-collapse diagnostic, clearer final-look wording, an opt-in strict-fail mode, and an opt-in RTSA analysis-route

This release implements the five actioned points of the 0.2.7.12 audit, plus an opt-in boundary_route argument the audit recommended over changing the default. Two audit points were declined, with reasons (see below).

Declined audit points (with reasons)

tsahr 0.2.7.12

Final futility bound now equals the final efficacy bound (as in RTSA); louder legacy fallback; cleanup

tsahr 0.2.7.11

Compiled RTSA-derived boundary engine; the final efficacy wall gap closed

The package now needs a C++ compiler (NeedsCompilation: yes, Rcpp).

What was wrong

Numerical comparison against a Python port of RTSA 0.2.2’s R sources (which reproduces RTSA’s published futility-vignette output: SMA timing 0.541/0.812/1.083, futility 0.332/1.292/2.014) traced the reported “beta bounds far from RTSA” symptom to orchestration, not to the C++ kernels (init_int/recur_int/prob were already term-for-term equal; first, other, fcab, qpos, trap are never called from any RTSA R file and are not needed):

  1. Final efficacy wall. RTSA root-finds the information-scale factor (root) so the futility bound meets the efficacy bound at t = 1, where that efficacy bound is the value of RTSA’s alpha recursion at t = 1 (2.127 for the 9-look schedule 0.461 … 0.961, 1). tsahr <= 0.2.7.10 used qnorm(1 - alpha/2) = 1.96 instead: root 1.1517 instead of 1.2107, first-look bound 0.479 instead of 0.531, and so on.
  2. Alpha engine. tsahr’s FFT alpha engine is an approximation of RTSA’s Simpson recursion (its own notes quote errors up to ~0.006), which also enters the futility recursion as the fixed upper wall.
  3. Route mix-up in 0.2.7.7-0.2.7.10. The RTSA type = "analysis" route was run against alpha bounds computed for the design timeline; RTSA recomputes them on t / design_R for that route. More importantly, the RTSA futility numbers used as the reference for these fractions are the type = "design" route’s (reproduced to 4 decimals), not the analysis route’s (which gives ~0.13 … 1.46 for the same fractions).

What changed

tsahr 0.2.7.10

Reverts the 0.2.7.9 regression: design_R calibration was switched to the wrong RTSA branch

0.2.7.9 changed .rtsa_beta_boundary_analysis()’s design_R/delta/ rm_bs calibration from a side = 2, futility = "non-binding" basis to a side = 1, futility = "none", right_power()-based one, on the strength of an external “live RTSA 0.2.2 reconstruction” that reported different numbers (delta = 2.486475, design_R = 1.057434, rm_bs = 0) than 0.2.7.7/0.2.7.8 produced (delta = 2.801585, design_R = 1.151571, rm_bs = 5).

That reconstruction queried the wrong branch of RTSA’s source. Re-reading RTSA’s own top-level RTSA() wrapper (R/RTSA.R), not just boundaries() in isolation, shows the internal call that manufactures design_R when no design object is supplied uses side = side, futility = futility – RTSA()’s own top-level arguments (side = 2, futility = "non-binding" for this package’s design), not hardcoded side = 1/futility = "none". The correct calibration is therefore exactly .rtsa_beta_boundary()’s existing two-pass warp_root search (side = 2, futility = "non-binding", type = "design") – what 0.2.7.7 already used.

tsahr 0.2.7.9

Post-R CMD check patch: design_R root search now filters out-of-range info fractions before searching, matching RTSA exactly

A live R CMD check/devtools::test() run against this fix (on real data, including the package’s own bundled example dataset, which reaches an info_fraction of 1.50 at its last study) surfaced two further problems in the brand-new .rtsa_design_R(), both now fixed:

Beta/futility engine now matches RTSA’s real type = "analysis" design_R and drift calibration

tsahr 0.2.7.8

Test-only fix: R CMD check on 0.2.7.7 found a bug in a test’s assumption, not in the package

tsahr 0.2.7.7

Beta/futility engine now reproduces RTSA’s type = "analysis" (retrospective) branch, not type = "design"

tsahr 0.2.7.6

Test-only fix: R CMD check on 0.2.7.5 found a bug in a test’s assumption, not in the package

tsahr 0.2.7.5

Root search from 0.2.7.4 failed almost universally – found and fixed by actually running the algorithm

tsahr 0.2.7.4

Beta/futility engine: RTSA’s information-scale root search was missing (numbers far from RTSA, final look didn’t meet efficacy boundary, negative early values not hidden)

tsahr 0.2.7.3

Test fix only: R CMD check failure was in a 0.2.7.2 regression test itself, not in the package code

Re-running R CMD check after 0.2.7.2 reported 4 failures, all in the one new test added in 0.2.7.2 ("0.2.7.2: a 3-node (m = 3) Simpson grid produces correct weights, not an error") – not in .rtsa2_z_n_w(), .rtsa2_seq_by2(), or any other package code, and not a crash: expect_length()/expect_equal() mismatches. The underlying 0.2.7.2 fix itself was already correct and is unchanged in this release.

Cause: that test picked lo = 1.5 as a stand-in for a near-collapsed [za[i], zb[i]] window. For the specific r = 18, delta = 0, sd_incr = 1 inputs used in the test, 1.5 happens to land EXACTLY on one of .rtsa2_z_n_w()’s own log-spaced grid nodes (node j = 72 evaluates to precisely -3 + (72 - 18)/12 = 1.5), so one extra original node coincided with lo and survived trimming, correctly producing a 5-node grid (m = 5) instead of the 2-node/3-node (m = 3) case the test’s hard-coded expected values assumed. The code was doing the right thing with the input it was given; the test’s prediction of what that input would produce was wrong.

Fix: rewrote the test (tests/testthat/test-boundaries-rtsa.R) to (a) use lo = 1.234567, deliberately off the r = 18 grid’s node spacing, and, more importantly, (b) stop hard-coding an exact node count or exact zj/wj values altogether, in favor of checking the invariants that must hold for ANY valid Simpson grid built on [lo, hi] regardless of how many interior nodes happen to survive trimming: no error, an odd node count >= 3, endpoints exactly at lo/hi, a non-decreasing sequence, and total Simpson weight equal to the window width (the property Simpson’s rule actually guarantees, and what the downstream recursion actually relies on). This is more robust against similar grid-alignment coincidences with any future choice of r/lo, not just a fix for this one value.

No change to R/obf_boundaries.R in this release.

tsahr 0.2.7.2

0.2.7.1 fixed the length(xi) <= 1 grid-collapse crash, but re-running R CMD check surfaced a second, closely related crash in the exact same function, .rtsa2_z_n_w(), now at seq(3, m - 2, 2): wrong sign in 'by' argument – hit by the same target_HR = NA example-data scenario as before (and by two of the new 0.2.7.1 regression tests themselves, which is how it was caught).

Root cause: the 0.2.7.1 clamp keeps za[i] only 1e-6 below zb[i] when the two would otherwise converge – deliberately tiny, so as not to perturb any well-separated boundary. But a 1e-6-wide interval is far narrower than the spacing between .rtsa2_z_n_w()’s log-spaced grid nodes, so trimming to [za[i], zb[i]] in that situation legitimately leaves exactly 2 points (the two endpoints, no interior node survives) – which is precisely what the 0.2.7.1 safety net widens degenerate cases to as well. Both routes land on the same m = length(xi) * 2 - 1 = 3 grid. That case turns out to have been separately broken already, for any m = 3 grid regardless of cause: the Simpson-weight loop’s k %in% seq(3, m - 2, 2) membership check evaluates seq(3, m - 2, 2) eagerly, and for m = 3 that’s seq(3, 1, 2) – an empty index range, but, as with 0.2.7.1’s seq(1, length(xi) - 1, 1), R’s seq() with an explicit by throws rather than returning integer(0) when to < from. So m = 3 (i.e. a 2-node grid) was never actually safe to reach, even after 0.2.7.1 – it was just newly reachable by 0.2.7.1’s own fix, where previously (pre-0.2.7.1) the crash at length(xi) <= 1 happened first and masked it.

Fix: new internal .rtsa2_seq_by2(from, to) helper – seq(from, to, 2), but returns integer(0) instead of erroring when to < from – used in place of the two raw seq(3, m - 2, 2) / seq(2, m - 1, 2) calls in .rtsa2_z_n_w()’s Simpson-weight loop. For any m where those ranges are non-empty (m >= 5), this is byte-for-byte the same seq() call as before – no change to any boundary value outside the previously- crashing case. Hand-traced the m = 3 case through the full weight loop to confirm it now produces the correct composite-Simpson weights (1/6, 4/6, 1/6 of the interval width, summing to the full width) rather than just failing to crash.

Also fixed the two 0.2.7.1 regression tests that this same bug broke (test-boundaries-rtsa.R): both exercised exactly the m = 3 path (the real tsa_hr(path, verbose = FALSE) call, and the direct .rtsa2_z_n_w() unit test with equal/reversed za/zb) and so were themselves failing under R CMD check, for the same underlying reason they were written to catch the previous bug – no test changes were needed once the underlying .rtsa2_seq_by2() fix was in place; they pass as originally written.

tsahr 0.2.7.1

Bug fix: R CMD check failure – grid collapse in the new RTSA-ported beta/futility engine

R CMD check on 0.2.7 failed 3 tests with Error in seq.default(1, length(xi) - 1, 1): wrong sign in 'by' argument, raised from .rtsa2_z_n_w() via .rtsa2_beta_boundary_core() / .rtsa_beta_boundary(), triggered by the package’s own bundled example data under target_HR = NA (the circular-target scenario exercised by tsa_hr(path, verbose = FALSE) with no target_HR).

Root cause: .rtsa2_z_n_w() builds a Simpson’s-rule integration grid on [za[i], zb[i]] (the futility and efficacy boundaries at look i) by trimming a fixed log-spaced node vector down to that interval. The non-binding futility boundary za[i], returned unconstrained by .rtsa2_searchfunc()’s root search, is expected to approach the fixed efficacy wall zb[i] closely near the final look by design (the two are constructed to meet at t = 1) – but nothing kept it from landing at or past zb[i], which collapses the trimmed grid to a single point (or fewer). The two-argument form seq(1, length(xi) - 1, 1) then throws “wrong sign in ‘by’ argument” once length(xi) <= 1, instead of quietly returning an empty sequence – this is a real edge case surfaced by this specific port (RTSA’s own equivalent R source has the identical unguarded pattern), not a mistranslation.

Fix, two parts:

No change to any boundary value for the normal (well-separated za/zb) case tested elsewhere in the suite – the clamp is a no-op unless za[i] would otherwise land within 1e-6 of zb[i], and the safety net is only reached if the clamp somehow didn’t fire first.

tsahr 0.2.7

Beta/futility boundary engine reconstructed to match RTSA (correctness/provenance)

tsahr 0.2.6.9

Fixes a broken test introduced in 0.2.6.8 (R CMD check failure)

tsahr 0.2.6.8

Fixes a semantic bug in circularity_warning, plus three documentation/validation refinements

Prompted by an external (ChatGPT) audit of 0.2.6.7, which rated the release otherwise ready and identified circularity_warning as the one item to fix before finalising. Each item was checked against the code before acting on it.

Not changed, deliberately: the beta engine remains frozen and RTSA-derived/adapted, as in 0.2.6.7. The audit’s suggestion to escalate order_by NA handling from warning to error was not adopted – the current behaviour is transparent and reproducible, and the audit itself scoped that as a possible future major release, not a fix for this one.

tsahr 0.2.6.7

Reverses an incorrect 0.2.6.6 decision: method = "CO" is a real metafor alias and is now supported

Prompted by an external (ChatGPT) review of 0.2.6.6, which flagged the "CO" removal as a release blocker. The flag was correct; this release reverses that removal and picks up several smaller items from the same review. Each was checked against primary sources or the actual code before acting on it.

Input-validation gaps closed

Test coverage

Wording corrections (no behaviour change)

tsahr 0.2.6.6

Bug fix: 3 of 13 advertised method values never worked, plus a documentation correction and several audit-driven improvements

Prompted by a second external (ChatGPT) audit of 0.2.6.5, verified against the actual code and against current metafor documentation before acting on any of it (see below for what was independently corroborated and how).

Bug fix (correctness): method = "CO", "GENQ", "GENQM" never worked

Documentation fix: final futility boundary wording

Other fixes and improvements from the audit

tsahr 0.2.6.5

Input-validation fix, three real documentation bugs, and two judgment calls left as-is (documented, not silently resolved)

Prompted by an external (ChatGPT) review; each item below was checked against the actual code before acting on it, not applied at face value – see the per-item notes.

tsahr 0.2.6.4

Cosmetic: superscript “2” in “Diversity D2” on the TSA plot

tsahr 0.2.6.3

Cleanup: removed dead .beta_spend_OF() and fixed the stale doc pointing at it

tsahr 0.2.6.2

Doc fix: R/obf_boundaries.R’s VALIDATION section contradicted itself — and one of the two contradicting claims turned out to be based on a units mix-up, not a real gap

(Supersedes an interim 0.2.6.1 that introduced this fix but also introduced a second, separate documentation problem – see below.)

tsahr 0.2.6

Bug fix: alpha-spending formula did not match this package’s own reference methodology (correctness — please upgrade)

tsahr 0.2.5.1

Minor

tsahr 0.2.5

New feature

tsahr 0.2.4.8

Bug fix (from a real R CMD check --run-donttest run, Windows)

tsahr 0.2.4.7

Bug fixes (from a real R CMD check run)

tsahr 0.2.4.6

New feature

tsahr 0.2.4.5

Test-suite fixes, following a self-reported regression review of 0.2.4.4

This release does not change any file under R/ – tsa_hr.R, methods.R, and obf_boundaries.R are byte-identical to 0.2.4.4 (this was verified directly, not assumed). Both the alpha-boundary recursive engine and the RTSA-matched beta-boundary engine are unchanged, per explicit instruction that both are deliberate design choices, not bugs to be second-guessed here.

A review of 0.2.4.4 claimed three things: (1) the alpha-spending formula had “regressed” to a one-sided-parameterized bug, with a specific claim that the correct first-look boundary was 4.88 rather than 4.38; (2) the package fails R CMD check with real errors, not just warnings, due to a test file that used readLines(file.path("R", "tsa_hr.R")) (a relative path that does not exist when tests run against an installed package) and a second test asserting stale (pre-RTSA-match) behavior at the final look; (3) none of this had ever actually been run.

Each claim was checked independently before acting on it, via independent recomputation in Python rather than by running the package itself:

tsahr 0.2.4.2

tsahr 0.2.4.1

tsahr 0.2.4 corrected RTSA futility output

tsahr 0.2.4

Beta/futility boundary engine

tsahr 0.2.3

Built from the 0.2.2 release (not from an interim 0.2.3 that had unrelated problems and was withdrawn), applying fixes from a further external statistical review of the 0.2.2 source.

High priority

Important

Moderate

Minor

Explicitly not addressed in this release

Per the same reviewer’s own priority ranking, and consistent with prior NEWS entries: the two-sided beta/futility betaAdjustment geometry and independent numerical comparison against another group sequential package (e.g. rpact) both remain open. The next step recommended in the 0.2.2 review – and still the recommendation here – is external numerical validation against an established group-sequential implementation.

tsahr 0.2.2

Methodological fixes, prompted by external statistical review

Not addressed in this release

Two items from the external review are explicitly not resolved here, and are flagged for a future release rather than attempted without adequate tooling:

tsahr 0.2.1

New feature

Bug fix

tsahr 0.2.0

These binaries (installable software) and packages are in development.
They may not be fully stable and should be used with caution. We make no claims about them.