Rahka commited on
Commit
baa7cce
1 Parent(s): 608f80c

first draft

Browse files
.gitattributes CHANGED
@@ -33,3 +33,4 @@ saved_model/**/* filter=lfs diff=lfs merge=lfs -text
33
  *.zip filter=lfs diff=lfs merge=lfs -text
34
  *.zst filter=lfs diff=lfs merge=lfs -text
35
  *tfevents* filter=lfs diff=lfs merge=lfs -text
 
 
33
  *.zip filter=lfs diff=lfs merge=lfs -text
34
  *.zst filter=lfs diff=lfs merge=lfs -text
35
  *tfevents* filter=lfs diff=lfs merge=lfs -text
36
+ static/images/banner.jpg filter=lfs diff=lfs merge=lfs -text
Dockerfile ADDED
@@ -0,0 +1,35 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ FROM python:3.10
2
+
3
+ WORKDIR /app
4
+
5
+ ENV POETRY_VERSION=1.6.1
6
+ RUN pip install "poetry==$POETRY_VERSION"
7
+
8
+ RUN poetry config virtualenvs.create false
9
+
10
+ COPY ./poetry.lock /app/poetry.lock
11
+ COPY ./pyproject.toml /app/pyproject.toml
12
+ RUN poetry install --no-dev
13
+
14
+ # User
15
+ RUN useradd -m -u 1000 user
16
+ USER user
17
+ ENV HOME /home/user
18
+ ENV PATH $HOME/.local/bin:$PATH
19
+
20
+ WORKDIR $HOME
21
+ RUN mkdir app
22
+ WORKDIR $HOME/app
23
+ COPY . $HOME/app
24
+
25
+ # RUN --mount=type=secret,id=QDRANT_DATABASE__API_KEY,mode=0444,required=true
26
+ # RUN --mount=type=secret,id=QDRANT_DATABASE__URL,mode=0444,required=true
27
+ # RUN --mount=type=secret,id=LLM_PROVIDER__MODEL,mode=0444,required=true
28
+ # RUN --mount=type=secret,id=LLM_PROVIDER__API_KEY,mode=0444,required=true
29
+
30
+ EXPOSE 8501
31
+ CMD streamlit run src/app/app.py \
32
+ --server.headless true \
33
+ --server.enableCORS false \
34
+ --server.enableXsrfProtection false \
35
+ --server.fileWatcherType none
README.md CHANGED
@@ -1,8 +1,8 @@
1
  ---
2
- title: Test Space Negotiate Ai
3
- emoji: 🌍
4
- colorFrom: indigo
5
- colorTo: indigo
6
  sdk: docker
7
  pinned: false
8
  ---
 
1
  ---
2
+ title: Giz Test Space
3
+ emoji: 📉
4
+ colorFrom: blue
5
+ colorTo: gray
6
  sdk: docker
7
  pinned: false
8
  ---
data/example_prompts/example_prompts_inc.json ADDED
@@ -0,0 +1,14 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ [
2
+ {
3
+ "id": 1,
4
+ "question": "What is Malysia's position on chemicals and polymers of concern?"
5
+ },
6
+ {
7
+ "id": 2,
8
+ "question": "Compare Indias and New Zealands position on just transition."
9
+ },
10
+ {
11
+ "id": 3,
12
+ "question": "Do the selected countries prefer a top-down instrument?"
13
+ }
14
+ ]
data/example_prompts/example_prompts_knowledge_hub.json ADDED
@@ -0,0 +1,14 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ [
2
+ {
3
+ "id": 1,
4
+ "question": "What can be done to improve tracking and management of non-packaging plastic waste to support better environmental policies?"
5
+ },
6
+ {
7
+ "id": 2,
8
+ "question": "How can Pacific Island policy frameworks be improved to address the full life cycle impacts of plastics on the environment and public health?"
9
+ },
10
+ {
11
+ "id": 3,
12
+ "question": "Are industry-promoted solutions like recycling and burning plastic effective in addressing the plastics crisis?"
13
+ }
14
+ ]
data/taxonomies/authors_filter.json ADDED
@@ -0,0 +1,518 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "Members - Countries": [
3
+ "Algeria",
4
+ "Angola",
5
+ "Antigua And Barbuda",
6
+ "Argentina",
7
+ "Armenia",
8
+ "Australia",
9
+ "Azerbaijan",
10
+ "Bahrain",
11
+ "Bangladesh",
12
+ "Barbados",
13
+ "Benin",
14
+ "Bosnia And Herzegovina",
15
+ "Brazil",
16
+ "Burkina Faso",
17
+ "Cambodia",
18
+ "Cameroon",
19
+ "Canada",
20
+ "Chile",
21
+ "China",
22
+ "Colombia",
23
+ "Comoros",
24
+ "Cook Islands",
25
+ "Costa Rica",
26
+ "Cuba",
27
+ "Cote DIvoire",
28
+ "Democratic Republic Of The Congo",
29
+ "Dominican Republic",
30
+ "Ecuador",
31
+ "Egypt",
32
+ "El Salvador",
33
+ "Equatorial Guinea",
34
+ "Eritrea",
35
+ "Eswatini",
36
+ "Ethiopia",
37
+ "Fiji",
38
+ "France",
39
+ "Gabon",
40
+ "Gambia",
41
+ "Georgia",
42
+ "Germany",
43
+ "Ghana",
44
+ "Grenada",
45
+ "Guatemala",
46
+ "Guinea",
47
+ "Guinea Bissau",
48
+ "Honduras",
49
+ "Iceland",
50
+ "India",
51
+ "Indonesia",
52
+ "Iraq",
53
+ "Islamic Republic Of Iran",
54
+ "Israel",
55
+ "Italy",
56
+ "Jamaica",
57
+ "Japan",
58
+ "Jordan",
59
+ "Kazakhstan",
60
+ "Kenya",
61
+ "Kiribati",
62
+ "Kuwait",
63
+ "Libya",
64
+ "Madagascar",
65
+ "Malawi",
66
+ "Malaysia",
67
+ "Maldives",
68
+ "Mali",
69
+ "Marshall Islands",
70
+ "Mauritius",
71
+ "Mexico",
72
+ "Micronesia",
73
+ "Moldova",
74
+ "Monaco",
75
+ "Mongolia",
76
+ "Montenegro",
77
+ "Morocco",
78
+ "Nauru",
79
+ "Nepal",
80
+ "New Zealand",
81
+ "Niger",
82
+ "Nigeria",
83
+ "North Macedonia",
84
+ "Norway",
85
+ "Oman",
86
+ "Pakistan",
87
+ "Palau",
88
+ "Panama",
89
+ "Papua New Guinea",
90
+ "Paraguay",
91
+ "Peru",
92
+ "Philippines",
93
+ "Qatar",
94
+ "Republic Of Congo",
95
+ "Republic Of Korea",
96
+ "Republic Of Moldova",
97
+ "Romania",
98
+ "Russian Federation",
99
+ "Rwanda",
100
+ "Samoa",
101
+ "Saudi Arabia",
102
+ "Senegal",
103
+ "Seychelles",
104
+ "Sierra Leone",
105
+ "Singapore",
106
+ "Solomon Islands",
107
+ "Somalia",
108
+ "South Africa",
109
+ "Sri Lanka",
110
+ "State Of Palestine",
111
+ "Switzerland",
112
+ "Syrian Arab Republic",
113
+ "Thailand",
114
+ "Timor-Leste",
115
+ "Togo",
116
+ "Tonga",
117
+ "Trinidad And Tobago",
118
+ "Tunisia",
119
+ "Turkey",
120
+ "Tuvalu",
121
+ "Uganda",
122
+ "Ukraine",
123
+ "United Arab Emirates",
124
+ "United Kingdom Of Great Britain And Northern Ireland",
125
+ "United Republic Of Tanzania",
126
+ "United States Of America",
127
+ "Uruguay",
128
+ "Venezuela",
129
+ "Vietnam",
130
+ "Yemen",
131
+ "Zambia",
132
+ "Zimbabwe"
133
+ ],
134
+ "Members - International and Regional State Associations": [
135
+ "Asia-Pacific States",
136
+ "European Union (EU) And Its 27 Member States",
137
+ "Federated States Of Micronesia",
138
+ "Gulf Cooperation Council",
139
+ "High Ambition Coalition",
140
+ "Latin American And Caribbean Group (GRULAC)",
141
+ "Like Minded Countries",
142
+ "Pacific Small Island Developing States (PSIDS)",
143
+ "Alliance Of Small Island States (AOSIS)",
144
+ "The Federated States Of Micronesia",
145
+ "The Group Of African States",
146
+ "Western European And Other States",
147
+ "Coordinating Body on the Seas of East Asia (COBSEA)"
148
+ ],
149
+ "Intergovernmental Negotiation Committee": [
150
+ "Executive Secretary Of The INC",
151
+ "Intergovernmental Negotiation Committee"
152
+ ],
153
+ "Observers and Other Participants": [
154
+ "10YFP Secretariat (One Planet Network)",
155
+ "ABIPLAST - Brazilian Association Of The Plastic Industry",
156
+ "ACTS Organization",
157
+ "ASTM International (ASTM)",
158
+ "AWTAD Anti-Corruption Organization",
159
+ "Aaina",
160
+ "Action Et Education Pour Tous (AEPT)",
161
+ "Action On Smoking And Health (ASH)",
162
+ "Africa Climate And Environment Foundation (ACEF)",
163
+ "African Alliance For Health Research Economic Development",
164
+ "African Environmental Network",
165
+ "African Petroleum Producers\u2019 Organization (APPO)",
166
+ "Aguaclara",
167
+ "Alianza Basura Cero",
168
+ "Alianza Latinoamericana De Asociaciones De La Industria De Alimentos Y Bebidas (ALAIAB)",
169
+ "All-China Environment Federation",
170
+ "Alliance Panafricaine Multi-Acteurs Sur La Pollution Plastique",
171
+ "Alliance Pour Le Controle Du Tabac En Afrique (ACTA)",
172
+ "American Chemistry Council",
173
+ "American Fuel and Petrochemical Manufacturers (AFPM)",
174
+ "And Colectivo Jaguares De Nuestra Madre Tierra",
175
+ "Aotearoa Plastic Pollution Alliance (APPA)",
176
+ "Arctic Monitoring And Assessment Programme (AMAP)",
177
+ "Armenian Women For Health And Healthy Environment",
178
+ "Arnika",
179
+ "Asia Indigenous Peoples Pact And Indigenous Peoples",
180
+ "Asian Marine Conservation Association",
181
+ "Asociaci\u00f3n Ecol\u00f3gica Santo Tom\u00e1s",
182
+ "Asociaci\u00f3n Sustentar",
183
+ "Association For Promoting Sustainability In Campuses And Communities (APSCC)",
184
+ "Association For Rural Area Social Modification, Improvement And Nestling (ARASMIN)",
185
+ "Association For Supporting The SDGs For The United Nations",
186
+ "Association Institute Of Total Environment (INTEV)",
187
+ "Association Nationale Du Civisme",
188
+ "Association Of Leadership You-Lean",
189
+ "Association Of Plastic Recyclers",
190
+ "Association Of Solidarity Through Humanitarian Imperative Actions International (ASHIA)",
191
+ "Association Pour L'Integration Et La Developpement Durable Au Burundi",
192
+ "Australian Packaging Covenant Organisation (APCO)",
193
+ "Azul",
194
+ "BAN Toxics",
195
+ "BVRio",
196
+ "Barranquilla + 20",
197
+ "Basel Action Network (BAN)",
198
+ "Beijing Greenovation Institute For Public Welfare Development (GHub)",
199
+ "Brazilian Chemical Industry Association",
200
+ "Break Free From Plastic",
201
+ "Breathe Free Detroit",
202
+ "Bridgers Association Cameroon",
203
+ "Bureau Of International Recycling",
204
+ "Business And Industry Major Group Presented By World Business Council For Sustainable Development",
205
+ "Business Coalition For A Global Plastics Treaty Convened By The Ellen MacArthur Foundation And WWF, In Collaboration With Aligned Businesses And Financial Institutions, And Supported By NGO Partners",
206
+ "CAIRPLAS, C\u00e1mara Argentina De La Industria De Reciclados Plasticos",
207
+ "CDP",
208
+ "CEMPRE Colombia \u2013 Compromiso Empresarial Para El Reciclaje",
209
+ "CESTA",
210
+ "Carrizo Comecrudo Tribe",
211
+ "Center For Biological Diversity",
212
+ "Center For Coalfield Justice",
213
+ "Center For International Environmental Law (CIEL)",
214
+ "Center For International Law And Governance",
215
+ "Center For Islamic Studies Of Universitas Nasional, Jakarta",
216
+ "Center For Oceanic Awareness, Research, And Education (COARE)",
217
+ "Center For Public Health And Environmental Development (CEPHED)",
218
+ "Centre De Recherche Et D\u2019Education Pour Le D\u00e9veloppement (CREPD)",
219
+ "Centre D\u2019Accompagnement Des Alternatives Locales De D\u00e9veloppement (Caald)",
220
+ "Centre For Environmental Justice",
221
+ "Centre For Human Rights And Climate Change Research",
222
+ "Centre For Science And Environment (CSE)",
223
+ "Centre International De Droit Compar\u00e9 De L\u2019environnement",
224
+ "Centre International De Droit Compar\u00e9 De L\u2019environnement",
225
+ "Chemical And Allied Industries\u2019 Association (CAIA)",
226
+ "Chia Funkuin Foundation",
227
+ "Children And Youth Major Group (CYMG)",
228
+ "Children\u2019s Environmental Health Foundation",
229
+ "China Biodiversity Conservation And Green Development Foundation (CBCGDF)",
230
+ "Circular Economy For Flexible Packaging In Europe Initiative (CEFLEX)",
231
+ "Citeo",
232
+ "Citizen Consumer And Civic Action Group (CAG)",
233
+ "Civil Society And Rights Holder Coalition",
234
+ "Civil Society Organizations In Africa",
235
+ "Civil Society Organizations In Asia Pacific",
236
+ "Civil Society Organizations In Latin America",
237
+ "Co-habiter",
238
+ "Comision Centro Americana",
239
+ "Comit\u00e9 National Contre Le Tabagisme",
240
+ "Community Action Against Plastic Waste (CAPws)",
241
+ "Congregations Of St Joseph",
242
+ "Consciente Colectivo",
243
+ "Consumer Goods Forum",
244
+ "Consumers International",
245
+ "Contact Group 1",
246
+ "Contact Group 2",
247
+ "Convention On Biological Diversity (CBD)",
248
+ "Corporate Accountability",
249
+ "Council For Scientific And Industrial Research",
250
+ "C\u00e1mara De La Industria Qu\u00edmica Y Petroqu\u00edmica (CIQyP\u00ae), Miembro Del Concejo Internacional De Asociaciones Qu\u00edmicas (ICCA) Y EURECA",
251
+ "Danimer Scientific",
252
+ "EDANA And INDA",
253
+ "EPS Branchen-en Del Af Plastindustrien (Denmark)",
254
+ "EPS Industry Alliance",
255
+ "EURECA",
256
+ "Earth Day",
257
+ "Earth Law Center",
258
+ "Ecoplas",
259
+ "Ecoproject Partnership",
260
+ "Ellen MacArthur Foundation",
261
+ "Endocrine Society",
262
+ "Engineers Australia",
263
+ "Entidad Especializada En Pl\u00e1sticos Y Medio Ambiente Para Una Econom\u00eda Circular (ECOPLAS)",
264
+ "Entidades Unidas Reafirmando La Econom\u00eda Circular En Argentina (EURECA)",
265
+ "Environmental And Social Development Organization (ESDO)",
266
+ "Environmental Coalition On Standards (ECOS)",
267
+ "Environmental Development Association (FASEEL)",
268
+ "Environmental Investigation Agency",
269
+ "European Bioplastics (EUBP)",
270
+ "European Manufacturers Of EPS",
271
+ "European Manufacturers Of Expanded Polystyrene (EUMEPS)",
272
+ "Expanded Polystyrene Australia",
273
+ "Fauna and Flora International",
274
+ "Fauna and Flora International And Zoological Society Of London (ZSL)",
275
+ "Fenceline Watch",
276
+ "First Modern Agro Tools Common Initiative Group ( FI.MO.AT.C.I.G)",
277
+ "Fondation De La Mer",
278
+ "Food And Agriculture Organization Of The United Nations (FAO)",
279
+ "Food And Livestock Initiative (FLI Asbl)",
280
+ "Forum On Trade, Environment and The SDGs (TESS)",
281
+ "Foundation Of Fokus Nexus Tiga (Nexus3 Foundation)",
282
+ "French Water Partnership (Partenariat Fran\u00e7ais Pour L\u2019eau)",
283
+ "Friends World Committee For Consultation (FWCC)",
284
+ "Fronteras Comunes",
285
+ "Fundacion Avina",
286
+ "Fundaci\u00f3n Ambiente Y Recursos Naturales",
287
+ "Fundaci\u00f3n Interamericana Del Coraz\u00f3n (FIC)",
288
+ "GRID-Arendal",
289
+ "Galapagos Conservation Trust",
290
+ "Gallifrey Foundation",
291
+ "Geneva Cities Hub (GCH)",
292
+ "Gerakan Indonesia Diet Kantong Plastik (GIDKP) - The Indonesia Plastic Bag Diet Movement",
293
+ "Global Alliance For Incinerator Alternatives (GAIA)",
294
+ "Global Alliance On Health And Pollution (GAHP)",
295
+ "Global Cement And Concrete Association",
296
+ "Global Council For Science And The Environment (GCSE)",
297
+ "Global Plastics Policy Centre, University Of Portsmouth",
298
+ "Global Youth Coalition On Plastic Pollution (GYCPP)",
299
+ "Green Africa Youth Organization",
300
+ "Greenpeace International",
301
+ "GroundWork South Africa (GroundWorkSA)",
302
+ "Haitelmex Foundation",
303
+ "Hasiru Dala In Collaboration With Eleven Other Civil Society Organizations",
304
+ "Health And Environment Justice Support (HEJSupport)",
305
+ "Health Care Without Harm (HCWH)",
306
+ "Healthy Hospitals Project - PHS",
307
+ "Human Rights Watch",
308
+ "ICLEI - Local Governments For Sustainability",
309
+ "India Institute For Critical Action Centre In Movement (CACIM)",
310
+ "India Water Foundation",
311
+ "India Youth For Society",
312
+ "Indigenous Caucus",
313
+ "Indigenous Peoples And Their Communities Major Group",
314
+ "Indigenous Peoples Representatives",
315
+ "Indonesian Centre For Environmental Law (ICEL)",
316
+ "Innovazing Vision",
317
+ "Institute For Sustainable Development And Research (ISDR)",
318
+ "Integrated Strategies Forum",
319
+ "Interamerican Heart Foundation",
320
+ "International Air Transport Association",
321
+ "International Alliance Of Waste Pickers (IAWP)",
322
+ "International Alliance Of Waste-pickers",
323
+ "International Atomic Energy Agency (IAEA)",
324
+ "International Center Of Comparative Environmental Law (CIDCE)",
325
+ "International Centre For Environmental Education And Community Development (ICENECDEV)",
326
+ "International Chamber Of Commerce (ICC)",
327
+ "International Council Of Beverages Associations (ICBA)",
328
+ "International Council Of Chemical Associations (ICCA)",
329
+ "International Knowledge Hub Against Plastic Pollution (IKHAPP)",
330
+ "International Labour Office",
331
+ "International Labour Organization (ILO)",
332
+ "International Maritime Organization (IMO)",
333
+ "International Medical Crisis Response Alliance (IMCRA)",
334
+ "International Movement For Advancement Of Education Culture Social and Economic Development (IMAESED)",
335
+ "International Network For Bamboo And Rattan (INBAR)",
336
+ "International Organization For Standardization (ISO)",
337
+ "International Pollutants Elimination Network (IPEN)",
338
+ "International Science Council (ISC)",
339
+ "International Society Of Doctors For The Environment (ISDE)",
340
+ "International Solid Waste Association (ISWA)",
341
+ "International Trade Union Confederation (ITUC)",
342
+ "International Union For Conservation Of Nature And Natural Resources (IUCN)",
343
+ "Inuit Circumpolar Council (ICC)",
344
+ "Japan Clean Ocean Material Alliance (CLOMA)",
345
+ "King Abdullah Petroleum Studies And Research Center (KAPSARC)",
346
+ "Krityanand UNESCO Club, Jamshedpur",
347
+ "La Grande Puissance De Dieu",
348
+ "Latin American Organizations - Alianza Basura Cero",
349
+ "Ligue Camerounaise Des Droits De L'Homme",
350
+ "Litter4tokens South Africa NPO",
351
+ "Local And Subnational Government Working Group",
352
+ "Local Authorities",
353
+ "Loop",
354
+ "Major Alliance Education Centre (MAEC)",
355
+ "Major Group For Children And Youth",
356
+ "MarViva",
357
+ "Marine Ecosystems Protected Areas (MEPA) Trust",
358
+ "Members Of Microplastics Working Group",
359
+ "Mexican Network Of Ecological Action",
360
+ "Minderoo Foundation",
361
+ "Ministry Of Environment And Wildlife - Southwest State Of Somalia",
362
+ "Moms Clean Air Force",
363
+ "Multifaith Action Group On Pollution",
364
+ "NGO Major Group",
365
+ "NORCE On Behalf Of The North Atlantic Microplastic Centre (NAMC)",
366
+ "National Old Folks Of Liberia (NOFOL)",
367
+ "National Retail Association (NRA)",
368
+ "Natural Resources Defense Council (NRDC)",
369
+ "Neste",
370
+ "Nexus For Health, Environment, And Development (Nexus3) Foundation",
371
+ "Nipe Fagio",
372
+ "No Balloon Release Australia",
373
+ "No More Butts",
374
+ "Norwegian Academy Of International Law (NAIL)",
375
+ "Norwegian Institute For Water Research",
376
+ "Norwegian Institute For Water Research (NIVA)",
377
+ "Norwegian Research Centre (NORCE)",
378
+ "ONG Jeunesse Active De Guin\u00e9e (JAG)",
379
+ "Occidental Arts And Ecology Center (OAEC)",
380
+ "Ocean Conservancy",
381
+ "Ocean Recovery Alliance",
382
+ "Ocean. Now",
383
+ "OceanCare",
384
+ "OceanCare Global Ghost Gear Initiative",
385
+ "Office Of The UN High Commissioner For Human Rights (OHCHR)",
386
+ "OpenOceans Global",
387
+ "Organisation For Economic Co-operation And Development (OECD)",
388
+ "Organization Of Arab Petroleum Exporting Countries (OAPEC)",
389
+ "Organization Of The Petroleum Exporting Countries (OPEC)",
390
+ "Our Sea Of East Asia Network (OSEAN)",
391
+ "Out For Sustainability",
392
+ "PCX Solutions (HOPEx Environment Group, Inc)",
393
+ "Pacific Environment And Resources Center (Pacific Environment)",
394
+ "Pan American Neuroendocrine Society",
395
+ "Partnerships For Change",
396
+ "Paryavaran Mitra",
397
+ "PetStar",
398
+ "Planeteer Alliance And Captain Planet Foundation",
399
+ "Plastalliance - Alliance Plasturgie Et Composites Du Futur",
400
+ "Plastic Change",
401
+ "Plastic Free Foundation",
402
+ "Plastic Free Future",
403
+ "Plastic Oceans Australasia",
404
+ "Plastic Pollution Coalition",
405
+ "Plastics Federation Of South Africa",
406
+ "Plastics Industry Association",
407
+ "PlasticsEurope",
408
+ "Plasticulture",
409
+ "ProDelphinus",
410
+ "Public Services International (PSI)",
411
+ "RAPAL",
412
+ "Rapal Uruguay",
413
+ "Recycling Partnership",
414
+ "Red De Acci\u00f3n Ecol\u00f3gica De M\u00e9xico",
415
+ "Red De Acci\u00f3n Por Los Derechos Ambientales",
416
+ "Red Mexicana De Accion Ecologica (Accion Ecologica)",
417
+ "Regions4 Sustainable Development",
418
+ "Reloop Platform",
419
+ "Resolve",
420
+ "Royal Society Of Chemistry",
421
+ "Samo Foundation",
422
+ "Sanid Organization For Relief And Development (SORD)",
423
+ "Sasakawa Peace Foundation",
424
+ "Saudi Green Building Forum",
425
+ "Sciaena",
426
+ "Scientists\u2019 Coalition For An Effective Plastics Treaty (Scientists\u2019 Coalition)",
427
+ "Secretariat For The Pacific Regional Environment Programme",
428
+ "Secretariat Of The Basel, Rotterdam And Stockholm Conventions",
429
+ "Secretariat Of The Convention On The Protection And Use Of Transboundary Watercourses And International Lakes (Water Convention)",
430
+ "Secretariat Of The Pacific Regional Environment Programme (SPREP)",
431
+ "Secretariat Of The WHO Framework Convention On Tobacco Control",
432
+ "Secretariats Of The Basel, Rotterdam And Stockholm Conventions",
433
+ "Shenzhen Zero Waste",
434
+ "Smoke Free Partnership, A Member Of The Stop Tobacco Pollution Alliance (STPA)",
435
+ "Sociedad Peruana De Derecho Ambiental (Peruvian Society Of Environmental Law)",
436
+ "Somali Sustainable Development Organisation (SOSDO)",
437
+ "Somali Youth Development Foundation (SYDF)",
438
+ "South Asia Cooperative Environment Programme",
439
+ "Stand Earth",
440
+ "Stevenson Holistic Care Foundation (SHCF)",
441
+ "Stichting CEFLEX \u2013 The Circular Economy For Flexible Packaging Initiative",
442
+ "Stiftelsen Stockholm International Water Institute",
443
+ "Styrenics Industry",
444
+ "Sustainable Coastlines Charitable Trust",
445
+ "Sustainable Environment Food And Agriculture Initiative",
446
+ "Swedish Society For Nature Conservation (SSNC)",
447
+ "Systemiq",
448
+ "T/A Plastics SA",
449
+ "Take 3 For The Sea",
450
+ "Taller Ecologista",
451
+ "Tangaroa Blue Foundation",
452
+ "Tearfund",
453
+ "Thailand",
454
+ "The Australian Marine Conservation Society",
455
+ "The Center For Oceanic Awareness, Research, And Education (COARE)",
456
+ "The Descendants Project",
457
+ "The Fletcher School",
458
+ "The Global Organization For PHA (GO!PHA)",
459
+ "The Nature Conservancy",
460
+ "The Ocean Cleanup",
461
+ "The Pew Charitable Trusts",
462
+ "The Sea Cleaners",
463
+ "The Society Of Native Nations",
464
+ "The Terracycle Foundation",
465
+ "The Vinyl Institute",
466
+ "Toxics Link",
467
+ "Toxisphera, Mingas Por El Mar",
468
+ "Trade Unions Major Group",
469
+ "Trash Hero World",
470
+ "Trash4tokens NGO",
471
+ "Tufts University",
472
+ "U.S. Council For International Business (USCIB)",
473
+ "UN Women\u2019s Major Group",
474
+ "UNESCO Association - Guwahati",
475
+ "UNESCO Chair For Ocean Sustainability",
476
+ "Udisha",
477
+ "Unbutton Fashion",
478
+ "Unions Workers And Wastepickers",
479
+ "United Nations Association of Spain and the Government of Catalonia",
480
+ "United Nations Conference On Trade And Development (UNCTAD)",
481
+ "United Nations Development Programme (UNDP)",
482
+ "United Nations Economic Commission For Europe (UNECE)",
483
+ "United Nations Global Compact",
484
+ "United Nations Human Settlements Programme (UN-Habitat)",
485
+ "United Nations Industrial Development Organization (UNIDO)",
486
+ "United Nations Institute For Training And Research (UNITAR)",
487
+ "United Nations Office For Disaster Risk Reduction (UNDRR)",
488
+ "United Nations Office On Drugs And Crime (UNODC)",
489
+ "United States Council For Business (USCIB)",
490
+ "University Of Wollongong",
491
+ "Unplastify",
492
+ "Verra",
493
+ "Vital Strategies",
494
+ "WWF-Australia",
495
+ "Waste Free Oceans",
496
+ "Whole World",
497
+ "William Ruto",
498
+ "Women In Informal Employment Globalizing And Organizing (WIEGO)",
499
+ "Women Working Group",
500
+ "Wonjin Institute For Occupational And Environmental Health (WIOEH)",
501
+ "Workers And Trade Unions Major Group",
502
+ "Working Group On Marine Litter (WGML) Of Coordinating Body On The Seas Of East Asia (COBSEA)",
503
+ "World Against Single Use Plastic (WASUP)",
504
+ "World Business Council For Sustainable Development (WBCSD)",
505
+ "World Economic Forum And Global Plastic Action Partnership (GPAP)",
506
+ "World Health Organisation",
507
+ "World Health Organization, Including The Secretariat Of The WHO Framework Convention On Tobacco Control",
508
+ "World Plastics Council (WPC)",
509
+ "World Welfare Association",
510
+ "World Wide Fund For Nature (WWF)",
511
+ "Wrap",
512
+ "Youth Alive Uganda",
513
+ "Youth Focus Group",
514
+ "Yunus Environment Hub",
515
+ "Zero Waste Europe",
516
+ "Zoological Society Of London (ZSL)"
517
+ ]
518
+ }
data/taxonomies/authors_taxonomy.json ADDED
@@ -0,0 +1,520 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "Members": {
3
+ "Countries": [
4
+ "Algeria",
5
+ "Angola",
6
+ "Antigua And Barbuda",
7
+ "Argentina",
8
+ "Armenia",
9
+ "Australia",
10
+ "Azerbaijan",
11
+ "Bahrain",
12
+ "Bangladesh",
13
+ "Barbados",
14
+ "Benin",
15
+ "Bosnia And Herzegovina",
16
+ "Brazil",
17
+ "Burkina Faso",
18
+ "Cambodia",
19
+ "Cameroon",
20
+ "Canada",
21
+ "Chile",
22
+ "China",
23
+ "Colombia",
24
+ "Comoros",
25
+ "Cook Islands",
26
+ "Costa Rica",
27
+ "Cuba",
28
+ "Cote DIvoire",
29
+ "Democratic Republic Of The Congo",
30
+ "Dominican Republic",
31
+ "Ecuador",
32
+ "Egypt",
33
+ "El Salvador",
34
+ "Equatorial Guinea",
35
+ "Eritrea",
36
+ "Eswatini",
37
+ "Ethiopia",
38
+ "Fiji",
39
+ "France",
40
+ "Gabon",
41
+ "Gambia",
42
+ "Georgia",
43
+ "Germany",
44
+ "Ghana",
45
+ "Grenada",
46
+ "Guatemala",
47
+ "Guinea",
48
+ "Guinea Bissau",
49
+ "Honduras",
50
+ "Iceland",
51
+ "India",
52
+ "Indonesia",
53
+ "Iraq",
54
+ "Islamic Republic Of Iran",
55
+ "Israel",
56
+ "Italy",
57
+ "Jamaica",
58
+ "Japan",
59
+ "Jordan",
60
+ "Kazakhstan",
61
+ "Kenya",
62
+ "Kiribati",
63
+ "Kuwait",
64
+ "Libya",
65
+ "Madagascar",
66
+ "Malawi",
67
+ "Malaysia",
68
+ "Maldives",
69
+ "Mali",
70
+ "Marshall Islands",
71
+ "Mauritius",
72
+ "Mexico",
73
+ "Micronesia",
74
+ "Moldova",
75
+ "Monaco",
76
+ "Mongolia",
77
+ "Montenegro",
78
+ "Morocco",
79
+ "Nauru",
80
+ "Nepal",
81
+ "New Zealand",
82
+ "Niger",
83
+ "Nigeria",
84
+ "North Macedonia",
85
+ "Norway",
86
+ "Oman",
87
+ "Pakistan",
88
+ "Palau",
89
+ "Panama",
90
+ "Papua New Guinea",
91
+ "Paraguay",
92
+ "Peru",
93
+ "Philippines",
94
+ "Qatar",
95
+ "Republic Of Congo",
96
+ "Republic Of Korea",
97
+ "Republic Of Moldova",
98
+ "Romania",
99
+ "Russian Federation",
100
+ "Rwanda",
101
+ "Samoa",
102
+ "Saudi Arabia",
103
+ "Senegal",
104
+ "Seychelles",
105
+ "Sierra Leone",
106
+ "Singapore",
107
+ "Solomon Islands",
108
+ "Somalia",
109
+ "South Africa",
110
+ "Sri Lanka",
111
+ "State Of Palestine",
112
+ "Switzerland",
113
+ "Syrian Arab Republic",
114
+ "Thailand",
115
+ "Timor-Leste",
116
+ "Togo",
117
+ "Tonga",
118
+ "Trinidad And Tobago",
119
+ "Tunisia",
120
+ "Turkey",
121
+ "Tuvalu",
122
+ "Uganda",
123
+ "Ukraine",
124
+ "United Arab Emirates",
125
+ "United Kingdom Of Great Britain And Northern Ireland",
126
+ "United Republic Of Tanzania",
127
+ "United States Of America",
128
+ "Uruguay",
129
+ "Venezuela",
130
+ "Vietnam",
131
+ "Yemen",
132
+ "Zambia",
133
+ "Zimbabwe"
134
+ ],
135
+ "International and Regional State Associations": [
136
+ "Asia-Pacific States",
137
+ "European Union (EU) And Its 27 Member States",
138
+ "Federated States Of Micronesia",
139
+ "Gulf Cooperation Council",
140
+ "High Ambition Coalition",
141
+ "Latin American And Caribbean Group (GRULAC)",
142
+ "Like Minded Countries",
143
+ "Pacific Small Island Developing States (PSIDS)",
144
+ "Alliance Of Small Island States (AOSIS)",
145
+ "The Federated States Of Micronesia",
146
+ "The Group Of African States",
147
+ "Western European And Other States",
148
+ "Coordinating Body on the Seas of East Asia (COBSEA)"
149
+ ]
150
+ },
151
+ "Intergovernmental Negotiation Committee": [
152
+ "Executive Secretary Of The INC",
153
+ "Intergovernmental Negotiation Committee"
154
+ ],
155
+ "Observers and Other Participants": [
156
+ "10YFP Secretariat (One Planet Network)",
157
+ "ABIPLAST - Brazilian Association Of The Plastic Industry",
158
+ "ACTS Organization",
159
+ "ASTM International (ASTM)",
160
+ "AWTAD Anti-Corruption Organization",
161
+ "Aaina",
162
+ "Action Et Education Pour Tous (AEPT)",
163
+ "Action On Smoking And Health (ASH)",
164
+ "Africa Climate And Environment Foundation (ACEF)",
165
+ "African Alliance For Health Research Economic Development",
166
+ "African Environmental Network",
167
+ "African Petroleum Producers\u2019 Organization (APPO)",
168
+ "Aguaclara",
169
+ "Alianza Basura Cero",
170
+ "Alianza Latinoamericana De Asociaciones De La Industria De Alimentos Y Bebidas (ALAIAB)",
171
+ "All-China Environment Federation",
172
+ "Alliance Panafricaine Multi-Acteurs Sur La Pollution Plastique",
173
+ "Alliance Pour Le Controle Du Tabac En Afrique (ACTA)",
174
+ "American Chemistry Council",
175
+ "American Fuel and Petrochemical Manufacturers (AFPM)",
176
+ "And Colectivo Jaguares De Nuestra Madre Tierra",
177
+ "Aotearoa Plastic Pollution Alliance (APPA)",
178
+ "Arctic Monitoring And Assessment Programme (AMAP)",
179
+ "Armenian Women For Health And Healthy Environment",
180
+ "Arnika",
181
+ "Asia Indigenous Peoples Pact And Indigenous Peoples",
182
+ "Asian Marine Conservation Association",
183
+ "Asociaci\u00f3n Ecol\u00f3gica Santo Tom\u00e1s",
184
+ "Asociaci\u00f3n Sustentar",
185
+ "Association For Promoting Sustainability In Campuses And Communities (APSCC)",
186
+ "Association For Rural Area Social Modification, Improvement And Nestling (ARASMIN)",
187
+ "Association For Supporting The SDGs For The United Nations",
188
+ "Association Institute Of Total Environment (INTEV)",
189
+ "Association Nationale Du Civisme",
190
+ "Association Of Leadership You-Lean",
191
+ "Association Of Plastic Recyclers",
192
+ "Association Of Solidarity Through Humanitarian Imperative Actions International (ASHIA)",
193
+ "Association Pour L'Integration Et La Developpement Durable Au Burundi",
194
+ "Australian Packaging Covenant Organisation (APCO)",
195
+ "Azul",
196
+ "BAN Toxics",
197
+ "BVRio",
198
+ "Barranquilla + 20",
199
+ "Basel Action Network (BAN)",
200
+ "Beijing Greenovation Institute For Public Welfare Development (GHub)",
201
+ "Brazilian Chemical Industry Association",
202
+ "Break Free From Plastic",
203
+ "Breathe Free Detroit",
204
+ "Bridgers Association Cameroon",
205
+ "Bureau Of International Recycling",
206
+ "Business And Industry Major Group Presented By World Business Council For Sustainable Development",
207
+ "Business Coalition For A Global Plastics Treaty Convened By The Ellen MacArthur Foundation And WWF, In Collaboration With Aligned Businesses And Financial Institutions, And Supported By NGO Partners",
208
+ "CAIRPLAS, C\u00e1mara Argentina De La Industria De Reciclados Plasticos",
209
+ "CDP",
210
+ "CEMPRE Colombia \u2013 Compromiso Empresarial Para El Reciclaje",
211
+ "CESTA",
212
+ "Carrizo Comecrudo Tribe",
213
+ "Center For Biological Diversity",
214
+ "Center For Coalfield Justice",
215
+ "Center For International Environmental Law (CIEL)",
216
+ "Center For International Law And Governance",
217
+ "Center For Islamic Studies Of Universitas Nasional, Jakarta",
218
+ "Center For Oceanic Awareness, Research, And Education (COARE)",
219
+ "Center For Public Health And Environmental Development (CEPHED)",
220
+ "Centre De Recherche Et D\u2019Education Pour Le D\u00e9veloppement (CREPD)",
221
+ "Centre D\u2019Accompagnement Des Alternatives Locales De D\u00e9veloppement (Caald)",
222
+ "Centre For Environmental Justice",
223
+ "Centre For Human Rights And Climate Change Research",
224
+ "Centre For Science And Environment (CSE)",
225
+ "Centre International De Droit Compar\u00e9 De L\u2019environnement",
226
+ "Centre International De Droit Compar\u00e9 De L\u2019environnement",
227
+ "Chemical And Allied Industries\u2019 Association (CAIA)",
228
+ "Chia Funkuin Foundation",
229
+ "Children And Youth Major Group (CYMG)",
230
+ "Children\u2019s Environmental Health Foundation",
231
+ "China Biodiversity Conservation And Green Development Foundation (CBCGDF)",
232
+ "Circular Economy For Flexible Packaging In Europe Initiative (CEFLEX)",
233
+ "Citeo",
234
+ "Citizen Consumer And Civic Action Group (CAG)",
235
+ "Civil Society And Rights Holder Coalition",
236
+ "Civil Society Organizations In Africa",
237
+ "Civil Society Organizations In Asia Pacific",
238
+ "Civil Society Organizations In Latin America",
239
+ "Co-habiter",
240
+ "Comision Centro Americana",
241
+ "Comit\u00e9 National Contre Le Tabagisme",
242
+ "Community Action Against Plastic Waste (CAPws)",
243
+ "Congregations Of St Joseph",
244
+ "Consciente Colectivo",
245
+ "Consumer Goods Forum",
246
+ "Consumers International",
247
+ "Contact Group 1",
248
+ "Contact Group 2",
249
+ "Convention On Biological Diversity (CBD)",
250
+ "Corporate Accountability",
251
+ "Council For Scientific And Industrial Research",
252
+ "C\u00e1mara De La Industria Qu\u00edmica Y Petroqu\u00edmica (CIQyP\u00ae), Miembro Del Concejo Internacional De Asociaciones Qu\u00edmicas (ICCA) Y EURECA",
253
+ "Danimer Scientific",
254
+ "EDANA And INDA",
255
+ "EPS Branchen-en Del Af Plastindustrien (Denmark)",
256
+ "EPS Industry Alliance",
257
+ "EURECA",
258
+ "Earth Day",
259
+ "Earth Law Center",
260
+ "Ecoplas",
261
+ "Ecoproject Partnership",
262
+ "Ellen MacArthur Foundation",
263
+ "Endocrine Society",
264
+ "Engineers Australia",
265
+ "Entidad Especializada En Pl\u00e1sticos Y Medio Ambiente Para Una Econom\u00eda Circular (ECOPLAS)",
266
+ "Entidades Unidas Reafirmando La Econom\u00eda Circular En Argentina (EURECA)",
267
+ "Environmental And Social Development Organization (ESDO)",
268
+ "Environmental Coalition On Standards (ECOS)",
269
+ "Environmental Development Association (FASEEL)",
270
+ "Environmental Investigation Agency",
271
+ "European Bioplastics (EUBP)",
272
+ "European Manufacturers Of EPS",
273
+ "European Manufacturers Of Expanded Polystyrene (EUMEPS)",
274
+ "Expanded Polystyrene Australia",
275
+ "Fauna and Flora International",
276
+ "Fauna and Flora International And Zoological Society Of London (ZSL)",
277
+ "Fenceline Watch",
278
+ "First Modern Agro Tools Common Initiative Group ( FI.MO.AT.C.I.G)",
279
+ "Fondation De La Mer",
280
+ "Food And Agriculture Organization Of The United Nations (FAO)",
281
+ "Food And Livestock Initiative (FLI Asbl)",
282
+ "Forum On Trade, Environment and The SDGs (TESS)",
283
+ "Foundation Of Fokus Nexus Tiga (Nexus3 Foundation)",
284
+ "French Water Partnership (Partenariat Fran\u00e7ais Pour L\u2019eau)",
285
+ "Friends World Committee For Consultation (FWCC)",
286
+ "Fronteras Comunes",
287
+ "Fundacion Avina",
288
+ "Fundaci\u00f3n Ambiente Y Recursos Naturales",
289
+ "Fundaci\u00f3n Interamericana Del Coraz\u00f3n (FIC)",
290
+ "GRID-Arendal",
291
+ "Galapagos Conservation Trust",
292
+ "Gallifrey Foundation",
293
+ "Geneva Cities Hub (GCH)",
294
+ "Gerakan Indonesia Diet Kantong Plastik (GIDKP) - The Indonesia Plastic Bag Diet Movement",
295
+ "Global Alliance For Incinerator Alternatives (GAIA)",
296
+ "Global Alliance On Health And Pollution (GAHP)",
297
+ "Global Cement And Concrete Association",
298
+ "Global Council For Science And The Environment (GCSE)",
299
+ "Global Plastics Policy Centre, University Of Portsmouth",
300
+ "Global Youth Coalition On Plastic Pollution (GYCPP)",
301
+ "Green Africa Youth Organization",
302
+ "Greenpeace International",
303
+ "GroundWork South Africa (GroundWorkSA)",
304
+ "Haitelmex Foundation",
305
+ "Hasiru Dala In Collaboration With Eleven Other Civil Society Organizations",
306
+ "Health And Environment Justice Support (HEJSupport)",
307
+ "Health Care Without Harm (HCWH)",
308
+ "Healthy Hospitals Project - PHS",
309
+ "Human Rights Watch",
310
+ "ICLEI - Local Governments For Sustainability",
311
+ "India Institute For Critical Action Centre In Movement (CACIM)",
312
+ "India Water Foundation",
313
+ "India Youth For Society",
314
+ "Indigenous Caucus",
315
+ "Indigenous Peoples And Their Communities Major Group",
316
+ "Indigenous Peoples Representatives",
317
+ "Indonesian Centre For Environmental Law (ICEL)",
318
+ "Innovazing Vision",
319
+ "Institute For Sustainable Development And Research (ISDR)",
320
+ "Integrated Strategies Forum",
321
+ "Interamerican Heart Foundation",
322
+ "International Air Transport Association",
323
+ "International Alliance Of Waste Pickers (IAWP)",
324
+ "International Alliance Of Waste-pickers",
325
+ "International Atomic Energy Agency (IAEA)",
326
+ "International Center Of Comparative Environmental Law (CIDCE)",
327
+ "International Centre For Environmental Education And Community Development (ICENECDEV)",
328
+ "International Chamber Of Commerce (ICC)",
329
+ "International Council Of Beverages Associations (ICBA)",
330
+ "International Council Of Chemical Associations (ICCA)",
331
+ "International Knowledge Hub Against Plastic Pollution (IKHAPP)",
332
+ "International Labour Office",
333
+ "International Labour Organization (ILO)",
334
+ "International Maritime Organization (IMO)",
335
+ "International Medical Crisis Response Alliance (IMCRA)",
336
+ "International Movement For Advancement Of Education Culture Social and Economic Development (IMAESED)",
337
+ "International Network For Bamboo And Rattan (INBAR)",
338
+ "International Organization For Standardization (ISO)",
339
+ "International Pollutants Elimination Network (IPEN)",
340
+ "International Science Council (ISC)",
341
+ "International Society Of Doctors For The Environment (ISDE)",
342
+ "International Solid Waste Association (ISWA)",
343
+ "International Trade Union Confederation (ITUC)",
344
+ "International Union For Conservation Of Nature And Natural Resources (IUCN)",
345
+ "Inuit Circumpolar Council (ICC)",
346
+ "Japan Clean Ocean Material Alliance (CLOMA)",
347
+ "King Abdullah Petroleum Studies And Research Center (KAPSARC)",
348
+ "Krityanand UNESCO Club, Jamshedpur",
349
+ "La Grande Puissance De Dieu",
350
+ "Latin American Organizations - Alianza Basura Cero",
351
+ "Ligue Camerounaise Des Droits De L'Homme",
352
+ "Litter4tokens South Africa NPO",
353
+ "Local And Subnational Government Working Group",
354
+ "Local Authorities",
355
+ "Loop",
356
+ "Major Alliance Education Centre (MAEC)",
357
+ "Major Group For Children And Youth",
358
+ "MarViva",
359
+ "Marine Ecosystems Protected Areas (MEPA) Trust",
360
+ "Members Of Microplastics Working Group",
361
+ "Mexican Network Of Ecological Action",
362
+ "Minderoo Foundation",
363
+ "Ministry Of Environment And Wildlife - Southwest State Of Somalia",
364
+ "Moms Clean Air Force",
365
+ "Multifaith Action Group On Pollution",
366
+ "NGO Major Group",
367
+ "NORCE On Behalf Of The North Atlantic Microplastic Centre (NAMC)",
368
+ "National Old Folks Of Liberia (NOFOL)",
369
+ "National Retail Association (NRA)",
370
+ "Natural Resources Defense Council (NRDC)",
371
+ "Neste",
372
+ "Nexus For Health, Environment, And Development (Nexus3) Foundation",
373
+ "Nipe Fagio",
374
+ "No Balloon Release Australia",
375
+ "No More Butts",
376
+ "Norwegian Academy Of International Law (NAIL)",
377
+ "Norwegian Institute For Water Research",
378
+ "Norwegian Institute For Water Research (NIVA)",
379
+ "Norwegian Research Centre (NORCE)",
380
+ "ONG Jeunesse Active De Guin\u00e9e (JAG)",
381
+ "Occidental Arts And Ecology Center (OAEC)",
382
+ "Ocean Conservancy",
383
+ "Ocean Recovery Alliance",
384
+ "Ocean. Now",
385
+ "OceanCare",
386
+ "OceanCare Global Ghost Gear Initiative",
387
+ "Office Of The UN High Commissioner For Human Rights (OHCHR)",
388
+ "OpenOceans Global",
389
+ "Organisation For Economic Co-operation And Development (OECD)",
390
+ "Organization Of Arab Petroleum Exporting Countries (OAPEC)",
391
+ "Organization Of The Petroleum Exporting Countries (OPEC)",
392
+ "Our Sea Of East Asia Network (OSEAN)",
393
+ "Out For Sustainability",
394
+ "PCX Solutions (HOPEx Environment Group, Inc)",
395
+ "Pacific Environment And Resources Center (Pacific Environment)",
396
+ "Pan American Neuroendocrine Society",
397
+ "Partnerships For Change",
398
+ "Paryavaran Mitra",
399
+ "PetStar",
400
+ "Planeteer Alliance And Captain Planet Foundation",
401
+ "Plastalliance - Alliance Plasturgie Et Composites Du Futur",
402
+ "Plastic Change",
403
+ "Plastic Free Foundation",
404
+ "Plastic Free Future",
405
+ "Plastic Oceans Australasia",
406
+ "Plastic Pollution Coalition",
407
+ "Plastics Federation Of South Africa",
408
+ "Plastics Industry Association",
409
+ "PlasticsEurope",
410
+ "Plasticulture",
411
+ "ProDelphinus",
412
+ "Public Services International (PSI)",
413
+ "RAPAL",
414
+ "Rapal Uruguay",
415
+ "Recycling Partnership",
416
+ "Red De Acci\u00f3n Ecol\u00f3gica De M\u00e9xico",
417
+ "Red De Acci\u00f3n Por Los Derechos Ambientales",
418
+ "Red Mexicana De Accion Ecologica (Accion Ecologica)",
419
+ "Regions4 Sustainable Development",
420
+ "Reloop Platform",
421
+ "Resolve",
422
+ "Royal Society Of Chemistry",
423
+ "Samo Foundation",
424
+ "Sanid Organization For Relief And Development (SORD)",
425
+ "Sasakawa Peace Foundation",
426
+ "Saudi Green Building Forum",
427
+ "Sciaena",
428
+ "Scientists\u2019 Coalition For An Effective Plastics Treaty (Scientists\u2019 Coalition)",
429
+ "Secretariat For The Pacific Regional Environment Programme",
430
+ "Secretariat Of The Basel, Rotterdam And Stockholm Conventions",
431
+ "Secretariat Of The Convention On The Protection And Use Of Transboundary Watercourses And International Lakes (Water Convention)",
432
+ "Secretariat Of The Pacific Regional Environment Programme (SPREP)",
433
+ "Secretariat Of The WHO Framework Convention On Tobacco Control",
434
+ "Secretariats Of The Basel, Rotterdam And Stockholm Conventions",
435
+ "Shenzhen Zero Waste",
436
+ "Smoke Free Partnership, A Member Of The Stop Tobacco Pollution Alliance (STPA)",
437
+ "Sociedad Peruana De Derecho Ambiental (Peruvian Society Of Environmental Law)",
438
+ "Somali Sustainable Development Organisation (SOSDO)",
439
+ "Somali Youth Development Foundation (SYDF)",
440
+ "South Asia Cooperative Environment Programme",
441
+ "Stand Earth",
442
+ "Stevenson Holistic Care Foundation (SHCF)",
443
+ "Stichting CEFLEX \u2013 The Circular Economy For Flexible Packaging Initiative",
444
+ "Stiftelsen Stockholm International Water Institute",
445
+ "Styrenics Industry",
446
+ "Sustainable Coastlines Charitable Trust",
447
+ "Sustainable Environment Food And Agriculture Initiative",
448
+ "Swedish Society For Nature Conservation (SSNC)",
449
+ "Systemiq",
450
+ "T/A Plastics SA",
451
+ "Take 3 For The Sea",
452
+ "Taller Ecologista",
453
+ "Tangaroa Blue Foundation",
454
+ "Tearfund",
455
+ "Thailand",
456
+ "The Australian Marine Conservation Society",
457
+ "The Center For Oceanic Awareness, Research, And Education (COARE)",
458
+ "The Descendants Project",
459
+ "The Fletcher School",
460
+ "The Global Organization For PHA (GO!PHA)",
461
+ "The Nature Conservancy",
462
+ "The Ocean Cleanup",
463
+ "The Pew Charitable Trusts",
464
+ "The Sea Cleaners",
465
+ "The Society Of Native Nations",
466
+ "The Terracycle Foundation",
467
+ "The Vinyl Institute",
468
+ "Toxics Link",
469
+ "Toxisphera, Mingas Por El Mar",
470
+ "Trade Unions Major Group",
471
+ "Trash Hero World",
472
+ "Trash4tokens NGO",
473
+ "Tufts University",
474
+ "U.S. Council For International Business (USCIB)",
475
+ "UN Women\u2019s Major Group",
476
+ "UNESCO Association - Guwahati",
477
+ "UNESCO Chair For Ocean Sustainability",
478
+ "Udisha",
479
+ "Unbutton Fashion",
480
+ "Unions Workers And Wastepickers",
481
+ "United Nations Association of Spain and the Government of Catalonia",
482
+ "United Nations Conference On Trade And Development (UNCTAD)",
483
+ "United Nations Development Programme (UNDP)",
484
+ "United Nations Economic Commission For Europe (UNECE)",
485
+ "United Nations Global Compact",
486
+ "United Nations Human Settlements Programme (UN-Habitat)",
487
+ "United Nations Industrial Development Organization (UNIDO)",
488
+ "United Nations Institute For Training And Research (UNITAR)",
489
+ "United Nations Office For Disaster Risk Reduction (UNDRR)",
490
+ "United Nations Office On Drugs And Crime (UNODC)",
491
+ "United States Council For Business (USCIB)",
492
+ "University Of Wollongong",
493
+ "Unplastify",
494
+ "Verra",
495
+ "Vital Strategies",
496
+ "WWF-Australia",
497
+ "Waste Free Oceans",
498
+ "Whole World",
499
+ "William Ruto",
500
+ "Women In Informal Employment Globalizing And Organizing (WIEGO)",
501
+ "Women Working Group",
502
+ "Wonjin Institute For Occupational And Environmental Health (WIOEH)",
503
+ "Workers And Trade Unions Major Group",
504
+ "Working Group On Marine Litter (WGML) Of Coordinating Body On The Seas Of East Asia (COBSEA)",
505
+ "World Against Single Use Plastic (WASUP)",
506
+ "World Business Council For Sustainable Development (WBCSD)",
507
+ "World Economic Forum And Global Plastic Action Partnership (GPAP)",
508
+ "World Health Organisation",
509
+ "World Health Organization, Including The Secretariat Of The WHO Framework Convention On Tobacco Control",
510
+ "World Plastics Council (WPC)",
511
+ "World Welfare Association",
512
+ "World Wide Fund For Nature (WWF)",
513
+ "Wrap",
514
+ "Youth Alive Uganda",
515
+ "Youth Focus Group",
516
+ "Yunus Environment Hub",
517
+ "Zero Waste Europe",
518
+ "Zoological Society Of London (ZSL)"
519
+ ]
520
+ }
data/taxonomies/draftcat_taxonomy_filter.json ADDED
@@ -0,0 +1,64 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "Part I": [ "part i: general",
3
+ "preamble",
4
+ "objective",
5
+ "definition",
6
+ "principles",
7
+ "scope"
8
+ ],
9
+ "Part II": ["part ii: general",
10
+ "primary plastic polymers",
11
+ "chemicals and polymers of concern",
12
+ "problematic and avoidable plastic products, including short-lived and single-use plastic products and intentionally added microplastics",
13
+ "problematic and avoidable plastic products, including short-lived and single-use plastic products",
14
+ "intentionally added microplastics",
15
+ "micro- and nanoplastics",
16
+ "exemptions available to a party upon request",
17
+ "dedicated programmes of work",
18
+ "product design, composition and performance",
19
+ "product design and performance",
20
+ "reduce, reuse, refill and repair of plastics and plastic products",
21
+ "use of recycled plastic contents",
22
+ "alternative plastics and plastic products",
23
+ "non-plastic substitutes",
24
+ "extended producer responsibility",
25
+ "emissions and releases of plastic throughout its life cycle",
26
+ "waste management",
27
+ "waste management",
28
+ "fishing gear",
29
+ "trade in listed chemicals, polymers and products, and in plastic waste",
30
+ "trade in listed chemicals, polymers and products",
31
+ "transboundary movement of plastic waste",
32
+ "existing plastic pollution, including in the marine environment",
33
+ "just transition",
34
+ "transparency, tracking, monitoring and labeling",
35
+ "overarching provision related to part ii"
36
+ ],
37
+ "Part III": ["part iii: general",
38
+ "financing",
39
+ "capacity-building, technical assistance and technology transfer"
40
+ ],
41
+ "Part IV": ["part iv: general",
42
+ "national plans",
43
+ "implementation and compliance",
44
+ "reporting on progress",
45
+ "periodic assessment and monitoring of the progress of implementation of the instrument* and effectiveness evaluation",
46
+ "assessment and monitoring",
47
+ "effectiveness evaluation",
48
+ "review of chemicals and polymers of concern, microplastics and problematic and avoidable products",
49
+ "international cooperation",
50
+ "information exchange",
51
+ "awareness-raising, education and research",
52
+ "stakeholder engagement",
53
+ "health aspects"
54
+ ],
55
+ "Part V": [ "part v: general",
56
+ "institutional arrangements",
57
+ "governing body",
58
+ "subsidiary bodies",
59
+ "secretariat"
60
+ ],
61
+ "Part VI": [ "part vi: general",
62
+ "final provisions"
63
+ ]
64
+ }
data/taxonomies/organization.json ADDED
@@ -0,0 +1,99 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ [
2
+ "European Environment Agency",
3
+ "BUND",
4
+ "Break free from Plastics",
5
+ "Lund University",
6
+ "CIEL",
7
+ "EcoWaste Coalition",
8
+ "Rethink Plastics Alliance",
9
+ "Zero Waste Europe",
10
+ "National Institutes of Health",
11
+ "Fair Circularity Initiative",
12
+ "Systemiq",
13
+ "The Last Beach Cleanup",
14
+ "RSVP",
15
+ "We Choose Reuse",
16
+ "PlastChem",
17
+ "Exit Plastic DE",
18
+ "Nordic Council of Ministers",
19
+ "WECF",
20
+ "Genossenschaft Deutscher Brunnen",
21
+ "Heinrich Boell Stiftung",
22
+ "Microplastics Research Group",
23
+ "Environmental Investigation Agency",
24
+ "We choose reuse",
25
+ "GRID Arendal",
26
+ "5 Gyres",
27
+ "International Pellet Watch",
28
+ "University of Gothenburg",
29
+ "Serious Business",
30
+ "Human Rights Watch",
31
+ "HealthCare Without Harm",
32
+ "IPEN",
33
+ "ISWA WOW",
34
+ "Greenpeace",
35
+ "UN-Habitat",
36
+ "BRS Convention",
37
+ "UNEP",
38
+ "UN",
39
+ "Grid Arendal",
40
+ "Seas at Risk",
41
+ "Heinrich B\ufffdll Stiftung",
42
+ "Annuals of Global Health",
43
+ "GAIA",
44
+ "IUCN",
45
+ "Fracktracker",
46
+ "Beyond Plastics",
47
+ "As You Sow",
48
+ "Minderoo Foundation",
49
+ "EIP",
50
+ "Oceana",
51
+ "Center for Climate Integrity",
52
+ "Reloop",
53
+ "Berkeley Lab",
54
+ "Deutsche Umwelthilfe",
55
+ "ISWA",
56
+ "Prevent Waste Alliance",
57
+ "ACAT",
58
+ "Nexus3",
59
+ "OECD",
60
+ "Grid Ardenal",
61
+ "PGL",
62
+ "Shenzen Zero Waste",
63
+ "WOW / ISWA",
64
+ "Global Plastics Policy Centre",
65
+ "Ocean Care",
66
+ "NIVA",
67
+ "GIZ",
68
+ "Arnika",
69
+ "Tearfund",
70
+ "Health Care Without Harm",
71
+ "Eunomia",
72
+ "Zero Waste Germany",
73
+ "BEUC",
74
+ "ecos",
75
+ "Moore Institute for Plastic Pollution Research",
76
+ "Bennington College",
77
+ "COBSEA",
78
+ "ecoton",
79
+ "Acat",
80
+ "Environmental investigation agency",
81
+ "Ellen MacArthur Foundation",
82
+ "Science",
83
+ "European Environmental Bureau",
84
+ "Profundo",
85
+ "Global Green and Healthy Hospitals",
86
+ "Changing markets",
87
+ "National Toxics Network",
88
+ "World Resource Insitute",
89
+ "FairFin",
90
+ "WWF",
91
+ "WCEL",
92
+ "Client Earth",
93
+ "Endocrine Society",
94
+ "NTN",
95
+ "WBCSD",
96
+ "IKHAPP",
97
+ "Surfrider",
98
+ "Quaker United Nations Office"
99
+ ]
data/taxonomies/region.json ADDED
@@ -0,0 +1,31 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ [
2
+ "China",
3
+ "Vietnam",
4
+ "Alaska",
5
+ "East Africa",
6
+ "Turkey",
7
+ "Ghana",
8
+ "ASEAN",
9
+ "Southeast Asia",
10
+ "Pacific",
11
+ "Arctic",
12
+ "South America",
13
+ "Netherlands",
14
+ "Canada",
15
+ "Global",
16
+ "Europe",
17
+ "Germany",
18
+ "Scandinavia",
19
+ "Norway",
20
+ "Russia",
21
+ "Africa",
22
+ "European Union",
23
+ "South East Asia",
24
+ "East Asia",
25
+ "United States of America",
26
+ "Malaysia",
27
+ "Islands",
28
+ "Australia",
29
+ "Indonesia",
30
+ "SIDS"
31
+ ]
data/taxonomies/type_of_document.json ADDED
@@ -0,0 +1,10 @@
 
 
 
 
 
 
 
 
 
 
 
1
+ [
2
+ "2023",
3
+ "2024",
4
+ "2022",
5
+ "2020",
6
+ "2019",
7
+ "2021",
8
+ "2018",
9
+ "2017"
10
+ ]
poetry.lock ADDED
The diff for this file is too large to render. See raw diff
 
pyproject.toml ADDED
@@ -0,0 +1,27 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ [tool.poetry]
2
+ name = "negotiateai2"
3
+ version = "0.1.0"
4
+ description = ""
5
+ authors = ["Rahkakavee Baskaran <rahkakavee.baskaran@cause-effect.io>"]
6
+ readme = "README.md"
7
+
8
+ [tool.poetry.dependencies]
9
+ python = "^3.11"
10
+ haystack-ai = "^2.6.1"
11
+ qdrant-haystack = "^6.0.0"
12
+ pydantic-settings = "^2.6.0"
13
+ qdrant-client = "^1.12.0"
14
+ langchain = "^0.3.4"
15
+ langchain-community = "^0.3.3"
16
+ sentence-transformers = "^3.2.1"
17
+ streamlit = "^1.39.0"
18
+ pypdf = "^5.1.0"
19
+ extra-streamlit-components = "^0.1.71"
20
+ streamlit-lottie = "^0.0.5"
21
+ pdfminer-six = "^20240706"
22
+ plotly = "^5.24.1"
23
+
24
+
25
+ [build-system]
26
+ requires = ["poetry-core"]
27
+ build-backend = "poetry.core.masonry.api"
src/.DS_Store ADDED
Binary file (6.15 kB). View file
 
src/__init__py ADDED
File without changes
src/analysis/__init__.py ADDED
File without changes
src/analysis/submission_map_visualization.py ADDED
@@ -0,0 +1,132 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+ import pathlib
3
+
4
+ import pandas as pd
5
+ import plotly.express as px
6
+
7
+ csv_path = pathlib.Path(__file__).parent.parent.parent / "data" / "raw" / "inc_df.csv"
8
+ json_path = (
9
+ pathlib.Path(__file__).parent.parent.parent
10
+ / "data"
11
+ / "raw"
12
+ / "authors_state_associations.json"
13
+ )
14
+
15
+ # Load the data
16
+ df = pd.read_csv(csv_path)
17
+ with open(json_path, "r") as f:
18
+ association_mapping = json.load(f)
19
+
20
+
21
+ # Function to properly work with the authors column -> the json file "authors_state_associations" in the data file is needed for this to run
22
+ def expand_authors(row, association_mapping, round_number):
23
+ authors = eval(row)
24
+ expanded_countries = []
25
+ submission_types = []
26
+ rounds = []
27
+
28
+ for author in authors:
29
+ if author in association_mapping:
30
+ association_countries = set(association_mapping[author])
31
+ for country in association_countries:
32
+ if country not in authors:
33
+ expanded_countries.append(country)
34
+ submission_types.append("Group")
35
+ rounds.append(round_number)
36
+ elif "," in author:
37
+ countries = [country.strip() for country in author.split(",")]
38
+ expanded_countries.extend(countries)
39
+ submission_types.extend(["Individual"] * len(countries))
40
+ rounds.extend([round_number] * len(countries))
41
+ else:
42
+ expanded_countries.append(author.strip())
43
+ submission_types.append("Individual")
44
+ rounds.append(round_number)
45
+
46
+ return pd.DataFrame(
47
+ {
48
+ "country": expanded_countries,
49
+ "submission_type": submission_types,
50
+ "round": rounds,
51
+ }
52
+ )
53
+
54
+
55
+ # Apply the function to expand the "author" field in each row with round info
56
+ expanded_rows = df.apply(
57
+ lambda x: expand_authors(x["author"], association_mapping, x["round"]), axis=1
58
+ )
59
+
60
+ # Concatenate the expanded rows into a single DataFrame
61
+ expanded_df = pd.concat(expanded_rows.values).reset_index(drop=True)
62
+
63
+ # Count submissions by country, submission type, and round
64
+ country_submission_counts = (
65
+ expanded_df.groupby(["country", "submission_type", "round"])
66
+ .size()
67
+ .reset_index(name="submission_count")
68
+ )
69
+
70
+ # Pivot the data to separate columns for Individual and Group submissions
71
+ country_submission_counts_pivoted = country_submission_counts.pivot_table(
72
+ index=["country", "round"],
73
+ columns="submission_type",
74
+ values="submission_count",
75
+ fill_value=0,
76
+ ).reset_index()
77
+
78
+ country_submission_counts_pivoted["total_submission_count"] = (
79
+ country_submission_counts_pivoted["Group"]
80
+ + country_submission_counts_pivoted["Individual"]
81
+ )
82
+
83
+ # Choropleth map with larger dimensions
84
+ fig = px.choropleth(
85
+ country_submission_counts_pivoted,
86
+ locations="country",
87
+ locationmode="country names",
88
+ color="total_submission_count",
89
+ hover_name="country",
90
+ hover_data={
91
+ "Individual": True,
92
+ "Group": True,
93
+ "total_submission_count": True,
94
+ "round": True,
95
+ },
96
+ color_continuous_scale="ice_r",
97
+ range_color=(
98
+ 0,
99
+ country_submission_counts_pivoted["total_submission_count"].max(),
100
+ ), # Set color scale range
101
+ title="",
102
+ projection="natural earth", # Global map projection instead of Mercator
103
+ animation_frame="round",
104
+ width=1000,
105
+ height=800,
106
+ )
107
+
108
+ # Customize animation speed
109
+ fig.layout.updatemenus[0].buttons[0].args[1]["frame"]["duration"] = (
110
+ 1000 # Set frame duration (1000ms = 1 second)
111
+ )
112
+
113
+ # Add a footnote annotation at the bottom
114
+ fig.update_layout(
115
+ annotations=[
116
+ dict(
117
+ x=0.5,
118
+ y=-0.1,
119
+ xref="paper",
120
+ yref="paper",
121
+ text="""
122
+ Source: <a href='https://www.unep.org/inc-plastic-pollution' target='_blank'>
123
+ Intergovernmental Negotiating Committee on Plastic Pollution</a><br>
124
+ """,
125
+ showarrow=False, # Don't show an arrow
126
+ font=dict(size=12, color="gray"), # Set font size and color
127
+ align="left",
128
+ borderpad=10, # Padding around the annotation
129
+ width=1000, # Optional: Set a maximum width for wrapping text
130
+ )
131
+ ]
132
+ )
src/app/__init__.py ADDED
File without changes
src/app/app.py ADDED
@@ -0,0 +1,141 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import base64
2
+ from pathlib import Path
3
+
4
+ import extra_streamlit_components as stx
5
+ import streamlit as st
6
+
7
+ from src.analysis.submission_map_visualization import fig
8
+ from src.app.views.inc_page import init_inc_page
9
+ from src.app.views.knowledge_hub_page import init_knowledge_hub_page
10
+ from src.utils.data import load_css
11
+
12
+
13
+ # Function to load and encode the image
14
+ def get_base64_image(image_path):
15
+ with open(image_path, "rb") as img_file:
16
+ return base64.b64encode(img_file.read()).decode()
17
+
18
+
19
+ @st.cache_data
20
+ def load_css_style() -> None:
21
+ load_css(Path(__file__).parent.parent.parent / "style" / "style.css")
22
+
23
+
24
+ base64_image = get_base64_image("static/images/banner.jpg")
25
+
26
+ st.set_page_config(layout="wide")
27
+
28
+ # Load the custom CSS
29
+ load_css_style()
30
+
31
+ if "active_tab" not in st.session_state:
32
+ st.session_state.active_tab = "1"
33
+
34
+
35
+ # Function to change active tab
36
+ def set_active_tab(tab_id):
37
+ st.session_state.active_tab = tab_id
38
+
39
+
40
+ # Use session state to set the default tab in the tab bar
41
+ chosen_id = stx.tab_bar(
42
+ data=[
43
+ stx.TabBarItemData(
44
+ id=1,
45
+ title="Welcome to NegotiateAI!",
46
+ description="",
47
+ ),
48
+ stx.TabBarItemData(
49
+ id=2,
50
+ title="INC Plastic Pollution Country Profile Analysis",
51
+ description="",
52
+ ),
53
+ stx.TabBarItemData(
54
+ id=3,
55
+ title="Knowledge Hub",
56
+ description="",
57
+ ),
58
+ ],
59
+ default=st.session_state.active_tab, # Use the active tab from session state
60
+ )
61
+
62
+
63
+ if chosen_id == "1":
64
+ st.html(
65
+ """
66
+ <style>
67
+ /* Container holding the image and the text */
68
+ .container {
69
+ position: relative;
70
+ text-align: center;
71
+ }
72
+
73
+ </style>
74
+ </style>
75
+ """
76
+ )
77
+
78
+ st.markdown(
79
+ f"""
80
+ <div class="container">
81
+ <img src="data:image/png;base64,{base64_image}" alt="Image" style="width:100%; opacity: 0.9;">
82
+ </div>
83
+ """,
84
+ unsafe_allow_html=True,
85
+ )
86
+
87
+ st.write("")
88
+ st.write("")
89
+
90
+ inc_col, space, knowledge_hub_col = st.columns([1, 0.1, 1])
91
+
92
+ # Buttons to trigger tab switch
93
+ with inc_col:
94
+ st.header("INC Treaty")
95
+ st.markdown(
96
+ """
97
+ <p class="description">
98
+ NegotiateAI simplifies the search and analysis of documents by INC members, enabling negotiators and other interested parties to quickly pinpoint crucial information. <br> <br> With an intuitive interface, NegotiateAI supports treaty-specific queries and provides direct links to relevant documents for deeper research.
99
+ </p>
100
+ """,
101
+ unsafe_allow_html=True,
102
+ )
103
+ if st.button(
104
+ "INC Plastic Pollution Country Profile Analysis",
105
+ icon=":material/chevron_right:",
106
+ type="primary",
107
+ ):
108
+ set_active_tab("2")
109
+ st.rerun()
110
+
111
+ with knowledge_hub_col:
112
+ st.header("Knowledge Hub")
113
+ st.markdown(
114
+ """
115
+ <p class="description"> The Hub offers access to wealth of relevant documents such as reports, policy briefs, and research papers from NGOs, research institutions, foundations and other organizations. <br> <br>
116
+ User can query and engage with these resources, enabling them to delve deeper into specific topics and obtain comprehensive information on their work.
117
+ </p>
118
+ """,
119
+ unsafe_allow_html=True,
120
+ )
121
+ if st.button("Knowledge Hub", icon=":material/chevron_right:", type="primary"):
122
+ set_active_tab("3")
123
+ st.rerun()
124
+
125
+ st.markdown(
126
+ """<hr style="height:2px;border:none;color:#077493;background-color:#077493;" /> """,
127
+ unsafe_allow_html=True,
128
+ )
129
+
130
+ st.header(
131
+ "Explore Submissions Around the World!",
132
+ help="The data is based on different submissions from countries individually and in groups or associations. Countries are shown only when a submission exist. Borders may vary because of this. Until now names in the map comply to countries territory. We acknowledge that a more precise representation is needed and we are working on it.",
133
+ )
134
+ # st.write("The app is tailored to enhance the efficiency of finding and accessing information on the UN Plastics Treaty Negotiations. It hosts a comprehensive database of relevant documents submitted by the members available <a href="https://www.unep.org/inc-plastic-pollution"> here</a>, which users can explore through an intuitive chatbot interface as well as simple filtering options. The app excels in querying specific information about countries and their positions in the negotiations, providing targeted and precise answers. However, it can process only up to 8 relevant documents at a time, which may limit responses to more complex inquiries. Filter options by authors and sections of the negotiation draft ensure the accuracy of the answers. Each document found via these filters is also directly accessible via a link, ensuring complete and easy access to the desired information.")
135
+ st.plotly_chart(fig, theme="streamlit", use_container_width=True)
136
+
137
+ if chosen_id == "2":
138
+ init_inc_page()
139
+
140
+ if chosen_id == "3":
141
+ init_knowledge_hub_page()
src/app/views/__init__.py ADDED
File without changes
src/app/views/inc_page.py ADDED
@@ -0,0 +1,373 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import time
2
+ from pathlib import Path
3
+
4
+ import pandas as pd
5
+ import streamlit as st
6
+ from haystack_integrations.document_stores.qdrant import QdrantDocumentStore
7
+
8
+ from src.document_store.get_index import get_index
9
+ from src.rag.pipeline import RAGPipeline
10
+ from src.utils.data import load_css, load_json
11
+ from src.utils.writer import typewriter
12
+
13
+ DATA_BASE_PATH = Path(__file__).parent.parent.parent.parent / "data"
14
+
15
+
16
+ @st.cache_data
17
+ def load_css_style() -> None:
18
+ load_css(Path(__file__).parent.parent.parent.parent / "style" / "style.css")
19
+
20
+
21
+ @st.cache_data
22
+ def load_template() -> str:
23
+ path = (
24
+ Path(__file__).parent.parent.parent
25
+ / "rag"
26
+ / "prompt_templates"
27
+ / "inc_template.txt"
28
+ )
29
+ with open(path, "r") as file:
30
+ template = file.read()
31
+ return template
32
+
33
+
34
+ @st.cache_resource
35
+ def load_inc_pipeline(template: str) -> tuple[QdrantDocumentStore, RAGPipeline]:
36
+ inc_index = get_index(index="inc_data")
37
+ inc_rag = RAGPipeline(document_store=inc_index, top_k=3, template=template)
38
+ return inc_index, inc_rag
39
+
40
+
41
+ @st.cache_data
42
+ def get_authors_taxonomy() -> list[str]:
43
+ taxonomy = load_json(DATA_BASE_PATH / "taxonomies" / "authors_taxonomy.json")
44
+ countries = []
45
+ members = taxonomy["Members"]
46
+ for key, value in members.items():
47
+ if key == "Countries" or key == "International and Regional State Associations":
48
+ countries.extend(value)
49
+ return countries
50
+
51
+
52
+ @st.cache_data
53
+ def get_draft_cat_taxonomy() -> dict[str, list[str]]:
54
+ taxonomy = load_json(
55
+ DATA_BASE_PATH / "taxonomies" / "draftcat_taxonomy_filter.json"
56
+ )
57
+ draft_labels = []
58
+ for _, subpart in taxonomy.items():
59
+ for label in subpart:
60
+ draft_labels.append(label)
61
+ return draft_labels
62
+
63
+
64
+ @st.cache_data
65
+ def get_negotiations_rounds() -> list[int]:
66
+ return [1, 2, 3, 4, 5]
67
+
68
+
69
+ @st.cache_data
70
+ def get_example_prompts() -> list[str]:
71
+ return [
72
+ example["question"]
73
+ for example in load_json(
74
+ DATA_BASE_PATH / "example_prompts" / "example_prompts_inc.json"
75
+ )
76
+ ]
77
+
78
+
79
+ @st.cache_data
80
+ def set_trigger_state_values() -> tuple[bool, bool]:
81
+ trigger_filter_inc = st.session_state.setdefault("trigger_inc", False)
82
+ trigger_ask_inc = st.session_state.setdefault("trigger_inc", False)
83
+ return trigger_filter_inc, trigger_ask_inc
84
+
85
+
86
+ @st.cache_data
87
+ def load_app_init() -> None:
88
+ st.write("\n")
89
+ st.write("\n")
90
+
91
+
92
+ def init_inc_page():
93
+ load_css_style()
94
+ load_app_init()
95
+
96
+ # Load Cache Data and Resources
97
+ authors = get_authors_taxonomy()
98
+ draft_labs = get_draft_cat_taxonomy()
99
+ negotiation_rounds = get_negotiations_rounds()
100
+ example_prompts = get_example_prompts()
101
+ template = load_template()
102
+ trigger_filter_inc, trigger_ask_inc = set_trigger_state_values()
103
+ inc_index, inc_rag = load_inc_pipeline(template=template)
104
+
105
+ # Application Column
106
+ application_col_inc = st.columns(1)
107
+
108
+ with application_col_inc[0]:
109
+ st.markdown(
110
+ """
111
+ <p class="header" style="display: flex; align-items: center;">
112
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32" width="32" height="32" style="margin-right: 10px;">
113
+ <circle cx="16" cy="16" r="15" fill="none" stroke="#077493" stroke-width="2"/>
114
+ <text x="16" y="21" text-anchor="middle" font-size="16" font-family="Arial" font-weight="bold" fill="#077493">1</text>
115
+ </svg> Select Filters</span>
116
+ </p>
117
+ """,
118
+ unsafe_allow_html=True,
119
+ )
120
+ text_design_col_1, textext_design_col_2 = st.columns([1, 1])
121
+ with text_design_col_1:
122
+ st.markdown(
123
+ """<p class="description"> Selecting at least one filter is mandatory, because otherwise the model would have to analyze all available documents which results in inaccurate answers and long processing times. Please select at least one filter. We especially recommend to select countries you are interested in. """,
124
+ unsafe_allow_html=True,
125
+ )
126
+ st.write("\n")
127
+
128
+ col_1, col_2, col_3 = st.columns([1, 1, 1])
129
+
130
+ with col_1:
131
+ selected_authors_inc = st.multiselect(
132
+ label="Countries",
133
+ options=authors,
134
+ label_visibility="visible",
135
+ placeholder="Select",
136
+ key="selected_authors_inc",
137
+ help="Please select the countries of interest. Your selection will refine the database to include documents submitted by these countries or recognized groupings such as Small Developing States, the African States Group, etc.",
138
+ )
139
+
140
+ with col_2:
141
+ selected_rounds_inc = st.multiselect(
142
+ label="Round",
143
+ options=negotiation_rounds,
144
+ label_visibility="visible",
145
+ placeholder="Select",
146
+ key="selected_rounds_inc",
147
+ help="Please select the countries of interest. Your selection will refine the database to include documents submitted by these countries or recognized groupings such as Small Developing States, the African States Group, etc. </p>",
148
+ )
149
+
150
+ with col_3:
151
+ selected_draft_cats_inc = st.multiselect(
152
+ label="Draft Categories",
153
+ options=draft_labs,
154
+ label_visibility="visible",
155
+ placeholder="Select",
156
+ key="selected_draft_cats",
157
+ help=" Please select the parts of the negotiation draft of interest. The negotiation draft can be accessed (https://www.unep.org/inc-plastic-pollution/session-4/documents)",
158
+ )
159
+
160
+ st.write("\n")
161
+ st.write("\n")
162
+
163
+ st.markdown(
164
+ """
165
+ <p class="header" style="display: flex; align-items: center;">
166
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32" width="32" height="32" style="margin-right: 10px;">
167
+ <circle cx="16" cy="16" r="15" fill="none" stroke="#077493" stroke-width="2"/>
168
+ <text x="16" y="21" text-anchor="middle" font-size="16" font-family="Arial" font-weight="bold" fill="#077493">2</text>
169
+ </svg> Ask a question or show documents based on selected filters
170
+ </p>
171
+ """,
172
+ unsafe_allow_html=True,
173
+ )
174
+
175
+ asking_inc, filtering_inc = st.tabs(["Ask a question", "Filter documents"])
176
+
177
+ with asking_inc:
178
+ application_col_ask_inc, output_col_ask_inc = st.columns([1, 1.5])
179
+ with application_col_ask_inc:
180
+ st.markdown(
181
+ """
182
+ <p class="description"> Ask a question, noting that the database has been restricted by filters and that your question should pertain to the selected data. \n
183
+ """,
184
+ unsafe_allow_html=True,
185
+ )
186
+
187
+ if "prompt" not in st.session_state:
188
+ prompt_inc = st.text_area("")
189
+ if (
190
+ "prompt" in st.session_state
191
+ and st.session_state.prompt in example_prompts # noqa: E501
192
+ ): # noqa: E501
193
+ prompt_inc = st.text_area(
194
+ "Enter a question", value=st.session_state.prompt
195
+ ) # noqa: E501
196
+ if (
197
+ "prompt" in st.session_state
198
+ and st.session_state.prompt not in example_prompts # noqa: E501
199
+ ): # noqa: E501
200
+ del st.session_state["prompt"]
201
+ prompt_inc = st.text_area("Enter a question")
202
+
203
+ trigger_ask_inc = st.session_state.setdefault("trigger_inc", False)
204
+
205
+ if st.button("Ask", icon=":material/send:", type="primary"):
206
+ if prompt_inc == "":
207
+ st.error(
208
+ "Please enter a question. Reloading the app in few seconds"
209
+ )
210
+ time.sleep(3)
211
+ st.rerun()
212
+ with st.spinner("Filtering data...") as status:
213
+ if (
214
+ not selected_authors_inc
215
+ and not selected_draft_cats_inc
216
+ and not selected_rounds_inc
217
+ ):
218
+ st.error(
219
+ "Selecting a filter is mandatory. We especially recommend to select countries you are interested in. Selecting at least one filter is mandatory, because otherwise the model would have to analyze all available documents which results in inaccurate answers and long processing times. Please select at least one filter."
220
+ )
221
+ st.stop()
222
+
223
+ with st.spinner("Analyzing Filters") as status:
224
+ filter_selection = {
225
+ "author": selected_authors_inc,
226
+ "draft_labs": selected_draft_cats_inc,
227
+ "round": selected_rounds_inc,
228
+ }
229
+ filters = inc_rag.build_filter(
230
+ filter_selections=filter_selection
231
+ )
232
+ docs = inc_index.filter_documents(filters)
233
+ if not docs:
234
+ st.error(
235
+ "The combination of filters you've chosen does not match any documents. Please try another combination of filters. If a filter combination does not return any documents, it means that there are no documents that match the selected filters and therefore no answer can be given."
236
+ )
237
+ trigger_ask_inc = False
238
+ st.stop()
239
+ else:
240
+ st.success("Filtering completed.")
241
+ with st.spinner("Answering question..."):
242
+ result = inc_rag.run(
243
+ query=prompt_inc, filter_selections=filter_selection
244
+ )
245
+ trigger_ask_inc = True
246
+ st.success("Answering question completed.")
247
+
248
+ st.markdown(
249
+ "***≡ Examples***",
250
+ help="These are example prompts that can be used to ask questions to the model. Click on a prompt to use it as a question. You can also type your own question in the text area above. In general we highly recommend to use the filter functions to narrow down the data.",
251
+ )
252
+
253
+ for i, prompt_inc in enumerate(example_prompts):
254
+ # with col[i % 4]:
255
+ if st.button(prompt_inc):
256
+ if "key" not in st.session_state:
257
+ st.session_state["prompt"] = prompt_inc
258
+ # Define the button
259
+
260
+ with filtering_inc:
261
+ application_col_filter, output_col_filter = st.columns([1, 1.5])
262
+ # make the buttons text smaller
263
+ with application_col_filter:
264
+ st.markdown(
265
+ """
266
+ <p class="description">
267
+ This filter function allows you to see all documents that match the selected filters. The documents can be accessed via a link. \n
268
+ """,
269
+ unsafe_allow_html=True,
270
+ )
271
+ if st.button("Filter", icon=":material/filter_alt:", type="primary"):
272
+ if (
273
+ not selected_authors_inc
274
+ and not selected_draft_cats_inc
275
+ and not selected_rounds_inc
276
+ ):
277
+ st.info(
278
+ "No filters selected. All documents will be shown. Longer processing time expected."
279
+ )
280
+
281
+ with st.spinner("Filtering documents..."):
282
+ filter = RAGPipeline.build_filter(
283
+ filter_selections={
284
+ "author": selected_authors_inc,
285
+ "draft_labs": selected_draft_cats_inc,
286
+ "round": selected_rounds_inc,
287
+ }
288
+ )
289
+ result = inc_index.filter_documents(filter)
290
+
291
+ retriever_ids = set()
292
+ result_meta = []
293
+
294
+ for doc in result:
295
+ retriever_id = doc.meta["retriever_id"]
296
+ if retriever_id not in retriever_ids:
297
+ result_meta.append(
298
+ {
299
+ "author": doc.meta["author"],
300
+ "doc_type": doc.meta["doc_type"],
301
+ "round": doc.meta["round"],
302
+ "href": doc.meta["href"],
303
+ "draft_labs": doc.meta["draft_labs"],
304
+ "draft_cats": doc.meta["draft_cats"],
305
+ }
306
+ )
307
+ retriever_ids.add(retriever_id)
308
+ else:
309
+ continue
310
+
311
+ result_df = pd.DataFrame(result_meta)
312
+ if result_df.empty:
313
+ st.info(
314
+ "No documents found for the combination of filters you've chosen. All countries are represented at least once in the data. Remove the draft categories to see all documents for the countries selected or try other draft categories and/or rounds"
315
+ )
316
+ trigger_filter_inc = False
317
+ else:
318
+ trigger_filter_inc = True
319
+
320
+ if trigger_filter_inc:
321
+ with output_col_filter:
322
+ st.markdown("### Overview of all filtered documents")
323
+ st.dataframe(
324
+ result_df,
325
+ hide_index=True,
326
+ column_config={
327
+ "author": st.column_config.ListColumn("Authors"),
328
+ "href": st.column_config.LinkColumn("Link to Document"),
329
+ "draft_labs": st.column_config.ListColumn("Draft Categories"),
330
+ "round": st.column_config.NumberColumn("Round"),
331
+ "doc_type": st.column_config.TextColumn("Document Type"),
332
+ "draft_cats": st.column_config.ListColumn("Draft Categories"),
333
+ },
334
+ )
335
+
336
+ if trigger_ask_inc:
337
+ with output_col_ask_inc:
338
+ if result is None:
339
+ st.error(
340
+ "Open AI rate limit exceeded. Please try again in a few seconds."
341
+ )
342
+ st.stop()
343
+
344
+ reference_data = [
345
+ (doc.meta["retriever_id"], doc.meta["href"])
346
+ for doc in result["retriever"]["documents"]
347
+ ]
348
+
349
+ references = ["\n"]
350
+ for retriever_id, href in reference_data:
351
+ references.append(f"-[{retriever_id}]: {href} \n")
352
+
353
+ references = list(set(references))
354
+
355
+ st.markdown(
356
+ """<svg xmlns="http://www.w3.org/2000/svg" height="24px" viewBox="0 -960 960 960" width="24px" fill="#077493"><path d="m640-480 80 80v80H520v240l-40 40-40-40v-240H240v-80l80-80v-280h-40v-80h400v80h-40v280Zm-286 80h252l-46-46v-314H400v314l-46 46Zm126 0Z"/></svg> <b>Answer</b>""",
357
+ unsafe_allow_html=True,
358
+ )
359
+
360
+ typewriter(
361
+ text=result["llm"]["replies"][0],
362
+ references=references,
363
+ speed=100,
364
+ )
365
+
366
+ with st.expander("Show more information to the documents"):
367
+ for doc in result["retriever"]["documents"]:
368
+ markdown_text = f"- Document: {doc.meta['retriever_id']}\n"
369
+ markdown_text += " - Text passages\n"
370
+ markdown_text += f" - {doc.content}\n"
371
+ st.write(markdown_text)
372
+
373
+ trigger_ask_inc = False
src/app/views/knowledge_hub_page.py ADDED
@@ -0,0 +1,353 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import time
2
+ from pathlib import Path
3
+
4
+ import pandas as pd
5
+ import streamlit as st
6
+ from haystack_integrations.document_stores.qdrant import QdrantDocumentStore
7
+
8
+ from src.document_store.get_index import get_index
9
+ from src.rag.pipeline import RAGPipeline
10
+ from src.utils.data import load_css, load_json
11
+ from src.utils.writer import typewriter
12
+
13
+ DATA_BASE_PATH = Path(__file__).parent.parent.parent.parent / "data"
14
+
15
+
16
+ @st.cache_data
17
+ def load_css_style() -> None:
18
+ load_css(Path(__file__).parent.parent.parent.parent / "style" / "style.css")
19
+
20
+
21
+ @st.cache_resource
22
+ def load_knowledge_hub_pipeline(
23
+ template: str,
24
+ ) -> tuple[QdrantDocumentStore, RAGPipeline]:
25
+ knowledge_hub_index = get_index(index="knowledge_hub_data")
26
+ knowledge_hub_rag = RAGPipeline(
27
+ document_store=knowledge_hub_index, top_k=3, template=template
28
+ )
29
+ return knowledge_hub_index, knowledge_hub_rag
30
+
31
+
32
+ @st.cache_resource
33
+ def get_organization_filter() -> dict | list:
34
+ return load_json(DATA_BASE_PATH / "taxonomies" / "organization.json")
35
+
36
+
37
+ @st.cache_data
38
+ def load_template() -> str:
39
+ path = (
40
+ Path(__file__).parent.parent.parent
41
+ / "rag"
42
+ / "prompt_templates"
43
+ / "inc_template.txt"
44
+ )
45
+ with open(path, "r") as file:
46
+ template = file.read()
47
+ return template
48
+
49
+
50
+ @st.cache_data
51
+ def get_example_prompts() -> list[str]:
52
+ return [
53
+ example["question"]
54
+ for example in load_json(
55
+ DATA_BASE_PATH / "example_prompts" / "example_prompts_knowledge_hub.json"
56
+ )
57
+ ]
58
+
59
+
60
+ @st.cache_resource
61
+ def get_region_filter() -> dict | list:
62
+ return load_json(DATA_BASE_PATH / "taxonomies" / "region.json")
63
+
64
+
65
+ @st.cache_resource
66
+ def get_type_of_document_filter() -> dict | list:
67
+ return load_json(DATA_BASE_PATH / "taxonomies" / "type_of_document.json")
68
+
69
+
70
+ @st.cache_data
71
+ def set_trigger_state_values() -> tuple[bool, bool]:
72
+ trigger_filter_k = st.session_state.setdefault("trigger_k", False)
73
+ trigger_ask_k = st.session_state.setdefault("trigger_k", False)
74
+ return trigger_filter_k, trigger_ask_k
75
+
76
+
77
+ @st.cache_data
78
+ def load_app_init() -> None:
79
+ pass
80
+
81
+
82
+ def init_knowledge_hub_page():
83
+ load_css_style()
84
+ load_app_init()
85
+
86
+ # Load Cache Data and Resources
87
+ trigger_filter_k, trigger_ask_k = set_trigger_state_values()
88
+ knowledge_hub_template = load_template()
89
+ knowledge_hub_index, knowledge_hub_rag = load_knowledge_hub_pipeline(
90
+ template=knowledge_hub_template
91
+ )
92
+ example_prompts_k = get_example_prompts()
93
+ organization_filter = get_organization_filter()
94
+ region_filter = get_region_filter()
95
+ type_of_document_filter = get_type_of_document_filter()
96
+
97
+ # Application Column
98
+ application_col = st.columns(1)
99
+
100
+ with application_col[0]:
101
+ st.write("\n")
102
+ organization, region, type_of_document = st.columns(3)
103
+
104
+ with organization:
105
+ selected_organization = st.multiselect(
106
+ label="Organization",
107
+ options=organization_filter,
108
+ label_visibility="visible",
109
+ placeholder="Select organization",
110
+ )
111
+ with region:
112
+ selected_region = st.multiselect(
113
+ label="Region",
114
+ options=region_filter,
115
+ label_visibility="visible",
116
+ placeholder="Select region",
117
+ )
118
+ with type_of_document:
119
+ selected_type_of_document = st.multiselect(
120
+ label="Type of Document",
121
+ options=type_of_document_filter,
122
+ label_visibility="visible",
123
+ placeholder="Select type of document",
124
+ )
125
+
126
+ st.write("\n")
127
+
128
+ asking_k, filtering_k = st.tabs(["Ask a question", "Filter documents"])
129
+
130
+ with asking_k:
131
+ application_col_ask_k, output_col_ask_k = st.columns([1, 1.5])
132
+ with application_col_ask_k:
133
+ st.markdown(
134
+ """
135
+ <p class="description">
136
+ Please ask a question to get an answer or show documents based on the selected filters. This step is optional.</p>
137
+ """,
138
+ unsafe_allow_html=True,
139
+ )
140
+
141
+ if "prompt_k" not in st.session_state:
142
+ prompt_k = st.text_area(label="")
143
+ if (
144
+ "prompt_k" in st.session_state
145
+ and st.session_state.prompt_k in example_prompts_k
146
+ ):
147
+ prompt_k = st.text_area(
148
+ label="Enter a question",
149
+ value=st.session_state.prompt_k,
150
+ )
151
+ if (
152
+ "prompt_k" in st.session_state
153
+ and st.session_state.prompt_k not in example_prompts_k
154
+ ):
155
+ del st.session_state["prompt_k"]
156
+ prompt_k = st.text_area(label="Enter a question")
157
+
158
+ trigger_ask_k = st.session_state.setdefault("trigger", False)
159
+
160
+ if st.button(
161
+ "Ask", key="ask_k", type="primary", icon=":material/send:"
162
+ ):
163
+ if prompt_k == "":
164
+ st.error(
165
+ "Please enter a question. Reloading the app in few seconds",
166
+ icon=":material/error:",
167
+ )
168
+ time.sleep(3)
169
+ st.rerun()
170
+
171
+ with st.spinner("Querying Documents..."):
172
+ filter_selection = {
173
+ "organization": selected_organization,
174
+ "region": selected_region,
175
+ "type_of_document": selected_type_of_document,
176
+ }
177
+
178
+ if (
179
+ not selected_region
180
+ and not selected_organization
181
+ and not selected_type_of_document
182
+ ):
183
+ st.warning(
184
+ "No filters selected. All documents will be used for the question. Longer processing time expected. Please consider using the filter functions to narrow down the data.",
185
+ icon=":material/warning:",
186
+ )
187
+ filters = knowledge_hub_rag.build_filter(
188
+ filter_selections=filter_selection
189
+ )
190
+
191
+ docs = knowledge_hub_index.filter_documents(filters=filters)
192
+
193
+ if not docs:
194
+ st.error(
195
+ "The combination of filters you've chosen does not match any documents. Please try another combination of filters. If a filter combination does not return any documents, it means that there are no documents that match the selected filters and therefore no answer can be given.",
196
+ icon=":material/error:",
197
+ )
198
+ trigger_ask_k = False
199
+ st.stop()
200
+ else:
201
+ st.success("Filtering completed.", icon=":material/check:")
202
+ with st.spinner("Answering question..."):
203
+ result = knowledge_hub_rag.run(
204
+ query=prompt_k, filter_selections=filter_selection
205
+ )
206
+
207
+ trigger_ask_k = True
208
+ st.success(
209
+ "Answering question completed.", icon=":material/check:"
210
+ )
211
+
212
+ st.markdown(
213
+ "***≡ Examples***",
214
+ help="These are example prompts that can be used to ask questions to the model. Click on a prompt to use it as a question. You can also type your own question in the text area above. In general we highly recommend to use the filter functions to narrow down the data.",
215
+ )
216
+
217
+ for i, prompt_inc in enumerate(example_prompts_k):
218
+ # with col[i % 4]:
219
+ if st.button(prompt_inc):
220
+ if "key" not in st.session_state:
221
+ st.session_state["prompt_k"] = prompt_inc
222
+
223
+ with filtering_k:
224
+ application_col_filter_k, output_col_filter_k = st.columns([1, 1.5])
225
+
226
+ with application_col_filter_k:
227
+ st.markdown(
228
+ """
229
+ <p class="description"> This filter function allows you to see all documents that match the selected filters. The documents can be accessed via a link \n </p>
230
+ """,
231
+ unsafe_allow_html=True,
232
+ )
233
+ if st.button(
234
+ "Filter documents",
235
+ key="filter_docuemts_k",
236
+ type="primary",
237
+ icon=":material/filter_alt:",
238
+ ):
239
+ if (
240
+ not selected_region
241
+ and not selected_organization
242
+ and not selected_type_of_document
243
+ ):
244
+ st.info(
245
+ "No filteres selected. All documents will be shown. Longer processing time expected."
246
+ )
247
+
248
+ with st.spinner("Filtering documents..."):
249
+ filter = RAGPipeline.build_filter(
250
+ filter_selections={
251
+ "organization": selected_organization,
252
+ "region": selected_region,
253
+ "type_of_document": selected_type_of_document,
254
+ }
255
+ )
256
+ result = knowledge_hub_index.filter_documents(filters=filter)
257
+
258
+ retriever_ids = set()
259
+ result_meta = []
260
+
261
+ for doc in result:
262
+ retriever_id = doc.meta["retriever_id"]
263
+ if retriever_id not in retriever_ids:
264
+ result_meta.append(
265
+ {
266
+ "organization": doc.meta["organization"],
267
+ "title": doc.meta["title"],
268
+ "year": doc.meta["year"],
269
+ "region": doc.meta["region"],
270
+ "keywords": doc.meta["key_words"],
271
+ "type_of_document": doc.meta[
272
+ "type_of_document"
273
+ ],
274
+ "type_of_organization": doc.meta[
275
+ "type_of_organization"
276
+ ],
277
+ "href": doc.meta["href"],
278
+ }
279
+ )
280
+ retriever_ids.add(retriever_id)
281
+ else:
282
+ continue
283
+
284
+ result_df = pd.DataFrame(result_meta)
285
+ if result_df.empty:
286
+ st.info(
287
+ "No documents found for the combination of filters you've chosen. All countries are represented at least once in the data. Remove the draft categories to see all documents for the countries selected or try other draft categories and/or rounds"
288
+ )
289
+ trigger_filter_k = False
290
+ else:
291
+ trigger_filter_k = True
292
+
293
+ if trigger_filter_k:
294
+ with output_col_filter_k:
295
+ st.markdown("### Overview of all filtered documents")
296
+ st.dataframe(
297
+ result_df,
298
+ hide_index=True,
299
+ use_container_width=True,
300
+ column_config={
301
+ "organization": st.column_config.ListColumn("Organization"),
302
+ "title": st.column_config.TextColumn("Title"),
303
+ "year": st.column_config.TextColumn("Year"),
304
+ "region": st.column_config.ListColumn("Region"),
305
+ "keywords": st.column_config.ListColumn("Keywords"),
306
+ "type_of_document": st.column_config.TextColumn(
307
+ "Type of Document"
308
+ ),
309
+ "type_of_organization": st.column_config.TextColumn(
310
+ "Type of Organization"
311
+ ),
312
+ "href": st.column_config.LinkColumn("Link"),
313
+ },
314
+ )
315
+ trigger_filter_k = False
316
+
317
+ if trigger_ask_k:
318
+ with output_col_ask_k:
319
+ if result is None:
320
+ st.error(
321
+ "Open AI rate limit exceeded. Please try again in a few seconds."
322
+ )
323
+ st.stop()
324
+
325
+ reference_data = [
326
+ (doc.meta["retriever_id"], doc.meta["href"])
327
+ for doc in result["retriever"]["documents"]
328
+ ]
329
+
330
+ references = ["\n"]
331
+
332
+ for retriever_id, href in reference_data:
333
+ references.append(f"-[{retriever_id}]: {href} \n")
334
+
335
+ references = list(set(references))
336
+
337
+ st.markdown(
338
+ """<svg xmlns="http://www.w3.org/2000/svg" height="24px" viewBox="0 -960 960 960" width="24px" fill="#077493"><path d="m640-480 80 80v80H520v240l-40 40-40-40v-240H240v-80l80-80v-280h-40v-80h400v80h-40v280Zm-286 80h252l-46-46v-314H400v314l-46 46Zm126 0Z"/></svg> <b>Answer</b>""",
339
+ unsafe_allow_html=True,
340
+ )
341
+
342
+ typewriter(
343
+ text=result["llm"]["replies"][0], references=references, speed=100
344
+ )
345
+
346
+ with st.expander("Show more information to the documents"):
347
+ for doc in result["retriever"]["documents"]:
348
+ markdown_text = f"- Document: {doc.meta['retriever_id']}\n"
349
+ markdown_text += " - Text passages\n"
350
+ markdown_text += f" - {doc.content}\n"
351
+ st.write(markdown_text)
352
+
353
+ trigger_ask_k = False
src/document_store/get_index.py ADDED
@@ -0,0 +1,17 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from haystack.utils import Secret
2
+ from haystack_integrations.document_stores.qdrant import QdrantDocumentStore
3
+
4
+ from src.settings import settings
5
+
6
+
7
+ def get_index(index: str = "document") -> QdrantDocumentStore:
8
+ return QdrantDocumentStore(
9
+ url=settings.qdrant_database.url,
10
+ api_key=Secret.from_env_var("QDRANT_DATABASE__API_KEY"),
11
+ index=index,
12
+ embedding_dim=settings.qdrant_database.embedding_dim,
13
+ similarity="cosine",
14
+ recreate_index=False,
15
+ wait_result_from_api=True,
16
+ return_embedding=True,
17
+ )
src/rag/__init__.py ADDED
File without changes
src/rag/pipeline.py ADDED
@@ -0,0 +1,114 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from haystack import Pipeline
2
+ from haystack.components.builders import PromptBuilder
3
+ from haystack.components.embedders import SentenceTransformersTextEmbedder
4
+ from haystack.components.generators import OpenAIGenerator
5
+ from haystack.utils import Secret
6
+ from haystack_integrations.components.retrievers.qdrant import QdrantEmbeddingRetriever
7
+
8
+ from src.document_store.document_store import DocumentStore
9
+ from src.settings import settings
10
+
11
+
12
+ class RAGPipeline:
13
+ def __init__(
14
+ self,
15
+ document_store: DocumentStore,
16
+ template: str,
17
+ top_k: int,
18
+ ) -> None:
19
+ self.text_embedder: SentenceTransformersTextEmbedder # type: ignore
20
+ self.retriever: QdrantEmbeddingRetriever # type: ignore
21
+ self.prompt_builder: PromptBuilder # type: ignore
22
+ self.llm_provider: OpenAIGenerator # type: ignore
23
+ self.pipeline: Pipeline | None = None
24
+ self.document_store = document_store
25
+ self.template = template
26
+ self.top_k = top_k
27
+
28
+ self.get_text_embedder()
29
+ self.get_retriever()
30
+ self.get_prompt_builder()
31
+ self.get_llm_provider()
32
+
33
+ def run(self, query: str, filter_selections: dict[str, list] | None = None) -> dict:
34
+ if not self.pipeline:
35
+ self.build_pipeline()
36
+ if self.pipeline:
37
+ filters = RAGPipeline.build_filter(filter_selections=filter_selections)
38
+ result = self.pipeline.run(
39
+ data={
40
+ "text_embedder": {"text": query},
41
+ "retriever": {"filters": filters},
42
+ "prompt_builder": {"query": query},
43
+ },
44
+ include_outputs_from=["retriever", "llm"],
45
+ )
46
+ return result
47
+
48
+ def get_text_embedder(self) -> None:
49
+ self.text_embedder = SentenceTransformersTextEmbedder(
50
+ model=settings.qdrant_database.model
51
+ )
52
+ self.text_embedder.warm_up()
53
+
54
+ def get_retriever(self) -> None:
55
+ self.retriever = QdrantEmbeddingRetriever(
56
+ document_store=self.document_store, top_k=self.top_k
57
+ )
58
+
59
+ def get_prompt_builder(self) -> None:
60
+ self.prompt_builder = PromptBuilder(template=self.template)
61
+
62
+ def get_llm_provider(self) -> None:
63
+ self.llm_provider = OpenAIGenerator(
64
+ model=settings.llm_provider.model,
65
+ api_key=Secret.from_env_var("LLM_PROVIDER__API_KEY"),
66
+ max_retries=3,
67
+ generation_kwargs={"max_tokens": 5000, "temperature": 0.2},
68
+ )
69
+
70
+ @staticmethod
71
+ def build_filter(filter_selections: dict[str, list] | None = None) -> dict:
72
+ filters: dict[str, str | list[dict]] = {"operator": "AND", "conditions": []}
73
+ if filter_selections:
74
+ for meta_data_name, selections in filter_selections.items():
75
+ filters["conditions"].append( # type: ignore
76
+ {
77
+ "field": "meta." + meta_data_name,
78
+ "operator": "in",
79
+ "value": selections,
80
+ }
81
+ )
82
+ else:
83
+ filters = {}
84
+ return filters
85
+
86
+ def build_pipeline(self):
87
+ self.pipeline = Pipeline()
88
+ self.pipeline.add_component("text_embedder", self.text_embedder)
89
+ self.pipeline.add_component("retriever", self.retriever)
90
+ self.pipeline.add_component("prompt_builder", self.prompt_builder)
91
+ self.pipeline.add_component("llm", self.llm_provider)
92
+
93
+ self.pipeline.connect("text_embedder.embedding", "retriever.query_embedding")
94
+ self.pipeline.connect("retriever", "prompt_builder.documents")
95
+ self.pipeline.connect("prompt_builder", "llm")
96
+
97
+
98
+ if __name__ == "__main__":
99
+ document_store = DocumentStore(index="inc_data")
100
+
101
+ with open("src/rag/prompt_templates/inc_template.txt", "r") as file:
102
+ template = file.read()
103
+
104
+ pipeline = RAGPipeline(
105
+ document_store=document_store.document_store, template=template, top_k=5
106
+ )
107
+ filter_selections = {
108
+ "author": ["Malaysia", "Australia"],
109
+ }
110
+ result = pipeline.run(
111
+ "What is Malaysia's position on plastic waste?",
112
+ filter_selections=filter_selections,
113
+ )
114
+ pass
src/rag/prompt_templates/inc_template.txt ADDED
@@ -0,0 +1,14 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ Answer the question {{ query }} using only the provided documents and avoiding text.
2
+ Formulate your answer in the style of an academic report.
3
+ Provide example quotes and citations using extracted text from the documents.
4
+ Use facts and numbers from the documents in your answer.
5
+ ALWAYS include the references of the documents used from documents at the end of each applicable sentence using the format [number].
6
+ If the answer isn't in the document say 'Answering is not possible given the available information'.
7
+
8
+ Documents:
9
+ {% for document in documents %}
10
+ {{ document.meta.retriever_id }}: {{ document.content }}
11
+
12
+ {% endfor %}
13
+
14
+ Answer:
src/rag/prompt_templates/knowledge_hub.txt ADDED
@@ -0,0 +1,14 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ Answer the question {{ query }} using only the provided text chunks from Reports and Scientific Papers.
2
+ Formulate your answer in the style of an scientific report.
3
+ Provide example quotes and citations using extracted text from the documents.
4
+ Use facts and numbers from the documents in your answer.
5
+ ALWAYS include the references of the documents used from documents at the end of each applicable sentence using the format [number].
6
+ If the answer isn't in the document say 'Answering is not possible given the available information'.
7
+
8
+ Documents:
9
+ {% for document in documents %}
10
+ {{ document.meta.retriever_id }}: {{ document.content }}
11
+
12
+ {% endfor %}
13
+
14
+ Answer:
src/settings.py ADDED
@@ -0,0 +1,26 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from pydantic import BaseModel
2
+ from pydantic_settings import BaseSettings, SettingsConfigDict
3
+
4
+
5
+ class QdrantDatabase(BaseModel):
6
+ url: str
7
+ api_key: str
8
+ embedding_dim: int = 512
9
+ model: str = "sentence-transformers/distiluse-base-multilingual-cased-v1"
10
+
11
+
12
+ class LlmProvider(BaseModel):
13
+ model: str
14
+ api_key: str
15
+
16
+
17
+ class Settings(BaseSettings):
18
+ qdrant_database: QdrantDatabase
19
+ llm_provider: LlmProvider
20
+
21
+ model_config = SettingsConfigDict(
22
+ case_sensitive=False, env_nested_delimiter="__", env_file=".env"
23
+ )
24
+
25
+
26
+ settings = Settings()
src/utils/__init__.py ADDED
File without changes
src/utils/data.py ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+ from pathlib import Path
3
+
4
+ import streamlit as st
5
+
6
+
7
+ def load_json(file_path: Path) -> dict | list:
8
+ with open(file_path, "r") as f:
9
+ return json.load(f)
10
+
11
+
12
+ def save_json(file_path: Path, data: dict | list) -> None:
13
+ with open(file_path, "w") as f:
14
+ json.dump(data, f, indent=4)
15
+
16
+
17
+ def load_css(file_name) -> None:
18
+ with open(file_name) as f:
19
+ st.markdown(f"<style>{f.read()}</style>", unsafe_allow_html=True)
src/utils/writer.py ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import time
2
+
3
+ import streamlit as st
4
+
5
+
6
+ def typewriter(text: str, references: list, speed: int):
7
+ tokens = text.split()
8
+ container = st.empty()
9
+ for index in range(len(tokens) + 1):
10
+ curr_full_text = " ".join(tokens[:index])
11
+ container.markdown(curr_full_text)
12
+ time.sleep(1 / speed)
13
+ curr_full_text += "\n"
14
+ container.markdown(curr_full_text)
15
+ curr_full_text += "\n **References** \n"
16
+ curr_full_text += "\n"
17
+ container.markdown(curr_full_text)
18
+ curr_full_text += "\n".join(references)
19
+ container.markdown(curr_full_text)
static/images/Firefly-1.jpg ADDED
static/images/banner.jpg ADDED

Git LFS Details

  • SHA256: fbf6e7d37fb0476bcf942f7cf4b6f9d5bfcc769c0a37402cd7c4bb1082d82800
  • Pointer size: 132 Bytes
  • Size of remote file: 1.94 MB
static/images/logo.jpg ADDED
style/style.css ADDED
@@ -0,0 +1,65 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ .feedback-link {
2
+ display: inline-block;
3
+ background-color: #077493; /* Adjusted color */
4
+ color: white;
5
+ border: none;
6
+ border-radius: 4px;
7
+ padding: 0.5rem 1rem;
8
+ text-decoration: none;
9
+ font-size: 1rem;
10
+ cursor: pointer;
11
+ box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1); /* Added */
12
+ }
13
+
14
+ .feedback-link:hover {
15
+ background-color: #077493; /* Adjusted hover color */
16
+ }
17
+
18
+ .feedback-link[href^="mailto"] {
19
+ color: white !important;
20
+ text-decoration: none !important;
21
+ }
22
+
23
+
24
+
25
+ /* Style streamlit general text */
26
+ .description {
27
+ font-size:15px !important;
28
+ }
29
+
30
+
31
+ /* Style streamlit header with bold text */
32
+ .header {
33
+ font-size: 20px;
34
+ font-weight: 700;
35
+ font-family: 'Arial', sans-serif;
36
+ color: #333; /* A modern dark gray */
37
+ display: flex;
38
+ align-items: center;
39
+ }
40
+
41
+
42
+ .stMultiSelect > div > div > div {
43
+ font-size: 15px;
44
+ }
45
+
46
+ /* Style columns */
47
+ [data-testid="column"] {
48
+ border-radius: 15px;
49
+ background-color: white;
50
+ box-shadow: 0 0 10px #eee;
51
+ border: 1px solid #ddd;
52
+ padding: 1rem;;
53
+ }
54
+ /* Style containers */
55
+ [data-testid="stVerticalBlock"] > [style*="flex-direction: column;"] > [data-testid="stVerticalBlock"] {
56
+ border-radius: 15px;
57
+ background-color: white;
58
+ box-shadow: 0 0 10px #eee;
59
+ border: 1px solid #ddd;
60
+ padding: 1rem;;
61
+ }
62
+
63
+ .stTabs [data-baseweb="tab-list"] button [data-testid="stMarkdownContainer"] p {
64
+ font-size:20px;
65
+ }