-
Notifications
You must be signed in to change notification settings - Fork 116
Open
Labels
backend.jdbcInteraction with ixmp_source via JDBCBackend & JPypeInteraction with ixmp_source via JDBCBackend & JPypebugwontfix
Description
Working on iiasa/message_ix#924, I ran into the following:
>>> import ixmp
>>> import message_ix
>>> mp = ixmp.Platform()
>>> s1 = message_ix.Scenario(mp, "model name", "scenario name", "new")
>>> s1.add_horizon([690, 719, 720], firstmodelyear=719)
>>> s1.par("duration_period")
year value unit
0 690 1.0 y
1 719 29.0 y
2 720 1.0 y
>>> s2 = Scenario(mp, "model name", "scenario name", "new")
>>> s2.add_horizon([690, 700, 720], firstmodelyear=700)
>>> s2.par("duration_period")
year value unit
0 690 10.0 y
1 700 10.0 y
2 720 20.0 y
Here the duration of the period 690 is different, but I am writing tests for which it should be the same. No problem: I explicitly set the value and then commit:
>>> dp = "duration_period"
>>> s1.add_par(dp, make_df(dp, year=690, value=10.0, unit="y"))
>>> s1.par("duration_period")
year value unit
0 690 10.0 y
1 719 29.0 y
2 720 1.0 y
>>> s1.add_set("technology", "t") # else commit() raises an exception
>>> s1.commit("")
>>> s1.par("duration_period")
year value unit
0 690 10.0 y
1 719 29.0 y
2 720 1.0 y
To this point, all good. However:
>>> try: # Don't actually solve
... s1.solve()
... except Exception:
... pass
>>> s1.par("duration_period")
year value unit
0 690 29.0 y
1 719 29.0 y
2 720 1.0 y
The value has been mutated from 10 to 29.
What's happening
This code (since it is in the private ixmp_source, I copy it here for clarity) always runs:
// initialize parameter period_duration
Parameter duration_period = getPar("duration_period");
// default duration of a period is 1 (relevant if set years has only one element)
for (int i = 1; i < years.size(); i++) {
int dur = years.get(i) - years.get(i - 1);
duration_period.addElement("" + years.get(i), (double) dur, "y");
}
// assume the first period lasts as long as the second
if (years.size() > 1) {
duration_period.addElement("" + years.get(0), (double) (years.get(1) - years.get(0)), "y");
} else {
duration_period.addElement("" + years.get(0), (double) (1), "y");
}
Thus with ixmp.JDBCBackend it is never possible to explicitly set duration_period
for the first period (entry in the year
set).
Workarounds
- In Fix historic vintages in map_tec_lifetime message_ix#924, I add an additional historical period (
year = 680
) that 'absorbs' this effect, withduration_period(year=680)
never relied on for a specific value. This allows thatduration_period(year=690)
can have a defined value, regardless of other entries in theyear
set.
Since ixmp_source is unmaintained, this bug is essentially 'wontfix', along with some other sub-issues of iiasa/message_ix#254. I note it here mainly for clarity. We can however do the following:
- In implementing the new IXMP4Backend, not reproduce this behaviour.
- In message_ix, add a warning tries to set such a value, to the effect that:
- if the user is using JDBCBackend, the value will be overwritten.
- if the user is using IXMP4Backend, it will succeed, but the code may not be portable to JDBCBackend.
Metadata
Metadata
Assignees
Labels
backend.jdbcInteraction with ixmp_source via JDBCBackend & JPypeInteraction with ixmp_source via JDBCBackend & JPypebugwontfix