@@ -6,7 +6,6 @@ use crate::commodity::{Commodity, CommodityID, CommodityType, DemandMap};
66use crate :: id:: IDCollection ;
77use crate :: region:: RegionID ;
88use crate :: time_slice:: TimeSliceInfo ;
9- use crate :: year:: parse_year_str;
109use anyhow:: { ensure, Result } ;
1110use serde:: Deserialize ;
1211use std:: collections:: { HashMap , HashSet } ;
@@ -21,8 +20,8 @@ struct Demand {
2120 commodity_id : String ,
2221 /// The region of the demand entry
2322 region_id : String ,
24- /// The year(s) of the demand entry
25- years : String ,
23+ /// The year of the demand entry
24+ year : u32 ,
2625 /// Annual demand quantity
2726 demand : f64 ,
2827}
@@ -120,18 +119,29 @@ where
120119 } ) ?;
121120 let region_id = region_ids. get_id_by_str ( & demand. region_id ) ?;
122121
122+ ensure ! (
123+ milestone_years. binary_search( & demand. year) . is_ok( ) ,
124+ "Year {} is not a milestone year. \
125+ Input of non-milestone years is currently not supported.",
126+ demand. year
127+ ) ;
128+
123129 ensure ! (
124130 demand. demand. is_normal( ) && demand. demand > 0.0 ,
125131 "Demand must be a valid number greater than zero"
126132 ) ;
127133
128- for year in parse_year_str ( & demand. years , milestone_years) ? {
129- try_insert (
130- & mut map,
131- ( commodity_id. clone ( ) , region_id. clone ( ) , year) ,
132- demand. demand ,
133- ) ?;
134- }
134+ ensure ! (
135+ map. insert(
136+ ( commodity_id. clone( ) , region_id. clone( ) , demand. year) ,
137+ demand. demand
138+ )
139+ . is_none( ) ,
140+ "Duplicate demand entries (commodity: {}, region: {}, year: {})" ,
141+ commodity_id,
142+ region_id,
143+ demand. year
144+ ) ;
135145 }
136146
137147 // Check that demand data is specified for all combinations of commodity, region and year
@@ -214,13 +224,13 @@ mod tests {
214224 ) {
215225 let demand = [
216226 Demand {
217- years : " 2020" . into ( ) ,
227+ year : 2020 ,
218228 region_id : "GBR" . to_string ( ) ,
219229 commodity_id : "commodity1" . to_string ( ) ,
220230 demand : 10.0 ,
221231 } ,
222232 Demand {
223- years : " 2020" . into ( ) ,
233+ year : 2020 ,
224234 region_id : "USA" . to_string ( ) ,
225235 commodity_id : "commodity1" . to_string ( ) ,
226236 demand : 11.0 ,
@@ -241,13 +251,13 @@ mod tests {
241251 // Bad commodity ID
242252 let demand = [
243253 Demand {
244- years : " 2020" . into ( ) ,
254+ year : 2020 ,
245255 region_id : "GBR" . to_string ( ) ,
246256 commodity_id : "commodity2" . to_string ( ) ,
247257 demand : 10.0 ,
248258 } ,
249259 Demand {
250- years : " 2020" . into ( ) ,
260+ year : 2020 ,
251261 region_id : "USA" . to_string ( ) ,
252262 commodity_id : "commodity1" . to_string ( ) ,
253263 demand : 11.0 ,
@@ -267,13 +277,13 @@ mod tests {
267277 // Bad region ID
268278 let demand = [
269279 Demand {
270- years : " 2020" . into ( ) ,
280+ year : 2020 ,
271281 region_id : "FRA" . to_string ( ) ,
272282 commodity_id : "commodity1" . to_string ( ) ,
273283 demand : 10.0 ,
274284 } ,
275285 Demand {
276- years : " 2020" . into ( ) ,
286+ year : 2020 ,
277287 region_id : "USA" . to_string ( ) ,
278288 commodity_id : "commodity1" . to_string ( ) ,
279289 demand : 11.0 ,
@@ -293,21 +303,22 @@ mod tests {
293303 // Bad year
294304 let demand = [
295305 Demand {
296- years : " 2010" . into ( ) ,
306+ year : 2010 ,
297307 region_id : "GBR" . to_string ( ) ,
298308 commodity_id : "commodity1" . to_string ( ) ,
299309 demand : 10.0 ,
300310 } ,
301311 Demand {
302- years : " 2020" . into ( ) ,
312+ year : 2020 ,
303313 region_id : "USA" . to_string ( ) ,
304314 commodity_id : "commodity1" . to_string ( ) ,
305315 demand : 11.0 ,
306316 } ,
307317 ] ;
308318 assert_error ! (
309319 read_demand_from_iter( demand. into_iter( ) , & commodity_ids, & region_ids, & [ 2020 ] ) ,
310- "Invalid year 2010"
320+ "Year 2010 is not a milestone year. \
321+ Input of non-milestone years is currently not supported."
311322 ) ;
312323 }
313324
@@ -324,7 +335,7 @@ mod tests {
324335 ) {
325336 // Bad demand quantity
326337 let demand = [ Demand {
327- years : " 2020" . into ( ) ,
338+ year : 2020 ,
328339 region_id : "GBR" . to_string ( ) ,
329340 commodity_id : "commodity1" . to_string ( ) ,
330341 demand : quantity,
@@ -343,27 +354,27 @@ mod tests {
343354 // Multiple entries for same commodity and region
344355 let demand = [
345356 Demand {
346- years : " 2020" . into ( ) ,
357+ year : 2020 ,
347358 region_id : "GBR" . to_string ( ) ,
348359 commodity_id : "commodity1" . to_string ( ) ,
349360 demand : 10.0 ,
350361 } ,
351362 Demand {
352- years : " 2020" . into ( ) ,
363+ year : 2020 ,
353364 region_id : "GBR" . to_string ( ) ,
354365 commodity_id : "commodity1" . to_string ( ) ,
355366 demand : 10.0 ,
356367 } ,
357368 Demand {
358- years : " 2020" . into ( ) ,
369+ year : 2020 ,
359370 region_id : "USA" . to_string ( ) ,
360371 commodity_id : "commodity1" . to_string ( ) ,
361372 demand : 11.0 ,
362373 } ,
363374 ] ;
364375 assert_error ! (
365376 read_demand_from_iter( demand. into_iter( ) , & commodity_ids, & region_ids, & [ 2020 ] ) ,
366- "Key (CommodityID( \" commodity1\" ), RegionID( \" GBR\" ), 2020) already exists in the map "
377+ "Duplicate demand entries (commodity: commodity1, region: GBR, year: 2020)"
367378 ) ;
368379 }
369380
@@ -373,35 +384,19 @@ mod tests {
373384 region_ids : HashSet < RegionID > ,
374385 ) {
375386 // Missing entry for a milestone year
376- let demand = [
377- Demand {
378- years : "2020" . into ( ) ,
379- region_id : "GBR" . to_string ( ) ,
380- commodity_id : "commodity1" . to_string ( ) ,
381- demand : 10.0 ,
382- } ,
383- Demand {
384- years : "2020" . into ( ) ,
385- region_id : "USA" . to_string ( ) ,
386- commodity_id : "commodity1" . to_string ( ) ,
387- demand : 11.0 ,
388- } ,
389- Demand {
390- years : "2030" . into ( ) ,
391- region_id : "GBR" . to_string ( ) ,
392- commodity_id : "commodity1" . to_string ( ) ,
393- demand : 10.0 ,
394- } ,
395- ] ;
396- assert_error ! (
397- read_demand_from_iter(
398- demand. into_iter( ) ,
399- & commodity_ids,
400- & region_ids,
401- & [ 2020 , 2030 ]
402- ) ,
403- "Commodity commodity1 is missing demand data for [(RegionID(\" USA\" ), 2030)]"
404- ) ;
387+ let demand = Demand {
388+ year : 2020 ,
389+ region_id : "GBR" . to_string ( ) ,
390+ commodity_id : "commodity1" . to_string ( ) ,
391+ demand : 10.0 ,
392+ } ;
393+ assert ! ( read_demand_from_iter(
394+ std:: iter:: once( demand) ,
395+ & commodity_ids,
396+ & region_ids,
397+ & [ 2020 , 2030 ]
398+ )
399+ . is_err( ) ) ;
405400 }
406401
407402 /// Create an example demand file in dir_path
@@ -410,9 +405,9 @@ mod tests {
410405 let mut file = File :: create ( file_path) . unwrap ( ) ;
411406 writeln ! (
412407 file,
413- "commodity_id,region_id,years ,demand\n \
408+ "commodity_id,region_id,year ,demand\n \
414409 commodity1,GBR,2020,10\n \
415- commodity1,USA,all ,11\n "
410+ commodity1,USA,2020 ,11\n "
416411 )
417412 . unwrap ( ) ;
418413 }
0 commit comments