Skip to content

Commit

Permalink
Temporarily hard-coded UP and residential cases
Browse files Browse the repository at this point in the history
  • Loading branch information
astronobri committed Jan 3, 2024
1 parent 522f2bc commit 85e614a
Showing 1 changed file with 159 additions and 43 deletions.
202 changes: 159 additions & 43 deletions omf/models/derUtilityCost.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import warnings
# warnings.filterwarnings("ignore")

import shutil, datetime, csv
import shutil, datetime, csv, json
from os.path import join as pJoin

# OMF imports
Expand All @@ -13,7 +13,7 @@
from omf.models import __neoMetaModel__
from omf.models.__neoMetaModel__ import *
from omf.models import vbatDispatch as vb
from omf.solvers import reopt_jl as RE
from omf.solvers import reopt_jl

# Model metadata:
tooltip = ('The derUtilityCost model evaluates the financial costs of controlling behind-the-meter '
Expand All @@ -22,21 +22,125 @@
modelName, template = __neoMetaModel__.metadata(__file__)
hidden = True

def work(modelDir, inputDict):
''' Run the model in its directory. '''

# Delete output file every run if it exists
outData = {}
def create_REopt_jl_jsonFile(inputDict):

## Site parameters
latitude = float(inputDict['latitude'])
longitude = float(inputDict['longitude'])
urdbLabel = str(inputDict['urdbLabel'])
year = int(inputDict['year'])

## Energy technologies
solar = inputDict['solar']
generator = inputDict['generator']
battery = inputDict['battery']
outData['solar'] = inputDict['solar']
outData['generator'] = inputDict['generator'] ## TODO: make generator switch on only during outage?
outData['battery'] = inputDict['battery']
outData['year'] = inputDict['year']

latitude = float(inputDict['latitude'])
longitude = float(inputDict['longitude'])
## Financial and Load parameters
energyCost = float(inputDict['energyCost'])
demandCost = float(inputDict['demandCost'])
wholesaleCost = float(inputDict['wholesaleCost'])
lostLoadValue = float(inputDict['value_of_lost_load'])
analysisYears = int(inputDict['analysisYears'])
omCostEscalator = float(inputDict['omCostEscalator'])
discountRate = float(inputDict['discountRate'])
criticalLoadFactor = float(inputDict['criticalLoadFactor'])
userCriticalLoadShape = True if inputDict['userCriticalLoadShape'] == "True" else False

## Solar parameters
solarCost = float(inputDict['solarCost'])
solarMin = float(inputDict['solarMin'])
if solar == 'off':
solarMax = 0
elif solar == 'on':
solarMax = float(inputDict['solarMax'])
solarExisting = float(inputDict['solarExisting'])

solarCanExport = True if inputDict['solarCanExport'] == "True" else False
solarCanCurtail = True if inputDict['solarCanCurtail'] == "True" else False
solarMacrsOptionYears = int(inputDict['solarMacrsOptionYears'])
solarItcpercent = float(inputDict['solarItcPercent'])

## BESS parameters
batteryPowerCost = float(inputDict['batteryPowerCost'])
batteryCapacityCost = float(inputDict['batteryCapacityCost'])
batteryPowerCostReplace = float(inputDict['batteryPowerCostReplace'])
batteryCapacityCostReplace = float(inputDict['batteryCapacityCostReplace'])
batteryPowerReplaceYear = float(inputDict['batteryPowerReplaceYear'])
batteryCapacityReplaceYear = float(inputDict['batteryCapacityReplaceYear'])
batteryPowerMin = float(inputDict['batteryPowerMin'])
batteryCapacityMin = float(inputDict['batteryCapacityMin'])
batteryMacrsOptionYears = int(inputDict['batteryMacrsOptionYears'])
batteryItcPercent = float(inputDict['batteryItcPercent'])

## Diesel Generator paramters
dieselGenCost = float(inputDict['dieselGenCost'])
dieselMacrsOptionYears = int(inputDict['dieselMacrsOptionYears'])
dieselMax = float(inputDict['dieselMax'])
dieselMin = float(inputDict['dieselMin'])
dieselFuelCostGal = float(inputDict['dieselFuelCostGal'])
dieselCO2Factor = float(inputDict['dieselCO2Factor'])
dieselOMCostKw = float(inputDict['dieselOMCostKw'])
dieselOMCostKwh = float(inputDict['dieselOMCostKwh'])
dieselOnlyRunsDuringOutage = True if inputDict['dieselOnlyRunsDuringOutage'] == "True" else False

## Outage/resilience paramters
outage_start_hour = int(inputDict['outage_start_hour'])
outage_duration = int(inputDict['outageDuration'])
outage_end_hour = outage_start_hour + outage_duration

scenario = {
"Site": {
"latitude": latitude,
"longitude": longitude
},
"ElectricTariff": {
"wholesale_rate": wholesaleCost
},
"ElectricLoad": {
"loads_kw": jsonifiableLoad,
"year": year
},
"Financial": {
"value_of_lost_load_per_kwh": value_of_lost_load,
"analysis_years": analysisYears,
"om_cost_escalation_rate_fraction": omCostEscalator,
"offtaker_discount_rate_fraction": discountRate
},
"PV": {
"installed_cost_per_kw": solarCost,
"min_kw": solarMin,
"max_kw": solarMax,
"can_export_beyond_nem_limit": solarCanExport,
"can_curtail": solarCanCurtail,
"macrs_option_years": solarMacrsOptionYears,
"federal_itc_fraction": solarItcPercent
},
"ElectricStorage": {
"installed_cost_per_kwh": batteryPowerCost,
"installed_cost_per_kwh": batteryCapacityCost,
"replace_cost_per_kw": batteryPowerCostReplace,
"replace_cost_per_kwh": batteryCapacityCostReplace,
"inverter_replacement_year": batteryPowerReplaceYear,
"battery_replacement_year": batteryCapacityReplaceYear,
"min_kw": batteryPowerMin,
"min_kwh": batteryCapacityMin,
"macrs_option_years": batteryMacrsOptionYears,
"total_itc_fraction": batteryItcPercent
},
"Generator": {
"installed_cost_per_kw": dieselGenCost,
"only_runs_during_grid_outage": dieselOnlyRunsDuringOutage,
"macrs_option_years": dieselMacrsOptionYears
}
}

return jsonFile

def work(modelDir, inputDict):
''' Run the model in its directory. '''

# Delete output file every run if it exists
out = {}

## Setting up the demand file (hourly kWh) and temperature file
with open(pJoin(modelDir, 'demand.csv'), 'w') as f:
Expand All @@ -47,17 +151,26 @@ def work(modelDir, inputDict):

with open(pJoin(modelDir, 'temp.csv'), 'w') as f:
lines = inputDict['tempCurve'].split('\n')
outData["tempData"] = [float(x) if x != '999.0' else float(inputDict['setpoint']) for x in lines if x != '']
out["tempData"] = [float(x) if x != '999.0' else float(inputDict['setpoint']) for x in lines if x != '']
correctData = [x+'\n' if x != '999.0' else inputDict['setpoint']+'\n' for x in lines if x != '']
f.write(''.join(correctData))
assert len(correctData) == 8760

outage = True if inputDict["outage"] == "on" else False



out['solar'] = inputDict['solar']
out['generator'] = inputDict['generator'] ## TODO: make generator switch on only during outage?
out['battery'] = inputDict['battery']
out['year'] = inputDict['year']

## Run REopt and gather outputs for vbatDispath
## TODO: Create a function that will gather the urdb label from a user provided location (city,state)
#RE.run_reopt_jl(modelDir,inputFile,outages)
RE.run_reopt_jl(path="/Users/astronobri/Documents/CIDER/reopt/inputs/", inputFile="UP_PV_outage_1hr.json", outages=outage) # UP coop PV

#RE.run_reopt_jl(path="/Users/astronobri/Documents/CIDER/reopt/inputs/", inputFile="UP_PV_outage_1hr.json", outages=outage) # UP coop PV
#RE.run_reopt_jl(path="/Users/astronobri/Documents/CIDER/reopt/inputs/", inputFile="residential_input.json", outages=True) # UP coop PV

#with open(pJoin(modelDir, 'results.json')) as jsonFile:
# results = json.load(jsonFile)
Expand All @@ -75,62 +188,72 @@ def work(modelDir, inputDict):
#modelDir = "/Users/astronobri/Documents/CIDER/omf/omf/data/Model/admin/meowtest"

test = vb.work(modelDir,inputDict)
print(test)

with open('/Users/astronobri/Documents/CIDER/jsontestfile.json', "w") as fp:
json.dump(test, fp)

#outData['stdout'] = test
#print(modDirvbatt)
#vbattWork_out = vb.work(modelDir,vbattNew_out[1])

# Model operations typically ends here.
# Stdout/stderr.
outData["stdout"] = "Success"
outData["stderr"] = ""
return outData
out["stdout"] = "Success"
out["stderr"] = ""
return out

def new(modelDir):
''' Create a new instance of this model. Returns true on success, false on failure. '''
with open(pJoin(__neoMetaModel__._omfDir,"static","testFiles","Texas_1yr_Load.csv")) as f:
demand_curve = f.read()
with open(pJoin(__neoMetaModel__._omfDir,"static","testFiles","Texas_1yr_Temp.csv")) as f:
temp_curve = f.read()

defaultInputs = {
"user" : "admin",
"modelType": modelName,
"latitude" : '39.7392358',
"latitude" : '39.7392358',
"longitude" : '-104.990251',
#"latitude" : '39.532165', ## Rivesville, WV
#"longitude" : '-80.120618',
"year" : '2018',
"analysis_years" : 25,
"urdbLabel" : '612ff9c15457a3ec18a5f7d3',
"analysis_years" : 25,
#"urdbLabel" : '612ff9c15457a3ec18a5f7d3', ## Brighton, CO - United Power
"urdbLabel" : '643476222faee2f0f800d8b1', ## Rivesville, WV - Monongahela Power
"demandCurve": demand_curve,
"tempCurve": temp_curve,
"outage": False,
"solar" : "on",
"battery" : "on",
"generator" : "off",
"created":str(datetime.datetime.now()),
"load_type": "1",
"number_devices": "2000",
"load_type": "2",
"number_devices": "1",
"power": "5.6",
"capacitance": "2",
"resistance": "2",
"cop": "2.5",
"setpoint": "22.5",
"setpoint": "19.5",
"deadband": "0.625",
"demandChargeCost":"25",
"electricityCost":"0.06",
"projectionLength":"15",
"electricityCost":"0.16",
"projectionLength":"25",
"discountRate":"2",
"unitDeviceCost":"150",
"unitUpkeepCost":"5",
"fileName": "Texas_1yr_Load.csv",
"tempFileName": "Texas_1yr_Temp.csv",
"modelType": modelName,
#"fileName": "Texas_1yr_Load.csv",
#"tempFileName": "Texas_1yr_Temp.csv",
#"fileName": "/Users/astronobri/Documents/CIDER/reopt/inputs/residential_PV_load.csv",
"fileName": "/Users/astronobri/Documents/CIDER/UP-slide18/3reopt-web-residential-load-profile.csv",
"tempFileName": "/Users/astronobri/Desktop/extended_temperature_data.csv",
"modelType": modelName
}
return __neoMetaModel__.new(modelDir, defaultInputs)

@neoMetaModel_test_setup
def _debugging():
#def _tests():
def _tests():
# Location
modelLoc = pJoin(__neoMetaModel__._omfDir,"data","Model","admin","Automated Testing of " + modelName)
modelLoc = pJoin(__neoMetaModel__._omfDir,"data","Model","admin","Automated_Testing_of_" + modelName)
# Blow away old test results if necessary.
try:
shutil.rmtree(modelLoc)
Expand All @@ -140,20 +263,13 @@ def _debugging():
# Create New.
new(modelLoc)
# Pre-run.
__neoMetaModel__.renderAndShow(modelLoc)
#__neoMetaModel__.renderAndShow(modelLoc)
# Run the model.
__neoMetaModel__.runForeground(modelLoc)
# Show the output.
__neoMetaModel__.renderAndShow(modelLoc)
#__neoMetaModel__.renderAndShow(modelLoc)

if __name__ == '__main__':
_debugging()
#_tests()
_tests()
#pass


"""import omf.models.vbatDispatch as vb
modelDir = "C:\\Users\\lisam\\Desktop\\Repositories\\omf\\omf\\data\\Model\\admin\testVbatt_CIDER"
[modDirvbatt, inputdict] = vb.new(modelDir)
vbattWork_out = vb.work(modelDir,vbattNew_out[1])"""

0 comments on commit 85e614a

Please sign in to comment.