Central, switchable logging across CLI, run(), and generated backends#63
Open
leon-k-martin wants to merge 2 commits into
Open
Central, switchable logging across CLI, run(), and generated backends#63leon-k-martin wants to merge 2 commits into
leon-k-martin wants to merge 2 commits into
Conversation
…ckends
Replace the process-wide `logging.disable(CRITICAL)` and scattered bare
`print()`s with a single `tvbo` logger hierarchy and one central switch,
shared by `tvbo run`, `SimulationExperiment.run()`, and the generated
tvboptim/jax backend scripts, so logging is consistent no matter the entry
point and can be turned off centrally.
- tvbo/log.py: NullHandler by default (silent as a library); public API
configure_logging / ensure_configured / set_log_level / get_log_level /
get_logger / silence / log_level, plus the TVBO_LOG_LEVEL env switch. An
explicitly set level sticks across repeated runs.
- __init__: drop the global logging.disable; re-export the public API.
- CLI: a global --log-level/--verbose/--quiet callback configures every verb;
_common.info/die route through the logger (machine-readable emit_json stays
on stdout).
- run(): ensure_configured() so scripts/notebooks surface progress like the CLI
without clobbering an app's own logging.
- Hot-path print() -> logger in classes/, codegen/, data/, adapters/julia.
- Generated code: logging.getLogger("tvbo.run"); drop the _quiet/_log/print
banner scheme; the standalone __main__ configures from TVBO_LOG_LEVEL.
Generated output is byte-identical apart from logging lines.
- log.py: drop the unused get_logger() helper; trim the OFF-level aliases to OFF/NONE (the two documented spellings). - experiment.py: hoist `from tvbo.log import ensure_configured` to module scope (was a per-call function-local import). - cli: emit user-facing output through a bare formatter (no "LEVEL [name]" diagnostic prefix), matching the plain lines the CLI printed before. - generated tvboptim: simplify the _log() helper to a single-arg form; guard the per-iteration algorithm progress with logger.isEnabledFor(INFO) so the float() device->host syncs are skipped when INFO is suppressed. - codegen/templater._log_source: skip building the numbered listing when INFO is off. - normalize stray blank lines after the added module loggers.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Central, switchable logging across all entry points
Running experiments emitted progress inconsistently: bare
print()scattered through the package and generated code, an ad-hocquiet/_logscheme plusverboseflags in the tvboptim templates, and — worst —tvbo/__init__.pydid a process-widelogging.disable(logging.CRITICAL)that muted every logger (tvbo's own included), which is exactly why everyone reached forprint.This replaces that with one
tvbologger hierarchy and one switch, sotvbo run(CLI),SimulationExperiment.run(), and the generated backend scripts all log the same way and can be turned off centrally.What changed
New
tvbo/log.py— the central logging module:tvbologger with aNullHandler(silent as a library by default; removed the globallogging.disable).tvbo:configure_logging(),ensure_configured(),set_log_level(),get_log_level(),silence(),log_level()(context manager),get_logger().TVBO_LOG_LEVELenv var (DEBUG/INFO/WARNING/ERROR/CRITICAL/OFF), ortvbo.set_log_level(...)/tvbo.silence()at runtime. An explicitly-set level sticks across repeated.run()calls.Harmonized entry points
--log-level/-L,--verbose/-v,--quiet/-qcallback configures the logger for every verb;cli/_common.info()/die()now route through it (machine-readableemit_jsonstays on stdout).SimulationExperiment.run()callsensure_configured()— visible progress in scripts/notebooks without clobbering an app's own logging setup.Hot-path
print→ logger inclasses/experiment.py,codegen/{code,templater}.py,data/types.py,adapters/julia.py, and the run-pathclasses/{dynamics,equation,observation,perturbation,atlas}.py.Generated backend scripts (tvboptim experiment + algorithm, jax sim): emit
logger = logging.getLogger("tvbo.run"), drop the_quiet/_log/printbanner scheme, and configure logging in the standalone__main__block fromTVBO_LOG_LEVEL. In-process runs inherit tvbo's central config; thequiet=/verbose=kwargs are preserved for back-compat.Behaviour change
import tvbono longer callslogging.disable(CRITICAL), so tvbo (and other libraries')WARNING+ records are no longer globally suppressed. tvbo itself stays silent until an entry point or the app configures a handler.Verified
silence()/set_log_level("WARNING")/TVBO_LOG_LEVEL=OFFall suppress it and the setting sticks across runs.infoshows by default, hidden under--quiet,diestill errors.tests/test_tvboptim_byte_identity.pynumeric faithfulness tests pass (trajectory/observation/optimization/inference).Note on a pre-existing failing test
test_experiment_result_roundtrips_via_sidecar(RWW-based) fails on this base withKeyError: 'empirical_fc'— reproduced on the committed base without these changes. It's unrelated to logging (the generated exploration code is byte-identical apart from log lines) and is already being reworked ondev(the in-progress Kuramoto_MINI_EXPERIMENTrewrite). Deselected from the numeric-guard run above.Out of scope (follow-up)
prints in dev-tools (ontology/,database/,plot/,analysis/,api/) and other backend templates (rateml/julia) — mechanical, deferred.Scope note
Branched from
dev; unrelated uncommitted WIP in the main checkout is not included here (both touchexperiment.py, so expect a small textual merge later).