Skip to content

Commit

Permalink
Merge branch 'main' into feat/expose-budget-constants
Browse files Browse the repository at this point in the history
  • Loading branch information
FabianKneissl committed May 10, 2024
2 parents 141c44a + 876f41c commit a53f5cc
Show file tree
Hide file tree
Showing 33 changed files with 2,912 additions and 1,485 deletions.
42 changes: 22 additions & 20 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,25 +10,31 @@ This package is part of [Pledge4Future](https://pledge4future.org/), a project t

## :computer: Installation

`co2calculator` is currently only available on GitHub. To use the code, clone the repository as usual, for example with:
### With pip (recommended)

```
git clone https://github.com/pledge4future/co2calculator.git
```
PyPi release coming soon!

The repository has a submodule (https://github.com/trainline-eu/stations). This has to be pulled with the following command:
<!--The recommended way to install this package is with pip from the Python Package Index ([PyPi](https://pypi.org/)):
```
git submodule update --init --recursive
```
pip install -U co2calculator
```-->

### From source

This package requires Python 3.9 and the packages listed in `requirements.txt`
To install this package from source, clone the repository as usual, for example with:

```
$ pip install -r requirements.txt
```
git clone https://github.com/pledge4future/co2calculator.git
cd co2calculator
```

This package requires Python 3.10, 3.11 or 3.12 and can be installed using [poetry](https://python-poetry.org/). You can install it in your (virtual) environment with:

```
$ pip install -U poetry
$ poetry install --no-root
```


## ⌨ How to Use
Expand All @@ -48,11 +54,6 @@ The CO<sub>2</sub> Calculator uses the [OpenRouteService (ORS) API](https://open

If you want to contribute to this project, please fork this repository and create a pull request with your suggested changes.

Running the unit tests and applying the pre-commit hooks requires installing the packages listed in `requirements-dev.txt`.

```
$ pip install -r requirements-dev.txt
```

### Install pre-commit hooks

Expand All @@ -77,14 +78,14 @@ $ pytest

### Emission factors

- [Probas](https://www.probas.umweltbundesamt.de/php/index.php)
- [UBA (2021). "Umweltfreundlich mobil"](https://www.umweltbundesamt.de/en/publikationen/umweltfreundlich-mobil)
- [GOV.UK (2020). Greenhouse gas reporting: conversion factors 2020](https://www.gov.uk/government/publications/greenhouse-gas-reporting-conversion-factors-2020)
- [Carbon footprint (2023). International electricity factors](https://www.carbonfootprint.com/international_electricity_factors.html)
- [GOV.UK (2023). Greenhouse gas reporting: conversion factors 2023](https://www.gov.uk/government/publications/greenhouse-gas-reporting-conversion-factors-2023)
- [mobitoool (2023). mobitool-Faktoren v3.0](https://www.mobitool.ch/de/tools/mobitool-faktoren-v2-1-25.html)

### Conversion factors

- [BAFA (2020): Merkblatt zur Ermittlung des Gesamtenergieverbrauchs](https://www.bafa.de/SharedDocs/Downloads/DE/Energie/ea_ermittlung_gesamtenergieverbrauch.html)
- [Krajnc, N. (2015): Wood fuels handbook, FAO](https://agris.fao.org/agris-search/search.do?recordID=XF2017001919)
- [Krajnc, N. (2015): Wood fuels handbook, FAO](http://large.stanford.edu/courses/2017/ph240/timcheck1/docs/fao-krajnc-2015.pdf)

### Detour coefficients and constants

Expand All @@ -94,9 +95,10 @@ $ pytest
- Detour coefficients for train trips (1.2) and bus trips (1.5):
- Adapted from [GES 1point5](https://labos1point5.org/ges-1point5), who were advised by Frédéric Héran (economist and urban planner).

### Airports
### Airports and Train Stations

- [OurAirports](https://ourairports.com/data/)
- [Stations - A Database of European Train Stations (Trainline EU)](https://github.com/trainline-eu/stations)

## 🤝 Project partners

Expand Down
37 changes: 15 additions & 22 deletions co2calculator/calculate.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,21 +21,17 @@

from ._types import Kilogram, Kilometer
from .constants import (
KWH_TO_TJ,
Size,
CarFuel,
BusFuel,
TrainFuel,
BusTrainRange,
FlightClass,
FerryClass,
ElectricityFuel,
HeatingFuel,
Unit,
TransportationMode,
CountryCode2,
)
from .data_handlers import EmissionFactors, ConversionFactors
from .distances import create_distance_request, get_distance, range_categories
from .parameters import (
ElectricityEmissionParameters,
HeatingEmissionParameters,
Expand All @@ -48,16 +44,21 @@


def calc_co2_electricity(
consumption: float, fuel_type: ElectricityFuel = None, energy_share: float = 1
consumption: float,
fuel_type: ElectricityFuel = None,
country_code: CountryCode2 = None,
own_share: float = 1,
) -> Kilogram:
"""Function to compute electricity emissions
:param consumption: energy consumption
:param fuel_type: energy (mix) used for electricity [german_energy_mix, solar]
:param fuel_type: energy (mix) used for electricity [production fuel mix, residual fuel mix]
:param country_code: 2 Letter ISO country code
:param energy_share: the research group's approximate share of the total electricity energy consumption
:type consumption: float
:type fuel_type: str
:type energy_share: float
:type country_code: str
:type own_share: float
:return: total emissions of electricity energy consumption
:rtype: Kilogram
"""
Expand All @@ -69,16 +70,14 @@ def calc_co2_electricity(
# Get the co2 factor
co2e = emission_factors.get(params.dict())

# co2 equivalents for heating and electricity refer to a consumption of 1 TJ
# so consumption needs to be converted to TJ
return consumption * energy_share / KWH_TO_TJ * co2e
return consumption * own_share * co2e


def calc_co2_heating(
consumption: float,
fuel_type: HeatingFuel,
unit: Unit = None,
area_share: float = 1.0,
own_share: float = 1.0,
) -> Kilogram:
"""Function to compute heating emissions
Expand All @@ -87,16 +86,16 @@ def calc_co2_heating(
[coal, district_heating, electricity, gas, heat_pump_air,
heat_pump_ground, liquid_gas, oil, pellet, solar, woodchips]
:param unit: unit of energy consumption [kwh, kg, l, m^3]
:param area_share: share of building area used by research group
:param own_share: share of building area used by research group
:type consumption: float
:type fuel_type: str
:type unit: str
:type area_share: float
:type own_share: float
:return: total emissions of heating energy consumption
:rtype: Kilogram
"""
# Validate parameters
assert 0 < area_share <= 1
assert 0 < own_share <= 1
params_extracted = {k: v for k, v in locals().items() if v is not None}
params = HeatingEmissionParameters(**params_extracted)

Expand All @@ -106,14 +105,11 @@ def calc_co2_heating(
if unit is not Unit.KWH:
# Get the conversion factor
conversion_factor = conversion_factors.get(fuel_type=fuel_type, unit=unit)

consumption_kwh = consumption * conversion_factor
else:
consumption_kwh = consumption

# co2 equivalents for heating and electricity refer to a consumption of 1 TJ
# so consumption needs to be converted to TJ
return consumption_kwh * area_share / KWH_TO_TJ * co2e
return consumption_kwh * co2e * own_share


def calc_co2_trip(
Expand Down Expand Up @@ -149,7 +145,6 @@ def calc_co2_commuting(
weekly_distance: Kilometer,
size: Size = None,
fuel_type: BusFuel | CarFuel | TrainFuel = None,
occupancy: int = None,
passengers: int = None,
) -> Kilogram:
"""Calculate co2 emissions for commuting per mode of transport
Expand All @@ -158,13 +153,11 @@ def calc_co2_commuting(
:param weekly_distance: distance in km per week
:param size: size of car or bus if applicable: [small, medium, large, average]
:param fuel_type: fuel type of car, bus or train if applicable
:param occupancy: occupancy [%], if applicable/known (only for bus): [20, 50, 80, 100]
:param passengers: number of passengers, if applicable (only for car)
:type transportation_mode: str
:type weekly_distance: Kilometer
:type size: str
:type fuel_type: str
:type occupancy: int
:type passengers: int
:return: total weekly emissions for the respective mode of transport
:rtype: Kilogram
Expand Down
29 changes: 9 additions & 20 deletions co2calculator/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,12 @@
import enum

import iso3166
import pandas as pd
from co2calculator.data_handlers import Airports

from dataclasses import dataclass

KWH_TO_TJ = 277777.77777778

DF_AIRPORTS = pd.read_csv(
"https://davidmegginson.github.io/ourairports-data/airports.csv"
)


@dataclass
class BudgetOnePointFiveDegrees:
Expand Down Expand Up @@ -49,26 +45,20 @@ class BudgetTwoDegrees:
class HeatingFuel(enum.Enum):
"""Enum for heating fuel types"""

HEAT_PUMP_AIR = "heat_pump_air"
HEAT_PUMP_GROUND = "heat_pump_ground"
HEAT_PUMP_WATER = "heat_pump_water"
LIQUID_GAS = "liquid_gas"
OIL = "oil"
PELLETS = "pellets"
SOLAR = "solar"
WOODCHIPS = "woodchips"
ELECTRICITY = "electricity"
GAS = "gas"
COAL = "coal"
DISTRICT_HEATING = "district_heating"
GAS = "gas"
WOOD_PELLETS = "wood pellets"
WOOD_CHIPS = "wood chips"
LPG = "liquid gas"


@enum.unique
class ElectricityFuel(str, enum.Enum):
"""Enum for electricity fuel types"""

GERMAN_ENERGY_MIX = "german_energy_mix"
SOLAR = "solar"
PRODUCTION_FUEL_MIX = "production fuel mix"
RESIDUAL_FUEL_MIX = "residual fuel mix"


@enum.unique
Expand Down Expand Up @@ -119,7 +109,6 @@ class FlightClass(str, enum.Enum):
"""Enum for flight classes"""

ECONOMY = "economy_class"
PREMIUM_ECONOMY = "premium_economy_class"
BUSINESS = "business_class"
FIRST = "first_class"
AVERAGE = "average"
Expand All @@ -138,9 +127,9 @@ class FerryClass(str, enum.Enum):
class FlightRange(str, enum.Enum):
"""Enum for flight ranges"""

DOMESTIC = "domestic"
SHORT_HAUL = "short-haul"
LONG_HAUL = "long-haul"
AVERAGE = "average"


@enum.unique
Expand Down Expand Up @@ -264,7 +253,7 @@ def __get_validators__(cls):

@classmethod
def validate_iata_code(cls, iata_code: str) -> str:
if iata_code in DF_AIRPORTS["iata_code"].values:
if iata_code in Airports().airports["iata_code"].values:
return iata_code
else:
raise ValueError(f"{iata_code} was not found in airport database")
6 changes: 3 additions & 3 deletions co2calculator/data/conversion_factors_heating.csv
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
,fuel_type,unit,conversion_value
0,oil,l,10.6
1,liquid_gas,kg,14.1
1,liquid gas,kg,14.1
2,coal,kg,6.0
3,pellet,kg,5.4
4,woodchips,kg,5.2
3,wood pellets,kg,5.4
4,wood chips,kg,5.2
5,gas,m^3,10.8
Loading

0 comments on commit a53f5cc

Please sign in to comment.