Files
cariflex/tools/shapeshifter-library-python-main/examples/dso/demo_dso.py
Eric F d398a6ced2 Add extracted tools: CitrineOS, OpenOCPP, ShapeShifter
- CitrineOS core extracted (CSMS OCPP 2.0.1)
- OpenOCPP extracted (firmware OCPP 1.6J/2.0.1)
- ShapeShifter library installed (pip install -e)
- ShapeShifter specification extracted
- EVerest extracted

TODO updated with progress
2026-06-08 00:38:27 -04:00

145 lines
4.8 KiB
Python

from datetime import datetime, timezone
from uuid import uuid4
from xsdata.models.datatype import XmlDate
from shapeshifter_uftp import ShapeshifterDsoService
from shapeshifter_uftp.uftp import (
AvailableRequested,
FlexOrder,
FlexOrderISP,
FlexRequest,
FlexRequestISP,
)
class DemoDSO(ShapeshifterDsoService):
def process_d_prognosis(self, message):
print(f"Received a message: {message}")
def process_dso_portfolio_query_response(self, message):
print(f"Received a message: {message}")
def process_dso_portfolio_update_response(self, message):
print(f"Received a message: {message}")
def process_flex_offer(self, message):
print(f"Received a message: {message}")
# Example of how to send a new message after
# processing an incoming message
agr_client = self.agr_client(message.sender_domain)
agr_client.send_flex_order(
FlexOrder(
isp_duration=message.isp_duration,
time_zone=message.time_zone,
period=message.period,
congestion_point=message.congestion_point,
flex_offer_message_id=message.message_id,
isps=[
FlexOrderISP(
power=isp.power,
start=isp.start,
duration=isp.duration,
)
for isp in message.offer_options[0].isps
],
price=message.offer_options[0].price,
currency="EUR",
order_reference="demo-order",
activation_factor=1.0
)
)
def process_flex_offer_revocation(self, message):
print(f"Received a message: {message}")
def process_flex_order_response(self, message):
print(f"Received a message: {message}")
def process_flex_request_response(self, message):
print(f"Received a message: {message}")
def process_flex_reservation_update_response(self, message):
print(f"Received a message: {message}")
def process_flex_settlement_response(self, message):
print(f"Received a message: {message}")
def process_metering(self, message):
print(f"Received a message: {message}")
# The Key Lookup function is used to look up the
# (public) signing key of other senders. You either
# implement a database-lookup or query to the GOPACS
# Shapeshifter Address Book here, or use some other method
# to find the appropriate public keys for the other
# participants.
def key_lookup(sender_domain, sender_role):
known_senders = {
("aggregator.demo", "AGR"): "kSyHrhqSGtSgLegJW1Rqib3sHfL9SdLlVE6qRrexfLc=",
("cro.demo", "CRO"): "ySUYU87usErRFKGJafwvVDLGhnBVJCCNYfQvmwv8ObM=",
}
return known_senders.get((sender_domain, sender_role))
# The Endpoint Lookup function is used to look up the
# endpoint URL for other participants.
def endpoint_lookup(sender_domain, sender_role):
known_senders = {
("aggregator.demo", "AGR"): "http://localhost:8080/shapeshifter/api/v3/message",
("cro.demo", "CRO"): "http://localhost:8082/shapeshifter/api/v3/message",
}
return known_senders.get((sender_domain, sender_role))
if __name__ == "__main__":
# Create a DemoDSO object that contains all the logic for
# responding to messages. In our case, we simply print incoming
# messages.
dso = DemoDSO(
sender_domain="dso.demo",
signing_key="OLgpAnYyZmskhCKGmFAj1tysKgGjwehK0msC6NoAg9g2xNur+IAFTq1uyOuIGD9nl1J9Cy26UPQakwjZ8sNZ5w==",
key_lookup_function=key_lookup,
endpoint_lookup_function=endpoint_lookup,
port=8081,
)
# Start the DSO service in a separate thread
dso.run_in_thread()
# Create a client object to talk to an aggregator at the given domain.
agr_client = dso.agr_client("aggregator.demo")
# Prepare a FlexRequest message
flex_request_message = FlexRequest(
isp_duration="PT15M",
period=XmlDate(2023, 1, 1),
congestion_point="ean.123456789012",
isps=[
FlexRequestISP(
disposition=AvailableRequested.REQUESTED,
min_power=0,
max_power=10,
start=1,
duration=1,
)
],
revision=1,
expiration_date_time=datetime.now(timezone.utc).isoformat(),
contract_id=str(uuid4()),
service_type="MyService",
)
# As a demo, press enter to send another FlexRequset message.
while True:
try:
input("Press return to send a FlexRequest message to the AGR")
response = agr_client.send_flex_request(flex_request_message)
print(f"Response was: {response}")
except:
dso.stop()
break