Call Circadian Workbench¶
Choose the entrance that matches the job. Think of these as different doors into the same laboratory: every door reaches the same registered scientific methods and returns the same numbers.
| I want to... | Use |
|---|---|
| analyse without writing code | the desktop |
| ask one familiar question | circadian ask |
| work in a notebook or another Python package | circadian_workbench |
| connect another local application | /api/v1 |
| reach a specialised registered action | cw.call(...) |
Complete cohort and study management is intentionally reserved for a separately agreed workflow and is not described here.
Use the Python interface reference for every constructor and bound method. Use the complete action reference for every registered action, exact signature, argument, default, unit, and meaning.
The shared figure options describe themes, sizing and explicit per-figure colours.
No code: use the desktop¶
Open Circadian Workbench, load a recording, then choose the scientific question. The desktop shows only the reviewed non-cohort questions and keeps the original recording read-only.
circadian-workbench-desktop
One question: use the plain-English command¶
The command accepts a recording followed by a reviewed question or short name. It prints a readable answer unless --json is requested.
circadian --list-questions
circadian ask mouse01.awd "What is the period?"
circadian ask mouse01.awd period --json
circadian ask demo period
Questions are fixed reviewed aliases, not free-text artificial-intelligence interpretation. A misspelling returns close choices instead of guessing which analysis to run. Destructive actions are not available through this command.
A few Python lines: open a recording¶
The complete recording-to-figure path is:
import circadian_workbench as workbench
recording = workbench.open("mouse.awd")
result = recording.detrend(window_hours=24).compare_periods()
result.plot().save("periods.svg")
This saves .circadian-agent/periods.svg plus exact data, statistics, evidence
and a replay producer. It never changes mouse.awd or starts a server. The
processed samples flow directly into comparison; plotting uses the completed
result. See complete runnable examples for
numeric traces, channels and explicit setting overrides.
For a single estimate and a text answer:
import circadian_workbench as cw
recording = cw.open("mouse01.awd")
period = recording.period(method="lomb")
print(period.answer)
period.show()
Settings use scientific names and units. Unspecified settings retain the installed
defaults, not those of the last run. Precedence is named method argument, then
per-call settings, then settings explicitly bound to the recording, then the
installed defaults. None means omitted; zero and False are explicit values.
Supplying both settings and its compatibility spelling config is an error.
period = cw.open(
"mouse01.awd",
settings={"period_min_hours": 20, "period_max_hours": 28},
).period()
Numeric data: skip file construction¶
Elapsed hours and values can be passed directly. Circadian Workbench sorts the time grid, preserves missing values, and infers the sampling interval.
trace = cw.trace(hours, values, name="cell 17")
trace.period()
trace.compare_periods(["lomb", "chi_square"])
trace.detrend(method="running mean", window_hours=24)
For an array already extracted by Motion or Auto-Organotypic, the complete comparison-to-figure call is the same:
import circadian_workbench as workbench
recording = workbench.trace(
hours,
values,
settings={"period_min_hours": 20, "period_max_hours": 28},
)
result = recording.compare_periods()
result.plot(theme="classic").save("periods.svg")
Supply your measured hours and values; the numeric example
also provides a synthetic fixture. analysis.circadian.trace in Motion and
auto_organotypic.rhythm.trace are the actual Workbench function, not copied
implementations with separate defaults.
Use the input that describes the experiment:
cw.population(hours, {"cell 1": cell_1, "cell 2": cell_2}).synchrony()
cw.phases([5.8, 6.1, 6.3], period_hours=24).summary(label="regions")
cw.phases({"control": control_phases, "treated": treated_phases}).compare()
cw.channels(hours, {"PER2": per2, "BMAL1": bmal1}).compare()
population means several independent oscillators. channels means several measurements from the same subject.
Common recording analyses¶
Routine analyses have named calls and share the same settings argument:
recording.profile().series["mean"]
recording.daily_timing().tables["days"]
recording.bouts().tables["events"]
recording.spectrum(kind="power")
recording.wavelet(cycles=8)
recording.detrend("linear").instantaneous_phase()
The Python reference lists the full set, including onset fits, autocorrelation,
nonparametric measures, peak alignment, phase angle, re-entrainment, masking,
sleep, food anticipation, ultradian rhythms, splitting and channel comparison.
is_rhythmic() uses the selected periodogram; rhythmicity(method="ejtk")
uses the separate rank/template test on this one series. For correction across
several series, use the registered rhythmicity action with all recordings.
For file-writing methods, root selects the output folder. The existing
recording.actogram(output=...) spelling remains supported; supply either
root or output, not both. Calendar-dependent analyses still require a real
recording clock; a numeric trace is not silently assigned a meaningful date.
The result returned by every friendly call¶
Every call returns Result, so callers do not need a new output convention for each analysis.
| Field | Meaning |
|---|---|
answer |
concise human-readable answer |
data |
complete analysis result |
table |
table when the result naturally has rows |
files |
files created beneath the chosen output folder |
warnings |
scientific qualifications and refusals |
provenance |
software version, source fingerprint, complete effective_config for configurable actions, changed settings and processing history where applicable |
run_record |
detached record of complete call inputs, effective settings, sources, seeds and software/code identity |
script |
verified replay: checks the recorded environment and inputs, then the scientific result |
Use result.show() for a person and result.as_dict() for strict JavaScript Object Notation (JSON). The raw registered-action envelope remains available as result.raw.
result.available_plots lists the supported views. result.plot() constructs a
detached figure; figure.data gives its exact displayed table. Choose display
options on that figure, for example result.plot(theme="classic", show_grid=False).
figure.save("profile.pdf", root="my-figures") returns the actual path and all
companion paths. Unsupported plots explain their absence rather than guessing
which numeric array to draw. See figure options.
The same result also provides named views without changing those fields:
estimate = recording.period()
period = estimate.measurements["period_hours"]
print(period.value, period.unit, period.status)
comparison = recording.compare_periods()
comparison.tables["estimates"] # column units are in .attrs["units"]
processed = recording.detrend(window_hours=24)
processed.series["processed"] # .x, .y, .x_unit, .y_unit, .context
Measurement status distinguishes reported, not_reported (the method returned
no value), and refused. An absent field is not added; zero stays zero. Units
are None when not declared, not an invented unit. Error fields keep their
original names and definitions in .context; they are not automatically
converted into confidence intervals. Named series retain missing samples as
None, the original clock and processing history. Each access returns a fresh
view, so editing a table or its metadata cannot change the scientific result.
Views are mapped explicitly for the single-recording, phase, population,
prediction and statistical actions. Full analyze and study_report bundles
retain their mixed sub-results in .data; file, settings, catalogue and
maintenance actions expose raw data and files rather than fabricated scientific
measurements. Actogram layers and wavelet matrices remain in .data; matrices
are not reduced to an arbitrary line series.
A package maintainer: use only the public front door¶
Dependent packages should import the package root and adapt the Result once at their boundary.
import circadian_workbench as cw
def estimate_cell_period(hours, values):
return cw.trace(hours, values, name="cell").period("lomb").as_dict()
Use from circadian_workbench import statistics for the shared Hedges' g, variance guard, degenerate-data guard and p-value corrections. Modules such as circadian_workbench.analysis and circadian_workbench.period_methods are engine internals, not compatibility contracts.
A specialised action: use call¶
cw.call is the escape hatch for registered actions that do not need a dedicated convenience method.
result = cw.call(
"temperature_compensation",
temperature_points=[
[20, 24.2, "slice 1"],
[25, 24.0, "slice 1"],
[30, 23.9, "slice 1"],
],
)
Use cw.ask("period", source="mouse01.awd") when the caller starts from one of the reviewed questions. It never guesses an action.
Another local application: use version 1 web calls¶
The local service exposes the same registry contract:
GET /api/v1/actions?action=estimate_period
POST /api/v1/validate
POST /api/v1/call
The request body for validation and execution is:
{
"action": "estimate_period",
"params": {
"recording": {"path": "mouse01.awd"},
"method": "lomb"
},
"root": "my-results"
}
Every response includes api_version: "1" and the registered-action envelope. An output root is a relative folder beneath the service's configured output area; absolute paths and parent-folder escapes are refused. Existing unversioned desktop routes remain compatible.
Errors a caller can act on¶
Friendly Python calls raise typed readable errors:
WorkbenchInputError: change the supplied values, settings or file.UnknownQuestionError: choose one of the suggested reviewed questions.UnknownActionError: inspect the registered actions and correct the name.ActionConfirmationRequired: a destructive machine action needs explicit confirmation.WorkbenchBackendError: the engine failed rather than declining invalid input.
The versioned web interface returns the corresponding error_type in its envelope. Only backend_error means the application itself is broken.
Compatibility promise¶
Workbench owns circadian scientific methods, argument meanings and defaults. Motion and Auto-Organotypic consume the installed Workbench interface; their existing explicit settings remain their callers' choices, not alternative Workbench defaults. The registry covers the implemented scientific core; the browser's reviewed question list is only a subset. This does not claim every circadian method in the literature has been implemented or independently validated.
Workbench: scientific methods + shared argument definitions + figure builder
|-- Python, commands and browser adapters
|-- Motion: selected science inside measurement workflows
`-- Auto-Organotypic: selected science inside slice workflows
cw.describe("compare_periods") exposes the action's referenced scientific
settings with their defaults, units and constraints. cw.discover() lists
registered capabilities. Each consumer's argument_group() returns fresh
copies of the same definitions; changing help or a definition centrally does
not require another independently maintained registry.
The new uniform trace(...) paths use Workbench defaults. Existing Motion
measurement calls retain their explicit 2–48-hour search, 0.05 significance
threshold, 24-hour linear detrending, 24-observation and three-cycle checks.
Existing Auto-Organotypic wrappers retain their 15–40-hour search and 30-minute
bins. Use identical explicit settings when comparing those legacy paths.
With fixed input data, settings, seeds and software versions, unrelated earlier
calls do not select a different method or figure theme. Saved evidence records
a call; it does not decide future defaults. Keep the input and recorded numerical
and rendering environment for long-term replay. result.script verifies input
fingerprints and the recorded environment before analysis, then checks the
scientific result. A saved figure's standalone producer also verifies the
complete declared figure. Mismatches are reported, never repaired by silently
installing or switching software. Data in an already completed result are not
recomputed by plotting; figure options cannot change the scientific answer.
Editing the original settings dictionary or a returned view cannot rewrite
the stored run record.
These checks establish reproducibility in the recorded environment, not bit-identical raster output across arbitrary operating systems or font engines. Preserve the original data and the recorded package versions/code, numerical execution conditions and fonts. Optional external ReproFig proof checks have their own supported-manifest requirements; a valid saved artifact alone is not a claim that every external proof mode has passed.
The shared architecture continues public application programming interface
version 1, introduced in 0.7. The cw.open, cw.trace, cw.population,
cw.phases, cw.channels, cw.ask, cw.call, Result, input contracts,
public errors and circadian_workbench.statistics addresses remain supported.
Migrated consumers require circadian-workbench>=0.8,<0.9; pin the exact
installed version and retain the recorded environment for replay.
The action registry remains the machine source of truth. python scripts/update_circadian_references.py --check verifies that generated action documentation matches it.