@@ -30,59 +30,6 @@ import (
3030
3131// --- Reuseable Functions for Route Logic -------------------------------------------------------
3232
33- // capacityToValueMultiplier return a number, plus the index to raise 10 to the power to
34- // to get the resultant number of Watts, to the closest power of 3.
35- // This is an important function which tries to preserve accuracy whilst also enabling a
36- // large range of values to be represented by two 16 bit integers.
37- func capacityToValueMultiplier (capacityWatts uint64 ) (int16 , int16 , error ) {
38- if capacityWatts == 0 {
39- return 0 , 0 , nil
40- }
41-
42- currentValue := capacityWatts
43- exponent := int16 (0 )
44-
45- const maxExponent = 18 // Limit to ExaWatts - current generation is ~20PW for the whole world!
46-
47- // Keep scaling up as long as the value exceeds the int16 limit
48- for currentValue > math .MaxInt16 {
49- if exponent >= maxExponent {
50- return 0 , exponent , fmt .Errorf (
51- "input represents a value greater than %d ExaWatts, which is not supported" ,
52- math .MaxInt16 ,
53- )
54- }
55-
56- // Divide by 1000 to get to the next SI unit prefix
57- // * add on 500 to round up numbers that are over halfway to the next 10^3
58- nextValue := (currentValue + 500 ) / 1000
59-
60- // Check we haven't accidentally rounded to 0
61- if nextValue == 0 && currentValue > 0 {
62- return 0 , exponent + 3 , fmt .Errorf (
63- "scaled value rounded to zero from large input %d at potential exponent %d" ,
64- capacityWatts , exponent + 3 )
65- }
66-
67- currentValue = nextValue
68-
69- exponent += 3
70- }
71-
72- // This is safe as currentValue is now less than or equal to int16 max
73- // but I've put a check to really be as safe as possible
74- if currentValue > math .MaxInt16 {
75- return 0 , exponent , fmt .Errorf (
76- "scaled value %d exceeds int16 max %d at exponent %d" ,
77- currentValue , math .MaxInt16 , exponent ,
78- )
79- }
80-
81- resultValue := int16 (currentValue )
82-
83- return resultValue , exponent , nil
84- }
85-
8633// timeWindowToPgWindow converts a TimeWindow protobuf message to a pair of pgtype.Timestamp values.
8734func timeWindowToPgWindow (
8835 window * pb.TimeWindow ,
@@ -636,11 +583,7 @@ func (s *DataPlatformDataServiceServerImpl) StreamForecastData(
636583 P50Fraction : float32 (pred .P50Sip ) / 30000.0 ,
637584 OtherStatisticsFractions : otherStatistics ,
638585 CreatedTimestampUtc : timestamppb .New (forecast .CreatedAtUtc .Time ),
639- EffectiveCapacityWatts : uint64 (
640- pred .CapacityIncLimit ,
641- ) * uint64 (
642- math .Pow10 (int (pred .CapacityUnitPrefixFactor )),
643- ),
586+ EffectiveCapacityWatts : uint64 (pred .CapacityWatts ),
644587 })
645588 if err != nil {
646589 return err
@@ -741,10 +684,8 @@ func (s *DataPlatformDataServiceServerImpl) GetWeekAverageDeltas(
741684 DeltaFraction : float32 (delta .AvgDeltaSip ) / 30000.0 ,
742685 HorizonMins : uint32 (delta .HorizonMins ),
743686 EffectiveCapacityWatts : uint64 (
744- dbSource .CapacityIncLimit ,
745- ) * uint64 (
746- math .Pow10 (int (dbSource .CapacityUnitPrefixFactor )),
747- ), // Should this be done over time? I'm not sure how important this is to the response
687+ dbSource .CapacityWatts ,
688+ ), // Should this be done over time?
748689 }
749690 }
750691
@@ -805,13 +746,9 @@ func (s *DataPlatformDataServiceServerImpl) GetObservationsAsTimeseries(
805746 values := make ([]* pb.GetObservationsAsTimeseriesResponse_Value , len (dbObs ))
806747 for i , obs := range dbObs {
807748 values [i ] = & pb.GetObservationsAsTimeseriesResponse_Value {
808- ValueFraction : float32 (obs .ValueSip ) / 30000.0 ,
809- TimestampUtc : timestamppb .New (obs .ObservationTimestampUtc .Time ),
810- EffectiveCapacityWatts : uint64 (
811- obs .EffectiveCapacity ,
812- ) * uint64 (
813- math .Pow10 (int (obs .CapacityUnitPrefixFactor )),
814- ),
749+ ValueFraction : float32 (obs .ValueSip ) / 30000.0 ,
750+ TimestampUtc : timestamppb .New (obs .ObservationTimestampUtc .Time ),
751+ EffectiveCapacityWatts : uint64 (obs .CapacityWatts ),
815752 }
816753 }
817754
@@ -945,14 +882,10 @@ func (s *DataPlatformDataServiceServerImpl) GetLatestObservations(
945882 observations := make ([]* pb.GetLatestObservationsResponse_Observation , len (dbObs ))
946883 for i , obs := range dbObs {
947884 observations [i ] = & pb.GetLatestObservationsResponse_Observation {
948- LocationUuid : obs .GeometryUuid .String (),
949- TimestampUtc : timestamppb .New (obs .ObservationTimestampUtc .Time ),
950- ValueFraction : float32 (obs .ValueSip ) / 30000.0 ,
951- EffectiveCapacityWatts : uint64 (
952- obs .CapacityIncLimit ,
953- ) * uint64 (
954- math .Pow10 (int (obs .CapacityUnitPrefixFactor )),
955- ),
885+ LocationUuid : obs .GeometryUuid .String (),
886+ TimestampUtc : timestamppb .New (obs .ObservationTimestampUtc .Time ),
887+ ValueFraction : float32 (obs .ValueSip ) / 30000.0 ,
888+ EffectiveCapacityWatts : uint64 (obs .CapacityWatts ),
956889 }
957890 }
958891
@@ -1091,14 +1024,10 @@ func (s *DataPlatformDataServiceServerImpl) GetForecastAtTimestamp(
10911024 values := make ([]* pb.GetForecastAtTimestampResponse_Value , len (dbPredictions ))
10921025 for i , value := range dbPredictions {
10931026 values [i ] = & pb.GetForecastAtTimestampResponse_Value {
1094- ValueFraction : float32 (value .P50Sip ) / 30000.0 ,
1095- EffectiveCapacityWatts : uint64 (
1096- value .CapacityIncLimit ,
1097- ) * uint64 (
1098- math .Pow10 (int (value .CapacityUnitPrefixFactor )),
1099- ),
1100- LocationUuid : value .GeometryUuid .String (),
1101- LocationName : value .GeometryName ,
1027+ ValueFraction : float32 (value .P50Sip ) / 30000.0 ,
1028+ EffectiveCapacityWatts : uint64 (value .CapacityWatts ),
1029+ LocationUuid : value .GeometryUuid .String (),
1030+ LocationName : value .GeometryName ,
11021031 Latlng : & pb.LatLng {
11031032 Latitude : value .Latitude ,
11041033 Longitude : value .Longitude ,
@@ -1144,7 +1073,7 @@ func (s *DataPlatformDataServiceServerImpl) GetLocation(
11441073 l .Debug ().
11451074 Str ("dp.source.geometry_uuid" , dbSource .GeometryUuid .String ()).
11461075 Int16 ("dp.source.type_id" , dbSource .SourceTypeID ).
1147- Int64 ("dp.source.capacity" , int64 (dbSource .CapacityIncLimit ) * int64 ( math . Pow10 ( int ( dbSource . CapacityUnitPrefixFactor )) )).
1076+ Int64 ("dp.source.capacity" , int64 (dbSource .CapacityWatts )).
11481077 Str ("dp.source.valid_from_utc" , dbSource .SysPeriod .Lower .Time .String ()).
11491078 Msg ("found source" )
11501079
@@ -1166,12 +1095,8 @@ func (s *DataPlatformDataServiceServerImpl) GetLocation(
11661095 Latitude : dbSource .Latitude ,
11671096 Longitude : dbSource .Longitude ,
11681097 },
1169- EffectiveCapacityWatts : uint64 (
1170- dbSource .CapacityIncLimit ,
1171- ) * uint64 (
1172- math .Pow10 (int (dbSource .CapacityUnitPrefixFactor )),
1173- ),
1174- Metadata : metadata ,
1098+ EffectiveCapacityWatts : uint64 (dbSource .CapacityWatts ),
1099+ Metadata : metadata ,
11751100 }, nil
11761101}
11771102
@@ -1217,28 +1142,17 @@ func (s *DataPlatformDataServiceServerImpl) CreateLocation(
12171142 )
12181143 }
12191144
1220- cp , ex , err := capacityToValueMultiplier (req .EffectiveCapacityWatts )
1221- if err != nil {
1222- l .Err (err ).Msgf ("capacityMwToValueMultiplier(%d)" , req .EffectiveCapacityWatts )
1223-
1224- return nil , status .Error (
1225- codes .InvalidArgument ,
1226- "Invalid capacity. Ensure capacity is non-negative." ,
1227- )
1228- }
1229-
12301145 // Set valid from time to now if not provided
12311146 if req .ValidFromUtc == nil {
12321147 req .ValidFromUtc = timestamppb .New (time .Now ().UTC ().Truncate (time .Minute ))
12331148 }
12341149
12351150 csprms := db.CreateSourceEntryParams {
1236- GeometryUuid : dbLocation .GeometryUuid ,
1237- SourceTypeID : int16 (req .EnergySource ),
1238- Capacity : cp ,
1239- CapacityUnitPrefixFactor : ex ,
1240- Metadata : metadata ,
1241- ValidFromUtc : pgtype.Timestamp {Time : req .ValidFromUtc .AsTime (), Valid : true },
1151+ GeometryUuid : dbLocation .GeometryUuid ,
1152+ SourceTypeID : int16 (req .EnergySource ),
1153+ CapacityWatts : int64 (req .EffectiveCapacityWatts ),
1154+ Metadata : metadata ,
1155+ ValidFromUtc : pgtype.Timestamp {Time : req .ValidFromUtc .AsTime (), Valid : true },
12421156 }
12431157
12441158 dbSource , err := querier .CreateSourceEntry (ctx , csprms )
@@ -1254,7 +1168,7 @@ func (s *DataPlatformDataServiceServerImpl) CreateLocation(
12541168 l .Debug ().
12551169 Str ("dp.source.geometry_uuid" , dbSource .GeometryUuid .String ()).
12561170 Int16 ("dp.source.type_id" , dbSource .SourceTypeID ).
1257- Int64 ("dp.source.capacity" , int64 (dbSource .Capacity ) * int64 ( math . Pow10 ( int ( dbSource . CapacityUnitPrefixFactor )) )).
1171+ Int64 ("dp.source.capacity" , int64 (dbSource .CapacityWatts )).
12581172 Str ("dp.source.valid_from_utc" , dbSource .ValidFromUtc .Time .String ()).
12591173 Msg ("created source entry for location" )
12601174
@@ -1267,13 +1181,9 @@ func (s *DataPlatformDataServiceServerImpl) CreateLocation(
12671181 l .Debug ().Msg ("refreshed sources materialised view" )
12681182
12691183 return & pb.CreateLocationResponse {
1270- LocationUuid : dbLocation .GeometryUuid .String (),
1271- LocationName : dbLocation .GeometryName ,
1272- EffectiveCapacityWatts : uint64 (
1273- dbSource .Capacity ,
1274- ) * uint64 (
1275- math .Pow10 (int (dbSource .CapacityUnitPrefixFactor )),
1276- ),
1184+ LocationUuid : dbLocation .GeometryUuid .String (),
1185+ LocationName : dbLocation .GeometryName ,
1186+ EffectiveCapacityWatts : uint64 (dbSource .CapacityWatts ),
12771187 }, nil
12781188}
12791189
@@ -1319,24 +1229,13 @@ func (s *DataPlatformDataServiceServerImpl) UpdateLocation(
13191229 l .Debug ().
13201230 Str ("dp.source.geometry_uuid" , dbSource .GeometryUuid .String ()).
13211231 Int16 ("dp.source.type_id" , dbSource .SourceTypeID ).
1322- Int64 ("dp.source.capacity" , int64 (dbSource .Capacity ) * int64 ( math . Pow10 ( int ( dbSource . CapacityUnitPrefixFactor )) )).
1232+ Int64 ("dp.source.capacity" , int64 (dbSource .CapacityWatts )).
13231233 Str ("dp.source.valid_from_utc" , dbSource .SysPeriod .Lower .Time .String ()).
13241234 Msg ("fetched source" )
13251235
1326- // Use existing capacity, unless a new capacity is provided
1327- cp := dbSource .Capacity
1328-
1329- ex := dbSource .CapacityUnitPrefixFactor
1236+ capacity := dbSource .CapacityWatts
13301237 if req .NewEffectiveCapacityWatts != nil {
1331- cp , ex , err = capacityToValueMultiplier (req .GetNewEffectiveCapacityWatts ())
1332- if err != nil {
1333- l .Err (err ).Msgf ("capacityMwToValueMultiplier(%d)" , req .NewEffectiveCapacityWatts )
1334-
1335- return nil , status .Error (
1336- codes .InvalidArgument ,
1337- "Invalid capacity. Ensure new capacity is non-negative." ,
1338- )
1339- }
1238+ capacity = int64 (* req .NewEffectiveCapacityWatts )
13401239 }
13411240
13421241 // Use existing metadata, unless new metadata is provided
@@ -1373,13 +1272,12 @@ func (s *DataPlatformDataServiceServerImpl) UpdateLocation(
13731272
13741273 // Update the source history with a new entry
13751274 csprms := db.CreateSourceEntryParams {
1376- GeometryUuid : dbSource .GeometryUuid ,
1377- SourceTypeID : dbSource .SourceTypeID ,
1378- Capacity : cp ,
1379- CapacityUnitPrefixFactor : ex ,
1380- CapacityLimitSip : dbSource .CapacityLimitSip , // TODO: Enable updating this
1381- ValidFromUtc : pgtype.Timestamp {Time : validFrom , Valid : true },
1382- Metadata : metadata ,
1275+ GeometryUuid : dbSource .GeometryUuid ,
1276+ SourceTypeID : dbSource .SourceTypeID ,
1277+ CapacityWatts : capacity ,
1278+ CapacityLimitSip : dbSource .CapacityLimitSip , // TODO: Enable updating this
1279+ ValidFromUtc : pgtype.Timestamp {Time : validFrom , Valid : true },
1280+ Metadata : metadata ,
13831281 }
13841282
13851283 dbNewSource , err := querier .CreateSourceEntry (ctx , csprms )
@@ -1395,7 +1293,7 @@ func (s *DataPlatformDataServiceServerImpl) UpdateLocation(
13951293 l .Debug ().
13961294 Str ("dp.source.geometry_uuid" , dbSource .GeometryUuid .String ()).
13971295 Int16 ("dp.source.type_id" , dbSource .SourceTypeID ).
1398- Int64 ("dp.source.new_capacity" , int64 (dbNewSource .Capacity ) * int64 ( math . Pow10 ( int ( dbNewSource . CapacityUnitPrefixFactor )) )).
1296+ Int64 ("dp.source.new_capacity" , int64 (dbNewSource .CapacityWatts )).
13991297 Str ("dp.source.valid_from_utc" , dbNewSource .ValidFromUtc .Time .String ()).
14001298 Msg ("updated source" )
14011299
@@ -1408,13 +1306,9 @@ func (s *DataPlatformDataServiceServerImpl) UpdateLocation(
14081306 l .Debug ().Msg ("refreshed sources materialised view" )
14091307
14101308 return & pb.UpdateLocationResponse {
1411- LocationUuid : req .LocationUuid ,
1412- LocationName : dbSource .GeometryName ,
1413- EffectiveCapacityWatts : uint64 (
1414- dbNewSource .Capacity ,
1415- ) * uint64 (
1416- math .Pow10 (int (dbNewSource .CapacityUnitPrefixFactor )),
1417- ),
1309+ LocationUuid : req .LocationUuid ,
1310+ LocationName : dbSource .GeometryName ,
1311+ EffectiveCapacityWatts : uint64 (dbNewSource .CapacityWatts ),
14181312 }, nil
14191313}
14201314
@@ -1555,14 +1449,10 @@ func (s *DataPlatformDataServiceServerImpl) GetForecastAsTimeseries(
15551449 }
15561450
15571451 values [i ] = & pb.GetForecastAsTimeseriesResponse_Value {
1558- TargetTimestampUtc : timestamppb .New (value .TargetTimeUtc .Time ),
1559- P50ValueFraction : float32 (value .P50Sip ) / 30000.0 ,
1560- OtherStatisticsFractions : otherStats ,
1561- EffectiveCapacityWatts : uint64 (
1562- value .CapacityIncLimit ,
1563- ) * uint64 (
1564- math .Pow10 (int (value .CapacityUnitPrefixFactor )),
1565- ),
1452+ TargetTimestampUtc : timestamppb .New (value .TargetTimeUtc .Time ),
1453+ P50ValueFraction : float32 (value .P50Sip ) / 30000.0 ,
1454+ OtherStatisticsFractions : otherStats ,
1455+ EffectiveCapacityWatts : uint64 (value .CapacityWatts ),
15661456 InitializationTimestampUtc : timestamppb .New (value .InitTimeUtc .Time ),
15671457 CreatedTimestampUtc : timestamppb .New (value .CreatedAtUtc .Time ),
15681458 }
@@ -1637,14 +1527,10 @@ func (s *DataPlatformDataServiceServerImpl) ListLocations(
16371527 Latitude : loc .Latitude ,
16381528 Longitude : loc .Longitude ,
16391529 },
1640- EffectiveCapacityWatts : uint64 (
1641- loc .Capacity ,
1642- ) * uint64 (
1643- math .Pow10 (int (loc .CapacityUnitPrefixFactor )),
1644- ),
1645- EnergySource : pb .EnergySource (loc .SourceTypeID ),
1646- LocationType : pb .LocationType (loc .GeometryTypeID ),
1647- Metadata : metadata ,
1530+ EffectiveCapacityWatts : uint64 (loc .CapacityWatts ),
1531+ EnergySource : pb .EnergySource (loc .SourceTypeID ),
1532+ LocationType : pb .LocationType (loc .GeometryTypeID ),
1533+ Metadata : metadata ,
16481534 })
16491535 }
16501536 }
@@ -1677,14 +1563,10 @@ func (s *DataPlatformDataServiceServerImpl) ListLocations(
16771563 Latitude : loc .Latitude ,
16781564 Longitude : loc .Longitude ,
16791565 },
1680- EffectiveCapacityWatts : uint64 (
1681- loc .Capacity ,
1682- ) * uint64 (
1683- math .Pow10 (int (loc .CapacityUnitPrefixFactor )),
1684- ),
1685- EnergySource : pb .EnergySource (loc .SourceTypeID ),
1686- LocationType : pb .LocationType (loc .GeometryTypeID ),
1687- Metadata : metadata ,
1566+ EffectiveCapacityWatts : uint64 (loc .CapacityWatts ),
1567+ EnergySource : pb .EnergySource (loc .SourceTypeID ),
1568+ LocationType : pb .LocationType (loc .GeometryTypeID ),
1569+ Metadata : metadata ,
16881570 })
16891571 }
16901572 }
@@ -1716,14 +1598,10 @@ func (s *DataPlatformDataServiceServerImpl) ListLocations(
17161598 Latitude : loc .Latitude ,
17171599 Longitude : loc .Longitude ,
17181600 },
1719- EffectiveCapacityWatts : uint64 (
1720- loc .Capacity ,
1721- ) * uint64 (
1722- math .Pow10 (int (loc .CapacityUnitPrefixFactor )),
1723- ),
1724- EnergySource : pb .EnergySource (loc .SourceTypeID ),
1725- LocationType : pb .LocationType (loc .GeometryTypeID ),
1726- Metadata : metadata ,
1601+ EffectiveCapacityWatts : uint64 (loc .CapacityWatts ),
1602+ EnergySource : pb .EnergySource (loc .SourceTypeID ),
1603+ LocationType : pb .LocationType (loc .GeometryTypeID ),
1604+ Metadata : metadata ,
17271605 })
17281606 }
17291607 }
0 commit comments