CaCoCa (The Carbon Contracts Calculator) is a tool to model carbon contracts for difference (CCfDs) for industrial decarbonization projects. Abatement cost time curves can be calculated, and auctions of such carbon contracts (where the projects bidding the lowest carbon price are awarded contracts) can be modeled.
The techno-economic input data provided in this repository is incomplete and not to be relied upon. It only serves as an example for the functionality of the code. It is advised to use your own data.
The Python version and packages are managed using PEP 621. Packages are listed in the file pyproject.toml. Detailed instructions for installation can be found in the documentation.
Runs are configured using a YAML input file. Example input files are located in the config folder.
Auction simulation — multi-round bidding with budget caps:
uv run python cacoca.py config/config.yml
Cost/emissions analysis and plotting — using CaCoCa's native tech data:
uv run python plot_slides.py
Both commands should be run from the repository root.
CaCoCa integrates with the POSTED techno-economic database as an alternative data source. POSTED is installed automatically as a dependency via uv sync.
To run an analysis using POSTED data:
uv run python posted_coupling/plot_slides_posted.py
The script loops over a list of products (e.g. steel, cement). For each product it reads a config file, computes LCOX and GHGI for all routes, and calls plot_stacked_bars_multi to produce the output slides. Each product requires two files described below.
Controls financial parameters, output settings, and which price scenario to use for each input commodity.
default_wacc: 0.08 # weighted average cost of capital
book_lifetime: 25 # economic lifetime in years
routes_file: config/posted_routes_<product>.yml
project_names: # route labels shown in the bar chart, in order
- RouteA
- RouteB
show_figures: true
show_figs_in_browser: true
save_figures: false
output_dir: output/plot_slides_posted
filename_prefix: <product>
scenarios_dir: data/scenarios/basic/
scenarios_actual:
prices: # component name → scenario name in prices_fuels.csv
Electricity: 'EEX Jahresfuture_DE'
CO2: 'PIKExpertGuess-CO2'
# ... all commodities consumed by any tech in the routes fileproject_names must match the route labels produced by varcombine (see below). Only components listed under scenarios_actual.prices that are also present in CACOCA_TO_TEAM_PRICE_MAP in posted_coupling/routes.py are passed to TEAM; unknown ones are silently ignored. If a listed scenario name does not exist in prices_fuels.csv, a ValueError is raised at startup with the available scenario names.
Defines one or more technology chains. Each top-level key is a route name.
routes:
MyRoute:
chain: "ProcessA -> OutputFlow => ProcessB -> FinalProduct"
techs:
- process_name: "ProcessA"
tedf: "Tech|ProcessA" # optional; defaults to Tech|<process_name>
aggregate:
some_filter: ["Option1", "Option2"] # passed to TEDF.aggregate()
units:
"Output Capacity|Flow": "t/yr" # unit overrides for aggregate()
calc_emissions: false # set true to compute scope 1+2 via emission factors
- process_name: "ProcessB"
calc_emissions: true
func_process: "ProcessB" # process that defines the functional unit
func_flow: "FinalProduct" # flow that defines the functional unit (1 t)
varcombine: "{route}-{some_filter}" # template for route label in output
rename: # optional: map filter values to display names
some_filter:
"Option1": "Conv"
"Option2": "CCS"Key fields:
chain: ProcessChain diagram string.->connects a process to its output flow;=>passes a flow as input to the next process.techs: ordered list of process steps. Each step's data is loaded from POSTED asTech|<process_name>(or the explicittedfpath) and aggregated. Theaggregatedict is forwarded verbatim toTEDF.aggregate()— use it to filter by field values (e.g.carbon_capture: ["No Capture", "End-of-pipe"]) or to override output units.calc_emissions: iftrue, emissions are computed for that step using the emission factors defined inplot_slides_posted.py, or standard emission factors from POSTED. Required for any process that consumes electricity, hydrogen, or other carriers with non-zero supply-chain emissions.func_process/func_flow: identify the reference process and flow for normalisation (functional unit = 1 t offunc_flow).varcombine: Jinja-style template that assembles the route label from the route name and any filtered field columns (e.g.{route}-{carbon_capture}). The resulting labels must matchproject_namesin the config file.rename: remaps field values to shorter display names beforevarcombineis applied.
- Create
config/posted_routes_<product>.ymlwith at least one route. - Create
config/posted_config_<product>.yml. List all commodities consumed across your routes underscenarios_actual.prices, picking a scenario name fromdata/scenarios/basic/prices_fuels.csvfor each. - Add
'<product>'to thefor product in [...]list inposted_coupling/plot_slides_posted.py. - If any process step uses
calc_emissions: true, add emission factors for its input flows to theemi_factorsDataFrame inplot_slides_posted.py(zero is acceptable as a placeholder). - Add any commodity not yet in
CACOCA_TO_TEAM_PRICE_MAPinposted_coupling/routes.py, specifying the TEAM variable name and the unit that matches the price data inprices_fuels.csv.
Add a new entry under routes: in the relevant routes YAML. Then append its label(s) to project_names in the config YAML. No changes to Python code are required unless the route introduces a new commodity type.
The authors of CaCoCa are:
Jakob Dürrwächter
Robin Blömer
Philipp Verpoort
Bennet Weiss
Paul Effing
Johannes Eckstein
Falko Ueckerdt
CaCoCa is Copyright (C) 2023, Jakob Dürrwächter, Robin Blömer, Johannes Eckstein and Falko Ueckerdt and is released under the terms of the
GNU General Public License v3.0. For the full license terms see
the included LICENSE file.
To cite CaCoCa, please use:
J. Dürrwächter, R.Blömer, P. Verpoort, B. Weiss, P. Effing, J. Eckstein, F. Ueckerdt (2023). CaCoCa: The Carbon Contracts Calculator. Version 2.0.0, https://github.com/JakobBD/cacoca.
A BibTeX entry for LaTeX users is:
```latex @Manual{, title = {CaCoCa: The Carbon Contracts Calculator}, author = {Jakob Dürrwächter and Robin Blömer and Philipp Verpoort and Bennet Weiss and Paul Effing and Johannes Eckstein and Falko Ueckerdt}, year = {2023}, note = {Version 2.0.0}, url = {https://github.com/JakobBD/cacoca}, }
## Documentation
Further documentation can be found in the [`doc/` folder](doc/).