Skip to content

Commit

Permalink
Merge pull request #997 from GbotemiB/csp_integration
Browse files Browse the repository at this point in the history
* CSP integration into config files

* rename cutout file for default config

* update costs file to accomodate csp

* added stores and links for csp

* corrected bus for csp bus

* renamed csp rows according to the technology repo

* fixed shape issues in links addition to the network

* added csp rows to the cost file

* added heat buses

* added bus and generator for csp

* more config for csp

* moved csp to extra components

* added more config to csp renewable

* revised csp config

* revised csp config

* fix for CI failing

* renamed csp values

* adjusted csp settings to csp-tower

* fixed typo

* added csp to the config for landlock

* changed key for csp

* adjusted csp naming

* adjusted csp naming

* renamed architecture

* removed correction factor

* add csp to docs

* fix for how_to_docs

* revert how to docs inclusion

* removed csp from extendable carrier

* adjusted capacity_per_sqkm value
  • Loading branch information
GbotemiB authored Jun 4, 2024
1 parent f5e26a5 commit b23cb9b
Show file tree
Hide file tree
Showing 15 changed files with 139 additions and 15 deletions.
2 changes: 1 addition & 1 deletion Snakefile
Original file line number Diff line number Diff line change
Expand Up @@ -456,7 +456,7 @@ rule build_renewable_profiles:
powerplants="resources/" + RDIR + "powerplants.csv",
regions=lambda w: (
"resources/" + RDIR + "bus_regions/regions_onshore.geojson"
if w.technology in ("onwind", "solar", "hydro")
if w.technology in ("onwind", "solar", "hydro", "csp")
else "resources/" + RDIR + "bus_regions/regions_offshore.geojson"
),
cutout=lambda w: "cutouts/"
Expand Down
25 changes: 23 additions & 2 deletions config.default.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ electricity:
custom_powerplants: false # "false" use only powerplantmatching (ppm) data, "merge" combines ppm and custom powerplants, "replace" use only custom powerplants

conventional_carriers: [nuclear, oil, OCGT, CCGT, coal, lignite, geothermal, biomass]
renewable_carriers: [solar, onwind, offwind-ac, offwind-dc, hydro]
renewable_carriers: [solar, csp, onwind, offwind-ac, offwind-dc, hydro]

estimate_renewable_capacities:
stats: "irena" # False, = greenfield expansion, 'irena' uses IRENA stats to add expansion limits
Expand Down Expand Up @@ -313,6 +313,26 @@ renewable:
method: hydro_capacities # 'hydro_capacities' to rescale country hydro production by using hydro_capacities, 'eia' to rescale by eia data, false for no rescaling
year: 2013 # (optional) year of statistics used to rescale the runoff time series. When not provided, the weather year of the snapshots is used
multiplier: 1.1 # multiplier applied after the normalization of the hydro production; default 1.0
csp:
cutout: cutout-2013-era5
resource:
method: csp
installation: SAM_solar_tower
capacity_per_sqkm: 2.392 # From 1.7 to 4.6 addresses issue #361
# Determined by comparing uncorrected area-weighted full-load hours to those
# published in Supplementary Data to
# Pietzcker, Robert Carl, et al. "Using the sun to decarbonize the power
# sector: The economic potential of photovoltaics and concentrating solar
# power." Applied Energy 135 (2014): 704-720.
copernicus:
grid_codes: [20, 30, 40, 60, 90]
distancing_codes: [50]
distance_to_codes: 3000
natura: true
potential: simple # or conservative
clip_p_max_pu: 1.e-2
extendable: true
csp_model: advanced # simple or advanced

# TODO: Needs to be adjusted for Africa.
# Costs Configuration (Do not remove, needed for Sphynx documentation).
Expand Down Expand Up @@ -467,7 +487,8 @@ plotting:
"HVDC links": "#8a1caf"
"DC-DC": "#8a1caf"
"DC link": "#8a1caf"
"load": "#FF0000"
"load": "#ff0000"
"csp": "#fdd404"
nice_names:
OCGT: "Open-Cycle Gas"
CCGT: "Combined-Cycle Gas"
Expand Down
25 changes: 23 additions & 2 deletions config.tutorial.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -169,7 +169,7 @@ electricity:
custom_powerplants: false # "false" use only powerplantmatching (ppm) data, "merge" combines ppm and custom powerplants, "replace" use only custom powerplants

conventional_carriers: [nuclear, oil, OCGT, CCGT, coal, lignite, geothermal, biomass]
renewable_carriers: [solar, onwind, offwind-ac, offwind-dc, hydro]
renewable_carriers: [solar, csp, onwind, offwind-ac, offwind-dc, hydro]

estimate_renewable_capacities:
stats: "irena" # False, = greenfield expansion, 'irena' uses IRENA stats to add expansion limits
Expand Down Expand Up @@ -310,6 +310,26 @@ renewable:
method: hydro_capacities # 'hydro_capacities' to rescale country hydro production by using hydro_capacities, 'eia' to rescale by eia data, false for no rescaling
year: 2013 # (optional) year of statistics used to rescale the runoff time series. When not provided, the cutout weather year is used
multiplier: 1.1 # multiplier applied after the normalization of the hydro production; default 1.0
csp:
cutout: cutout-2013-era5-tutorial
resource:
method: csp
installation: SAM_solar_tower
capacity_per_sqkm: 2.392 # From 1.7 to 4.6 addresses issue #361
# Determined by comparing uncorrected area-weighted full-load hours to those
# published in Supplementary Data to
# Pietzcker, Robert Carl, et al. "Using the sun to decarbonize the power
# sector: The economic potential of photovoltaics and concentrating solar
# power." Applied Energy 135 (2014): 704-720.
copernicus:
grid_codes: [20, 30, 40, 60, 90]
distancing_codes: [50]
distance_to_codes: 3000
natura: true
potential: simple # or conservative
clip_p_max_pu: 1.e-2
extendable: true
csp_model: advanced # simple or advanced

# TODO: Needs to be adjusted for Africa
costs:
Expand Down Expand Up @@ -453,7 +473,8 @@ plotting:
"HVDC links": "#8a1caf"
"DC-DC": "#8a1caf"
"DC link": "#8a1caf"
"load": "#FF0000"
"load": "#ff0000"
"csp": "#fdd404"
nice_names:
OCGT: "Open-Cycle Gas"
CCGT: "Combined-Cycle Gas"
Expand Down
9 changes: 9 additions & 0 deletions data/costs.csv
Original file line number Diff line number Diff line change
Expand Up @@ -193,3 +193,12 @@ HVDC submarine,2030,FOM,2,%/year,Hagspiel
HVDC inverter pair,2030,investment,150000,EUR/MW,Hagspiel
HVDC inverter pair,2030,lifetime,40,years,Hagspiel
HVDC inverter pair,2030,FOM,2,%/year,Hagspiel
csp-tower,2030,FOM,1.1,%/year,ATB CSP data (https://atb.nrel.gov/electricity/2021/concentrating_solar_power)
csp-tower,2030,investment,108.37,"EUR/kW_th,dp",ATB CSP data (https://atb.nrel.gov/electricity/2021/concentrating_solar_power) and NREL SAM v2021.12.2 (https://sam.nrel.gov/).
csp-tower,2030,lifetime,30.0,years,ATB CSP data (https://atb.nrel.gov/electricity/2021/concentrating_solar_power)
csp-tower TES,2030,FOM,1.1,%/year,see solar-tower.
csp-tower TES,2030,investment,14.52,EUR/kWh_th,ATB CSP data (https://atb.nrel.gov/electricity/2021/concentrating_solar_power) and NREL SAM v2021.12.2 (https://sam.nrel.gov/).
csp-tower TES,2030,lifetime,30.0,years,see solar-tower.
csp-tower power block,2030,FOM,1.1,%/year,see solar-tower.
csp-tower power block,2030,investment,759.17,EUR/kW_e,ATB CSP data (https://atb.nrel.gov/electricity/2021/concentrating_solar_power) and NREL SAM v2021.12.2 (https://sam.nrel.gov/).
csp-tower power block,2030,lifetime,30.0,years,see solar-tower.
15 changes: 15 additions & 0 deletions doc/configtables/csp.csv
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
,Unit,Values,Description
cutout,--,Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module can be ERA5 or SARAH-2.,Specifies the directory where the relevant weather data is stored that is specified at ``atlite/cutouts`` configuration. Both ``sarah`` and ``era5`` work.
resource,,,
-- method,--,Must be 'csp',
-- installation,--,"Should be 'SAM_solar_tower' as defined in `atlite <https://github.com/PyPSA/atlite/tree/master/atlite/resources/cspinstallation>`__",Specifies the csp technology and its characteristic attributes.
capacity_per_sqkm,:math:`MW/km^2`,float,Allowable density of csp tower placement. Value relates to socio-technical acceptable density.
copernicus,,,
-- grid_codes,--,Any subset of the `Copernicus Land Cover code list <https://land.copernicus.eu/pan-european/corine-land-cover/clc2018>`_,Specifies areas based on CLC which generally eligible for csp tower placement.
-- distance,m,"int","(Optional) Distance to reserve as uneligible area around 'distance_grid_codes' for the renewable technology."
-- distance_grid_codes,--,"(Optional with 'distance') Any subset of the `Copernicus Land Cover code list <https://land.copernicus.eu/pan-european/corine-land-cover/clc2018>`_","Specifies from which a distance of 'distance' metres is unavailable as a buffer area."
natura,bool,"{true, false}",Switch to exclude `Natura 2000 <https://en.wikipedia.org/wiki/Natura_2000>`_ natural protection areas. Area is excluded if ``true``.
potential,--,"One of {'simple', 'conservative'}",Method to compute the maximal installable potential for a node; confer :ref:`renewableprofiles`
clip_p_max_pu,p.u.,float,To avoid too small values in the renewables` per-unit availability time series values below this threshold are set to zero.
extendable, bool, "{True, False}", "True: In nodes where there is no csp generation, adds a zero-capacity csp generator so that csp is considered for capacity expansion. It is done in the ``add_electricity`` rule."
csp_model,--, One of {'advanced' or 'simple'}, Specifies the CSP model to be used. The advanced model attach stores and links to the csp buses while the simple has no stores and links.
2 changes: 1 addition & 1 deletion doc/configtables/hydro.csv
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
,Unit,Values,Description
cutout,--,"Must be 'europe-2013-era5'","Specifies the directory where the relevant weather data ist stored."
cutout,--,"Must be 'europe-2013-era5'","Specifies the directory where the relevant weather data is stored."
resource,,,
-- method,,, "Specifies the Atlite method to calculate renewable potential."
-- hydrobasin,,, "Specifies the file location for hydrobasins. They are used to make the runoff calibration, defining a polygon to compute the available water surface using a surface integral."
Expand Down
2 changes: 1 addition & 1 deletion doc/configtables/offwind-ac.csv
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
,Unit,Values,Description
cutout,--,"Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module must be ERA5.","Specifies the directory where the relevant weather data ist stored."
cutout,--,"Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module must be ERA5.","Specifies the directory where the relevant weather data is stored."
resource,,,
-- method,--,"Must be 'wind'","A superordinate technology type."
-- turbine,--,"One of turbine types included in `atlite <https://github.com/PyPSA/atlite/tree/master/atlite/resources/windturbine>`_","Specifies the turbine type and its characteristic power curve."
Expand Down
2 changes: 1 addition & 1 deletion doc/configtables/offwind-dc.csv
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
,Unit,Values,Description
cutout,--,"Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module must be ERA5.","Specifies the directory where the relevant weather data ist stored."
cutout,--,"Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module must be ERA5.","Specifies the directory where the relevant weather data is stored."
resource,,,
-- method,--,"Must be 'wind'","A superordinate technology type."
-- turbine,--,"One of turbine types included in `atlite <https://github.com/PyPSA/atlite/tree/master/atlite/resources/windturbine>`__","Specifies the turbine type and its characteristic power curve."
Expand Down
2 changes: 1 addition & 1 deletion doc/configtables/onwind.csv
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
,Unit,Values,Description
cutout,--,"Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module must be ERA5.","Specifies the directory where the relevant weather data ist stored."
cutout,--,"Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module must be ERA5.","Specifies the directory where the relevant weather data is stored."
resource,,,
-- method,--,"Must be 'wind'","A superordinate technology type."
-- turbine,--,"One of turbine types included in `atlite <https://github.com/PyPSA/atlite/tree/master/atlite/resources/windturbine>`__","Specifies the turbine type and its characteristic power curve."
Expand Down
2 changes: 1 addition & 1 deletion doc/configtables/solar.csv
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
,Unit,Values,Description
cutout,--,Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module can be ERA5 or SARAH-2.,Specifies the directory where the relevant weather data ist stored that is specified at ``atlite/cutouts`` configuration. Both ``sarah`` and ``era5`` work.
cutout,--,Should be a file name listed in the configuration ``atlite: cutouts:`` (e.g. 'europe-2013-era5') or reference an existing folder in the directory ``cutouts``. Source module can be ERA5 or SARAH-2.,Specifies the directory where the relevant weather data is stored that is specified at ``atlite/cutouts`` configuration. Both ``sarah`` and ``era5`` work.
resource,,,
-- method,--,Must be 'pv',A superordinate technology type.
-- panel,--,"One of {'Csi', 'CdTe', 'KANENA'} as defined in `atlite <https://github.com/PyPSA/atlite/tree/master/atlite/resources/solarpanel>`__",Specifies the solar panel technology and its characteristic attributes.
Expand Down
13 changes: 13 additions & 0 deletions doc/configuration.rst
Original file line number Diff line number Diff line change
Expand Up @@ -402,6 +402,19 @@ Specifies the options to obtain renewable potentials in every cutout. These are
:widths: 25,7,22,30
:file: configtables/hydro.csv

``csp``
---------------

.. literalinclude:: ../config.default.yaml
:language: yaml
:start-at: csp:
:end-at: csp_model:

.. csv-table::
:header-rows: 1
:widths: 25,7,22,30
:file: configtables/csp.csv

.. _costs_cf:

``costs``
Expand Down
14 changes: 11 additions & 3 deletions scripts/add_electricity.py
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,8 @@ def _add_missing_carriers_from_costs(n, costs, carriers):
costs.columns.to_series().loc[lambda s: s.str.endswith("_emissions")].values
)
suptechs = missing_carriers.str.split("-").str[0]
if "csp" in suptechs:
suptechs = suptechs.str.replace("csp", "csp-tower")
emissions = costs.loc[suptechs, emissions_cols].fillna(0.0)
emissions.index = missing_carriers
n.import_components_from_dataframe(emissions, "Carrier")
Expand Down Expand Up @@ -357,7 +359,9 @@ def attach_wind_and_solar(
)
)
else:
capital_cost = costs.at[tech, "capital_cost"]
capital_cost = costs.at[
"csp-tower" if tech == "csp" else tech, "capital_cost"
]

if not df.query("carrier == @tech").empty:
buses = n.buses.loc[ds.indexes["bus"]]
Expand All @@ -379,9 +383,13 @@ def attach_wind_and_solar(
p_nom_max=ds["p_nom_max"].to_pandas(),
p_max_pu=ds["profile"].transpose("time", "bus").to_pandas(),
weight=ds["weight"].to_pandas(),
marginal_cost=costs.at[suptech, "marginal_cost"],
marginal_cost=costs.at[
"csp-tower" if suptech == "csp" else suptech, "marginal_cost"
],
capital_cost=capital_cost,
efficiency=costs.at[suptech, "efficiency"],
efficiency=costs.at[
"csp-tower" if suptech == "csp" else suptech, "efficiency"
],
)


Expand Down
37 changes: 37 additions & 0 deletions scripts/add_extra_components.py
Original file line number Diff line number Diff line change
Expand Up @@ -184,6 +184,43 @@ def attach_stores(n, costs, config):
marginal_cost=costs.at["battery inverter", "marginal_cost"],
)

if ("csp" in config["renewable"].keys()) and (
config["renewable"]["csp"]["csp_model"] == "advanced"
):
# add buses for csp
n.madd("Bus", buses_i + " csp", carrier="csp", **bus_sub_dict)

csp_buses_i = n.buses.index[n.buses.index.str.contains("csp")]

# change bus of existing csp generators
old_csp_bus_vector = buses_i + " csp"
n.generators.loc[old_csp_bus_vector, "bus"] = csp_buses_i

# add stores for csp
n.madd(
"Store",
csp_buses_i,
bus=csp_buses_i,
carrier="csp",
e_cyclic=True,
e_nom_extendable=True,
capital_cost=costs.at["csp-tower TES", "capital_cost"],
marginal_cost=costs.at["csp-tower TES", "marginal_cost"],
)

# add links for csp
n.madd(
"Link",
csp_buses_i,
bus0=csp_buses_i,
bus1=buses_i,
carrier="csp",
efficiency=costs.at["csp-tower", "efficiency"],
capital_cost=costs.at["csp-tower", "capital_cost"],
p_nom_extendable=True,
marginal_cost=costs.at["csp-tower", "marginal_cost"],
)


def attach_hydrogen_pipelines(n, costs, config):
elec_opts = config["electricity"]
Expand Down
2 changes: 1 addition & 1 deletion scripts/simplify_network.py
Original file line number Diff line number Diff line change
Expand Up @@ -319,7 +319,7 @@ def simplify_links(
exclude_carriers=[],
aggregation_strategies=dict(),
):
## Complex multi-node links are folded into end-points
# Complex multi-node links are folded into end-points
logger.info("Simplifying connected link components")

if n.links.empty:
Expand Down
2 changes: 1 addition & 1 deletion test/config.landlock.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ retrieve_databundle: # required to be "false" for nice CI test output
countries: ["BW"]

electricity:
renewable_carriers: [solar, onwind, hydro]
renewable_carriers: [solar, csp, onwind, hydro]

build_osm_network:
force_ac: true # When true, it forces all components (lines and substation) to be AC-only

0 comments on commit b23cb9b

Please sign in to comment.