hmb HF Staff commited on
Commit
38c1b0d
·
verified ·
1 Parent(s): 121dc94

Upload folder using huggingface_hub

Browse files
Files changed (1) hide show
  1. app.py +144 -8
app.py CHANGED
@@ -77,6 +77,98 @@ POLICY_EVENTS = {
77
  {"year": 2012, "text": "Carbon farming legislation", "url": "https://en.wikipedia.org/wiki/Climate_change_in_Australia"},
78
  {"year": 2022, "text": "Nature Repair Market Act", "url": "https://en.wikipedia.org/wiki/Climate_change_in_Australia"},
79
  ],
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
80
  }
81
 
82
 
@@ -192,6 +284,7 @@ def get_forest_data(country: str) -> dict:
192
  forest = _fetch_wb(code, "AG.LND.FRST.ZS")
193
  governance = _fetch_wb(code, "RL.EST")
194
  policies = POLICY_EVENTS.get(country, [])
 
195
 
196
  summary = {}
197
  if forest:
@@ -212,6 +305,7 @@ def get_forest_data(country: str) -> dict:
212
  "forest": forest,
213
  "governance": governance,
214
  "policies": policies,
 
215
  "summary": summary,
216
  }
217
 
@@ -238,6 +332,8 @@ def explain_spike(country: str, year: int) -> dict:
238
 
239
  policies = POLICY_EVENTS.get(country, [])
240
  nearby_policies = [p for p in policies if abs(p["year"] - year) <= 3]
 
 
241
 
242
  window = [f for f in forest if abs(f["year"] - year) <= 5]
243
  window.sort(key=lambda x: x["year"])
@@ -288,6 +384,7 @@ def explain_spike(country: str, year: int) -> dict:
288
  "rate_5yr_before": rate_before,
289
  "rate_5yr_after": rate_after,
290
  "nearby_policies": nearby_policies,
 
291
  "context": context,
292
  "window": window,
293
  }
@@ -1143,9 +1240,14 @@ button.action:active {{
1143
  <canvas id="chart"></canvas>
1144
  </div>
1145
  <div class="figure-caption">
1146
- <span class="smallcaps">Note —</span> Forest area as percentage of total land. Oxblood markers denote known policy events
1147
- (hover the line to read). Rule of Law index plotted on secondary axis where available.
1148
- Click any data point for a detailed dossier.
 
 
 
 
 
1149
  </div>
1150
  </section>
1151
 
@@ -1377,14 +1479,14 @@ function renderChart(data, compareData) {{
1377
 
1378
  const annotations = {{}};
1379
  (data.policies || []).forEach((p, i) => {{
1380
- annotations['line' + i] = {{
1381
  type: 'line',
1382
  xMin: p.year, xMax: p.year,
1383
- borderColor: 'rgba(139, 42, 31, 0.25)',
1384
  borderWidth: 1,
1385
  borderDash: [3, 4],
1386
  }};
1387
- annotations['label' + i] = {{
1388
  type: 'point',
1389
  xValue: p.year,
1390
  yValue: data.forest.find(f => f.year === p.year)?.value || data.forest[0].value,
@@ -1395,6 +1497,26 @@ function renderChart(data, compareData) {{
1395
  hoverRadius: 8,
1396
  }};
1397
  }});
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1398
 
1399
  chart = new Chart(ctx, {{
1400
  type: 'line',
@@ -1442,8 +1564,12 @@ function renderChart(data, compareData) {{
1442
  afterBody: function(items) {{
1443
  if (!items.length) return;
1444
  const year = Math.round(items[0].parsed.x);
 
1445
  const policy = (data.policies || []).find(p => p.year === year);
1446
- return policy ? ['', ' + policy.text] : '';
 
 
 
1447
  }}
1448
  }}
1449
  }}
@@ -1637,7 +1763,7 @@ async function handlePointClick(year) {{
1637
 
1638
  if (result.nearby_policies && result.nearby_policies.length) {{
1639
  html += `<div class="nearby-block">
1640
- <div class="k">Nearby policy events · ±3 years</div>`;
1641
  result.nearby_policies.forEach(p => {{
1642
  const pLink = p.url ? ` <a href="${{p.url}}" target="_blank" style="color:var(--ink-mute);font-size:11px">↗</a>` : '';
1643
  html += `<div class="nearby-item"><span class="yr">${{p.year}}</span><span>${{p.text}}${{pLink}}</span></div>`;
@@ -1645,6 +1771,16 @@ async function handlePointClick(year) {{
1645
  html += `</div>`;
1646
  }}
1647
 
 
 
 
 
 
 
 
 
 
 
1648
  contentEl.innerHTML = html;
1649
  }}
1650
 
 
77
  {"year": 2012, "text": "Carbon farming legislation", "url": "https://en.wikipedia.org/wiki/Climate_change_in_Australia"},
78
  {"year": 2022, "text": "Nature Repair Market Act", "url": "https://en.wikipedia.org/wiki/Climate_change_in_Australia"},
79
  ],
80
+ "United States": [
81
+ {"year": 2001, "text": "Healthy Forests Initiative", "url": "https://en.wikipedia.org/wiki/Healthy_Forests_Initiative"},
82
+ {"year": 2008, "text": "Lacey Act amended to ban illegal timber", "url": "https://en.wikipedia.org/wiki/Lacey_Act_of_1900"},
83
+ {"year": 2022, "text": "Inflation Reduction Act — $5B for forests", "url": "https://en.wikipedia.org/wiki/Inflation_Reduction_Act"},
84
+ ],
85
+ "Russia": [
86
+ {"year": 1997, "text": "First Russian Forest Code", "url": "https://en.wikipedia.org/wiki/Forestry_in_Russia"},
87
+ {"year": 2006, "text": "New Forest Code — privatisation of management", "url": "https://en.wikipedia.org/wiki/Forestry_in_Russia"},
88
+ {"year": 2020, "text": "Forest protection reform after record fires", "url": "https://en.wikipedia.org/wiki/Forestry_in_Russia"},
89
+ ],
90
+ "Bolivia": [
91
+ {"year": 1996, "text": "Forestry Law 1700 enacted", "url": "https://en.wikipedia.org/wiki/Deforestation"},
92
+ {"year": 2012, "text": "Mother Earth Law", "url": "https://en.wikipedia.org/wiki/Law_of_the_Rights_of_Mother_Earth"},
93
+ ],
94
+ "Peru": [
95
+ {"year": 2011, "text": "Forest and Wildlife Law 29763", "url": "https://en.wikipedia.org/wiki/Deforestation_in_Peru"},
96
+ {"year": 2014, "text": "Joint Declaration with Norway & Germany", "url": "https://en.wikipedia.org/wiki/Deforestation_in_Peru"},
97
+ ],
98
+ "Paraguay": [
99
+ {"year": 2004, "text": "Zero Deforestation Law (East region)", "url": "https://en.wikipedia.org/wiki/Deforestation"},
100
+ ],
101
+ "Madagascar": [
102
+ {"year": 2003, "text": "Durban Vision — triple protected areas", "url": "https://en.wikipedia.org/wiki/Environment_of_Madagascar"},
103
+ {"year": 2015, "text": "National REDD+ strategy", "url": "https://en.wikipedia.org/wiki/REDD_and_REDD%2B"},
104
+ ],
105
+ "Cameroon": [
106
+ {"year": 1994, "text": "Forest Law 94/01 enacted", "url": "https://en.wikipedia.org/wiki/Forestry_in_Cameroon"},
107
+ {"year": 2010, "text": "CAFI partnership initiated", "url": "https://en.wikipedia.org/wiki/Forestry_in_Cameroon"},
108
+ ],
109
+ "Nigeria": [
110
+ {"year": 1999, "text": "Federal Forestry Policy", "url": "https://en.wikipedia.org/wiki/Forestry_in_Nigeria"},
111
+ {"year": 2017, "text": "Great Green Wall commitment", "url": "https://en.wikipedia.org/wiki/Great_Green_Wall_(Africa)"},
112
+ ],
113
+ "Myanmar": [
114
+ {"year": 1992, "text": "Forest Law passed", "url": "https://en.wikipedia.org/wiki/Deforestation"},
115
+ {"year": 2014, "text": "Raw log export ban", "url": "https://en.wikipedia.org/wiki/Deforestation"},
116
+ ],
117
+ "Tanzania": [
118
+ {"year": 2002, "text": "Forest Act enacted", "url": "https://en.wikipedia.org/wiki/Environmental_issues_in_Tanzania"},
119
+ {"year": 2015, "text": "National REDD+ strategy", "url": "https://en.wikipedia.org/wiki/REDD_and_REDD%2B"},
120
+ ],
121
+ }
122
+
123
+
124
+ CLIMATE_EVENTS = {
125
+ "Australia": [
126
+ {"year": 2002, "text": "Millennium Drought intensifies", "url": "https://en.wikipedia.org/wiki/2000s_Australian_drought"},
127
+ {"year": 2009, "text": "Black Saturday bushfires (430k ha)", "url": "https://en.wikipedia.org/wiki/Black_Saturday_bushfires"},
128
+ {"year": 2020, "text": "Black Summer fires (18.6M ha)", "url": "https://en.wikipedia.org/wiki/2019%E2%80%9320_Australian_bushfire_season"},
129
+ ],
130
+ "Indonesia": [
131
+ {"year": 1997, "text": "Southeast Asian haze from peat fires", "url": "https://en.wikipedia.org/wiki/1997_Southeast_Asian_haze"},
132
+ {"year": 2015, "text": "Peat fires burn 2.6M ha", "url": "https://en.wikipedia.org/wiki/2015_Southeast_Asian_haze"},
133
+ {"year": 2019, "text": "Major fire season, 1.6M ha burned", "url": "https://en.wikipedia.org/wiki/2019_Southeast_Asian_haze"},
134
+ ],
135
+ "Brazil": [
136
+ {"year": 2019, "text": "Amazon fires spike 84%", "url": "https://en.wikipedia.org/wiki/2019_Amazon_rainforest_wildfires"},
137
+ {"year": 2020, "text": "Pantanal wetland fires (4M ha)", "url": "https://en.wikipedia.org/wiki/2020_Pantanal_wildfires"},
138
+ ],
139
+ "Canada": [
140
+ {"year": 2005, "text": "Mountain pine beetle peak (18M ha)", "url": "https://en.wikipedia.org/wiki/Mountain_pine_beetle"},
141
+ {"year": 2016, "text": "Fort McMurray fire", "url": "https://en.wikipedia.org/wiki/2016_Fort_McMurray_wildfire"},
142
+ {"year": 2023, "text": "Record fire season (18.5M ha)", "url": "https://en.wikipedia.org/wiki/2023_Canadian_wildfires"},
143
+ ],
144
+ "Russia": [
145
+ {"year": 2010, "text": "Moscow smog — wildfires kill 56k", "url": "https://en.wikipedia.org/wiki/2010_Russian_wildfires"},
146
+ {"year": 2019, "text": "Siberian fires (4M ha)", "url": "https://en.wikipedia.org/wiki/2019_Siberia_wildfires"},
147
+ {"year": 2021, "text": "Record Siberian fires (18.8M ha)", "url": "https://en.wikipedia.org/wiki/2021_Russia_wildfires"},
148
+ ],
149
+ "China": [
150
+ {"year": 1998, "text": "Yangtze floods kill 4,000+", "url": "https://en.wikipedia.org/wiki/1998_China_floods"},
151
+ ],
152
+ "United States": [
153
+ {"year": 2018, "text": "Camp Fire destroys Paradise", "url": "https://en.wikipedia.org/wiki/Camp_Fire_(2018)"},
154
+ {"year": 2020, "text": "Record fire season (4.2M acres)", "url": "https://en.wikipedia.org/wiki/2020_California_wildfires"},
155
+ {"year": 2023, "text": "Maui fires & Canadian smoke crisis", "url": "https://en.wikipedia.org/wiki/2023_Hawaii_wildfires"},
156
+ ],
157
+ "Colombia": [
158
+ {"year": 2017, "text": "Deforestation spikes in post-FARC areas", "url": "https://en.wikipedia.org/wiki/Deforestation_in_Colombia"},
159
+ ],
160
+ "Mexico": [
161
+ {"year": 2011, "text": "Worst drought in 70 years", "url": "https://en.wikipedia.org/wiki/Climate_change_in_Mexico"},
162
+ ],
163
+ "Bolivia": [
164
+ {"year": 2019, "text": "Chiquitano fires burn 2.3M ha", "url": "https://en.wikipedia.org/wiki/2019_Amazon_rainforest_wildfires"},
165
+ ],
166
+ "Madagascar": [
167
+ {"year": 2020, "text": "Severe drought in southern regions", "url": "https://en.wikipedia.org/wiki/Environment_of_Madagascar"},
168
+ ],
169
+ "DR Congo": [
170
+ {"year": 2003, "text": "Second Congo War ends", "url": "https://en.wikipedia.org/wiki/Second_Congo_War"},
171
+ ],
172
  }
173
 
174
 
 
284
  forest = _fetch_wb(code, "AG.LND.FRST.ZS")
285
  governance = _fetch_wb(code, "RL.EST")
286
  policies = POLICY_EVENTS.get(country, [])
287
+ climate = CLIMATE_EVENTS.get(country, [])
288
 
289
  summary = {}
290
  if forest:
 
305
  "forest": forest,
306
  "governance": governance,
307
  "policies": policies,
308
+ "climate": climate,
309
  "summary": summary,
310
  }
311
 
 
332
 
333
  policies = POLICY_EVENTS.get(country, [])
334
  nearby_policies = [p for p in policies if abs(p["year"] - year) <= 3]
335
+ climate = CLIMATE_EVENTS.get(country, [])
336
+ nearby_climate = [c for c in climate if abs(c["year"] - year) <= 3]
337
 
338
  window = [f for f in forest if abs(f["year"] - year) <= 5]
339
  window.sort(key=lambda x: x["year"])
 
384
  "rate_5yr_before": rate_before,
385
  "rate_5yr_after": rate_after,
386
  "nearby_policies": nearby_policies,
387
+ "nearby_climate": nearby_climate,
388
  "context": context,
389
  "window": window,
390
  }
 
1240
  <canvas id="chart"></canvas>
1241
  </div>
1242
  <div class="figure-caption">
1243
+ <span class="smallcaps">Legend —</span>
1244
+ <span style="display:inline-block;width:9px;height:9px;border-radius:50%;background:var(--oxblood);vertical-align:middle;margin-right:4px"></span> policy event
1245
+ &nbsp;·&nbsp;
1246
+ <span style="display:inline-block;width:0;height:0;border-left:6px solid transparent;border-right:6px solid transparent;border-bottom:10px solid var(--amber);vertical-align:middle;margin-right:4px"></span> climate / disaster event
1247
+ &nbsp;·&nbsp;
1248
+ <span style="display:inline-block;width:12px;height:2px;background:var(--amber);vertical-align:middle;margin-right:4px"></span> rule of law
1249
+ <br>
1250
+ Hover the line to read an event. Click any year for a full dossier.
1251
  </div>
1252
  </section>
1253
 
 
1479
 
1480
  const annotations = {{}};
1481
  (data.policies || []).forEach((p, i) => {{
1482
+ annotations['pline' + i] = {{
1483
  type: 'line',
1484
  xMin: p.year, xMax: p.year,
1485
+ borderColor: 'rgba(139, 42, 31, 0.22)',
1486
  borderWidth: 1,
1487
  borderDash: [3, 4],
1488
  }};
1489
+ annotations['ppoint' + i] = {{
1490
  type: 'point',
1491
  xValue: p.year,
1492
  yValue: data.forest.find(f => f.year === p.year)?.value || data.forest[0].value,
 
1497
  hoverRadius: 8,
1498
  }};
1499
  }});
1500
+ (data.climate || []).forEach((c, i) => {{
1501
+ annotations['cline' + i] = {{
1502
+ type: 'line',
1503
+ xMin: c.year, xMax: c.year,
1504
+ borderColor: 'rgba(168, 115, 42, 0.22)',
1505
+ borderWidth: 1,
1506
+ borderDash: [1, 3],
1507
+ }};
1508
+ annotations['cpoint' + i] = {{
1509
+ type: 'point',
1510
+ xValue: c.year,
1511
+ yValue: data.forest.find(f => f.year === c.year)?.value || data.forest[0].value,
1512
+ radius: 6,
1513
+ pointStyle: 'triangle',
1514
+ backgroundColor: AMBER,
1515
+ borderColor: PAPER_TINT,
1516
+ borderWidth: 2,
1517
+ hoverRadius: 9,
1518
+ }};
1519
+ }});
1520
 
1521
  chart = new Chart(ctx, {{
1522
  type: 'line',
 
1564
  afterBody: function(items) {{
1565
  if (!items.length) return;
1566
  const year = Math.round(items[0].parsed.x);
1567
+ const lines = [];
1568
  const policy = (data.policies || []).find(p => p.year === year);
1569
+ const climateEv = (data.climate || []).find(c => c.year === year);
1570
+ if (policy) lines.push('', '§ Policy — ' + policy.text);
1571
+ if (climateEv) lines.push('', '△ Climate — ' + climateEv.text);
1572
+ return lines;
1573
  }}
1574
  }}
1575
  }}
 
1763
 
1764
  if (result.nearby_policies && result.nearby_policies.length) {{
1765
  html += `<div class="nearby-block">
1766
+ <div class="k">§ Nearby policy events · ±3 years</div>`;
1767
  result.nearby_policies.forEach(p => {{
1768
  const pLink = p.url ? ` <a href="${{p.url}}" target="_blank" style="color:var(--ink-mute);font-size:11px">↗</a>` : '';
1769
  html += `<div class="nearby-item"><span class="yr">${{p.year}}</span><span>${{p.text}}${{pLink}}</span></div>`;
 
1771
  html += `</div>`;
1772
  }}
1773
 
1774
+ if (result.nearby_climate && result.nearby_climate.length) {{
1775
+ html += `<div class="nearby-block">
1776
+ <div class="k" style="color:var(--amber-deep)">△ Nearby climate events · ±3 years</div>`;
1777
+ result.nearby_climate.forEach(c => {{
1778
+ const cLink = c.url ? ` <a href="${{c.url}}" target="_blank" style="color:var(--ink-mute);font-size:11px">↗</a>` : '';
1779
+ html += `<div class="nearby-item"><span class="yr" style="color:var(--amber-deep)">${{c.year}}</span><span>${{c.text}}${{cLink}}</span></div>`;
1780
+ }});
1781
+ html += `</div>`;
1782
+ }}
1783
+
1784
  contentEl.innerHTML = html;
1785
  }}
1786