{"id":7060,"library":"cabinetry","title":"cabinetry: Design and Steer Profile Likelihood Fits","description":"cabinetry is a Python library designed for building and steering profile likelihood fits, particularly used in high-energy physics for statistical analysis. It currently stands at version 0.6.0 and maintains an active development cycle with regular patch and minor releases, often coinciding with updates to its core dependency, `pyhf`.","status":"active","version":"0.6.0","language":"en","source_language":"en","source_url":"https://github.com/scikit-hep/cabinetry","tags":["HEP","physics","statistics","likelihood","fitting","data-analysis"],"install":[{"cmd":"pip install cabinetry","lang":"bash","label":"Install latest stable version"}],"dependencies":[{"reason":"Core library for statistical models and inference. cabinetry builds on pyhf's functionality.","package":"pyhf","optional":false},{"reason":"For visualizations and plotting of fit results and data/MC comparisons.","package":"matplotlib","optional":false},{"reason":"Requires Python 3.8 or higher, as of v0.6.0.","package":"python","optional":false}],"imports":[{"symbol":"cabinetry","correct":"import cabinetry"},{"symbol":"templates","correct":"from cabinetry import templates"},{"symbol":"fit","correct":"from cabinetry import fit"},{"symbol":"model_utils","correct":"from cabinetry import model_utils"},{"symbol":"workspace","correct":"from cabinetry import workspace"},{"symbol":"visualize","correct":"from cabinetry import visualize"}],"quickstart":{"code":"import cabinetry\nimport numpy as np\nimport pyhf\nimport os\n\n# 1. Define configuration (simplified for quickstart)\n# In a real scenario, this would likely be loaded from a YAML/JSON file\nconfig = {\n    \"General\": {\n        \"Measurement\": \"my_measurement\",\n        \"POI\": \"Signal_norm\",\n        \"Luminosity\": 1.0\n    },\n    \"Regions\": [\n        {\n            \"Name\": \"SR\",\n            \"HistogramFolders\": [\"data/\", \"signal/\", \"background/\"],\n            \"Variable\": \"m_yy\",\n            \"Binning\": [40, 50, 60, 70, 80, 90, 100]\n        }\n    ],\n    \"Samples\": [\n        {\"Name\": \"Signal\", \"Observable\": \"m_yy\", \"Normalization\": \"Signal_norm\"},\n        {\"Name\": \"Background\", \"Observable\": \"m_yy\"}\n    ],\n    \"Systematics\": [\n        {\n            \"Name\": \"lumi\",\n            \"Type\": \"lumi\",\n            \"Expression\": \"1.02\"\n        }\n    ]\n}\n\n# 2. Create dummy data/histograms in memory\nbins = config[\"Regions\"][0][\"Binning\"]\n\ndata_hists = {\n    \"SR\": np.array([5, 8, 12, 10, 7, 4])\n}\n\nsample_hists = [\n    {\n        \"name\": \"Signal\",\n        \"region\": \"SR\",\n        \"nominal\": np.array([2, 3, 4, 3, 2, 1]),\n        \"staterr\": np.sqrt(np.array([2, 3, 4, 3, 2, 1])) # Placeholder for stat error\n    },\n    {\n        \"name\": \"Background\",\n        \"region\": \"SR\",\n        \"nominal\": np.array([3, 5, 8, 7, 5, 3]),\n        \"staterr\": np.sqrt(np.array([3, 5, 8, 7, 5, 3]))\n    }\n]\n\n# Add systematic variation for \"lumi\"\nfor h in sample_hists:\n    h[\"lumi_up\"] = h[\"nominal\"] * 1.02\n    h[\"lumi_down\"] = h[\"nominal\"] * 0.98\n    h[\"bins\"] = bins # Add binning for plotting\n\n\n# 3. Build workspace\nws = cabinetry.workspace.build(config, sample_hists, data_hists)\nmodel, data = cabinetry.model_utils.model_and_data(ws)\n\n# 4. Perform fit\nfit_results = cabinetry.fit.fit(model, data)\n\n# 5. Visualize results (optional)\nplot_dir = \"cabinetry_quickstart_plots\"\nos.makedirs(plot_dir, exist_ok=True)\n\ncabinetry.visualize.data_mc(\n    model, data, fit_results=fit_results, config=config, save_path=os.path.join(plot_dir, \"data_mc_plot.pdf\")\n)\ncabinetry.visualize.ranking(\n    fit_results, save_path=os.path.join(plot_dir, \"ranking_plot.pdf\")\n)\n\nprint(\"cabinetry quickstart complete. Plots saved to:\", os.path.abspath(plot_dir))\n","lang":"python","description":"This quickstart demonstrates the core workflow of cabinetry: defining a statistical model via a configuration, generating dummy data and sample histograms, building a `pyhf` workspace, performing a profile likelihood fit, and visualizing the results. The example generates in-memory histograms to ensure runnability without external files."},"warnings":[{"fix":"Upgrade your Python environment to 3.8 or a later compatible version.","message":"As of cabinetry v0.6.0, support for Python 3.7 has been dropped. Previous versions may still run on Python 3.7, but v0.6.0+ explicitly requires Python 3.8 or newer.","severity":"breaking","affected_versions":">=0.6.0"},{"fix":"Ensure your `pyhf` installation is version 0.7.x or later (`pip install 'pyhf>=0.7.0'`). Review `pyhf`'s changelog for any direct API changes if you interact with `pyhf` objects outside of cabinetry's high-level API.","message":"cabinetry v0.5.0 adopted the `pyhf` 0.7 API. Code written for older `pyhf` versions or cabinetry versions prior to 0.5.0 may experience compatibility issues if the `pyhf` model definitions or API calls are used directly.","severity":"breaking","affected_versions":">=0.5.0"},{"fix":"Update all function calls to use keyword arguments. For instance, `cabinetry.fit.fit(model, data)` would become `cabinetry.fit.fit(model=model, data=data)`.","message":"From cabinetry v0.4.0 onwards, all API arguments are keyword-only. This means you must explicitly use the keyword when calling functions, e.g., `func(arg=value)` instead of `func(value)`.","severity":"breaking","affected_versions":">=0.4.0"},{"fix":"Call `pyhf.set_backend('your_backend_name')` at the beginning of your script if you require a specific `pyhf` backend.","message":"Since cabinetry v0.2.2, cabinetry no longer overrides the `pyhf` backend. If you need a specific `pyhf` backend (e.g., 'jax', 'torch'), you must set it explicitly using `pyhf.set_backend()` before any `pyhf` operations are performed.","severity":"gotcha","affected_versions":">=0.2.2"},{"fix":"Ensure your `matplotlib` installation is version 3.5.0 or newer (`pip install 'matplotlib>=3.5.0'`).","message":"cabinetry v0.5.1 introduced a minimum required `matplotlib` version of 3.5.0 to address plotting issues and enable new features.","severity":"gotcha","affected_versions":">=0.5.1"}],"env_vars":null,"last_verified":"2026-04-16T00:00:00.000Z","next_check":"2026-07-15T00:00:00.000Z","problems":[{"fix":"Update the function call to explicitly use keyword arguments. For example, change `cabinetry.fit.fit(model, data)` to `cabinetry.fit.fit(model=model, data=data)`.","cause":"Attempting to call a cabinetry function with positional arguments after v0.4.0, where all arguments became keyword-only.","error":"TypeError: <function_name> missing 1 required keyword-only argument: '<arg_name>'"},{"fix":"Upgrade your Python environment to version 3.8 or newer to meet the library's requirements.","cause":"Running cabinetry v0.6.0 or newer on an unsupported Python version (e.g., Python 3.7).","error":"RuntimeError: This version of cabinetry requires Python 3.8 or higher."},{"fix":"Ensure `pyhf` is updated to a compatible version, specifically `pyhf>=0.7.0` for cabinetry v0.5.0 and later (`pip install 'pyhf>=0.7.0'`).","cause":"Incompatibility between the `cabinetry` version and the installed `pyhf` version, particularly if `cabinetry` v0.5.0+ is used with an older `pyhf` (<0.7.0).","error":"pyhf.exceptions.InvalidSpecification: model specification not valid"},{"fix":"Upgrade `matplotlib` to at least version 3.5.0 (`pip install 'matplotlib>=3.5.0'`).","cause":"An outdated `matplotlib` version being used, which lacks features or has breaking API changes that cabinetry's visualization functions rely on.","error":"AttributeError: 'Figure' object has no attribute 'tight_layout' (or other plotting errors)"}]}