samuelrince commited on
Commit
85e37e1
1 Parent(s): 56b18b9

feat: massive update :)

Browse files
LICENSE CHANGED
@@ -1,202 +1,427 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
 
2
- Apache License
3
- Version 2.0, January 2004
4
- http://www.apache.org/licenses/
5
-
6
- TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
7
-
8
- 1. Definitions.
9
-
10
- "License" shall mean the terms and conditions for use, reproduction,
11
- and distribution as defined by Sections 1 through 9 of this document.
12
-
13
- "Licensor" shall mean the copyright owner or entity authorized by
14
- the copyright owner that is granting the License.
15
-
16
- "Legal Entity" shall mean the union of the acting entity and all
17
- other entities that control, are controlled by, or are under common
18
- control with that entity. For the purposes of this definition,
19
- "control" means (i) the power, direct or indirect, to cause the
20
- direction or management of such entity, whether by contract or
21
- otherwise, or (ii) ownership of fifty percent (50%) or more of the
22
- outstanding shares, or (iii) beneficial ownership of such entity.
23
-
24
- "You" (or "Your") shall mean an individual or Legal Entity
25
- exercising permissions granted by this License.
26
-
27
- "Source" form shall mean the preferred form for making modifications,
28
- including but not limited to software source code, documentation
29
- source, and configuration files.
30
-
31
- "Object" form shall mean any form resulting from mechanical
32
- transformation or translation of a Source form, including but
33
- not limited to compiled object code, generated documentation,
34
- and conversions to other media types.
35
-
36
- "Work" shall mean the work of authorship, whether in Source or
37
- Object form, made available under the License, as indicated by a
38
- copyright notice that is included in or attached to the work
39
- (an example is provided in the Appendix below).
40
-
41
- "Derivative Works" shall mean any work, whether in Source or Object
42
- form, that is based on (or derived from) the Work and for which the
43
- editorial revisions, annotations, elaborations, or other modifications
44
- represent, as a whole, an original work of authorship. For the purposes
45
- of this License, Derivative Works shall not include works that remain
46
- separable from, or merely link (or bind by name) to the interfaces of,
47
- the Work and Derivative Works thereof.
48
-
49
- "Contribution" shall mean any work of authorship, including
50
- the original version of the Work and any modifications or additions
51
- to that Work or Derivative Works thereof, that is intentionally
52
- submitted to Licensor for inclusion in the Work by the copyright owner
53
- or by an individual or Legal Entity authorized to submit on behalf of
54
- the copyright owner. For the purposes of this definition, "submitted"
55
- means any form of electronic, verbal, or written communication sent
56
- to the Licensor or its representatives, including but not limited to
57
- communication on electronic mailing lists, source code control systems,
58
- and issue tracking systems that are managed by, or on behalf of, the
59
- Licensor for the purpose of discussing and improving the Work, but
60
- excluding communication that is conspicuously marked or otherwise
61
- designated in writing by the copyright owner as "Not a Contribution."
62
-
63
- "Contributor" shall mean Licensor and any individual or Legal Entity
64
- on behalf of whom a Contribution has been received by Licensor and
65
- subsequently incorporated within the Work.
66
-
67
- 2. Grant of Copyright License. Subject to the terms and conditions of
68
- this License, each Contributor hereby grants to You a perpetual,
69
- worldwide, non-exclusive, no-charge, royalty-free, irrevocable
70
- copyright license to reproduce, prepare Derivative Works of,
71
- publicly display, publicly perform, sublicense, and distribute the
72
- Work and such Derivative Works in Source or Object form.
73
-
74
- 3. Grant of Patent License. Subject to the terms and conditions of
75
- this License, each Contributor hereby grants to You a perpetual,
76
- worldwide, non-exclusive, no-charge, royalty-free, irrevocable
77
- (except as stated in this section) patent license to make, have made,
78
- use, offer to sell, sell, import, and otherwise transfer the Work,
79
- where such license applies only to those patent claims licensable
80
- by such Contributor that are necessarily infringed by their
81
- Contribution(s) alone or by combination of their Contribution(s)
82
- with the Work to which such Contribution(s) was submitted. If You
83
- institute patent litigation against any entity (including a
84
- cross-claim or counterclaim in a lawsuit) alleging that the Work
85
- or a Contribution incorporated within the Work constitutes direct
86
- or contributory patent infringement, then any patent licenses
87
- granted to You under this License for that Work shall terminate
88
- as of the date such litigation is filed.
89
-
90
- 4. Redistribution. You may reproduce and distribute copies of the
91
- Work or Derivative Works thereof in any medium, with or without
92
- modifications, and in Source or Object form, provided that You
93
- meet the following conditions:
94
-
95
- (a) You must give any other recipients of the Work or
96
- Derivative Works a copy of this License; and
97
-
98
- (b) You must cause any modified files to carry prominent notices
99
- stating that You changed the files; and
100
-
101
- (c) You must retain, in the Source form of any Derivative Works
102
- that You distribute, all copyright, patent, trademark, and
103
- attribution notices from the Source form of the Work,
104
- excluding those notices that do not pertain to any part of
105
- the Derivative Works; and
106
-
107
- (d) If the Work includes a "NOTICE" text file as part of its
108
- distribution, then any Derivative Works that You distribute must
109
- include a readable copy of the attribution notices contained
110
- within such NOTICE file, excluding those notices that do not
111
- pertain to any part of the Derivative Works, in at least one
112
- of the following places: within a NOTICE text file distributed
113
- as part of the Derivative Works; within the Source form or
114
- documentation, if provided along with the Derivative Works; or,
115
- within a display generated by the Derivative Works, if and
116
- wherever such third-party notices normally appear. The contents
117
- of the NOTICE file are for informational purposes only and
118
- do not modify the License. You may add Your own attribution
119
- notices within Derivative Works that You distribute, alongside
120
- or as an addendum to the NOTICE text from the Work, provided
121
- that such additional attribution notices cannot be construed
122
- as modifying the License.
123
-
124
- You may add Your own copyright statement to Your modifications and
125
- may provide additional or different license terms and conditions
126
- for use, reproduction, or distribution of Your modifications, or
127
- for any such Derivative Works as a whole, provided Your use,
128
- reproduction, and distribution of the Work otherwise complies with
129
- the conditions stated in this License.
130
-
131
- 5. Submission of Contributions. Unless You explicitly state otherwise,
132
- any Contribution intentionally submitted for inclusion in the Work
133
- by You to the Licensor shall be under the terms and conditions of
134
- this License, without any additional terms or conditions.
135
- Notwithstanding the above, nothing herein shall supersede or modify
136
- the terms of any separate license agreement you may have executed
137
- with Licensor regarding such Contributions.
138
-
139
- 6. Trademarks. This License does not grant permission to use the trade
140
- names, trademarks, service marks, or product names of the Licensor,
141
- except as required for reasonable and customary use in describing the
142
- origin of the Work and reproducing the content of the NOTICE file.
143
-
144
- 7. Disclaimer of Warranty. Unless required by applicable law or
145
- agreed to in writing, Licensor provides the Work (and each
146
- Contributor provides its Contributions) on an "AS IS" BASIS,
147
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
148
- implied, including, without limitation, any warranties or conditions
149
- of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
150
- PARTICULAR PURPOSE. You are solely responsible for determining the
151
- appropriateness of using or redistributing the Work and assume any
152
- risks associated with Your exercise of permissions under this License.
153
-
154
- 8. Limitation of Liability. In no event and under no legal theory,
155
- whether in tort (including negligence), contract, or otherwise,
156
- unless required by applicable law (such as deliberate and grossly
157
- negligent acts) or agreed to in writing, shall any Contributor be
158
- liable to You for damages, including any direct, indirect, special,
159
- incidental, or consequential damages of any character arising as a
160
- result of this License or out of the use or inability to use the
161
- Work (including but not limited to damages for loss of goodwill,
162
- work stoppage, computer failure or malfunction, or any and all
163
- other commercial damages or losses), even if such Contributor
164
- has been advised of the possibility of such damages.
165
-
166
- 9. Accepting Warranty or Additional Liability. While redistributing
167
- the Work or Derivative Works thereof, You may choose to offer,
168
- and charge a fee for, acceptance of support, warranty, indemnity,
169
- or other liability obligations and/or rights consistent with this
170
- License. However, in accepting such obligations, You may act only
171
- on Your own behalf and on Your sole responsibility, not on behalf
172
- of any other Contributor, and only if You agree to indemnify,
173
- defend, and hold each Contributor harmless for any liability
174
- incurred by, or claims asserted against, such Contributor by reason
175
- of your accepting any such warranty or additional liability.
176
-
177
- END OF TERMS AND CONDITIONS
178
-
179
- APPENDIX: How to apply the Apache License to your work.
180
-
181
- To apply the Apache License to your work, attach the following
182
- boilerplate notice, with the fields enclosed by brackets "[]"
183
- replaced with your own identifying information. (Don't include
184
- the brackets!) The text should be enclosed in the appropriate
185
- comment syntax for the file format. We also recommend that a
186
- file or class name and description of purpose be included on the
187
- same "printed page" as the copyright notice for easier
188
- identification within third-party archives.
189
-
190
- Copyright [yyyy] [name of copyright owner]
191
-
192
- Licensed under the Apache License, Version 2.0 (the "License");
193
- you may not use this file except in compliance with the License.
194
- You may obtain a copy of the License at
195
-
196
- http://www.apache.org/licenses/LICENSE-2.0
197
-
198
- Unless required by applicable law or agreed to in writing, software
199
- distributed under the License is distributed on an "AS IS" BASIS,
200
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
201
- See the License for the specific language governing permissions and
202
- limitations under the License.
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ Attribution-ShareAlike 4.0 International
2
+
3
+ =======================================================================
4
+
5
+ Creative Commons Corporation ("Creative Commons") is not a law firm and
6
+ does not provide legal services or legal advice. Distribution of
7
+ Creative Commons public licenses does not create a lawyer-client or
8
+ other relationship. Creative Commons makes its licenses and related
9
+ information available on an "as-is" basis. Creative Commons gives no
10
+ warranties regarding its licenses, any material licensed under their
11
+ terms and conditions, or any related information. Creative Commons
12
+ disclaims all liability for damages resulting from their use to the
13
+ fullest extent possible.
14
+
15
+ Using Creative Commons Public Licenses
16
+
17
+ Creative Commons public licenses provide a standard set of terms and
18
+ conditions that creators and other rights holders may use to share
19
+ original works of authorship and other material subject to copyright
20
+ and certain other rights specified in the public license below. The
21
+ following considerations are for informational purposes only, are not
22
+ exhaustive, and do not form part of our licenses.
23
+
24
+ Considerations for licensors: Our public licenses are
25
+ intended for use by those authorized to give the public
26
+ permission to use material in ways otherwise restricted by
27
+ copyright and certain other rights. Our licenses are
28
+ irrevocable. Licensors should read and understand the terms
29
+ and conditions of the license they choose before applying it.
30
+ Licensors should also secure all rights necessary before
31
+ applying our licenses so that the public can reuse the
32
+ material as expected. Licensors should clearly mark any
33
+ material not subject to the license. This includes other CC-
34
+ licensed material, or material used under an exception or
35
+ limitation to copyright. More considerations for licensors:
36
+ wiki.creativecommons.org/Considerations_for_licensors
37
+
38
+ Considerations for the public: By using one of our public
39
+ licenses, a licensor grants the public permission to use the
40
+ licensed material under specified terms and conditions. If
41
+ the licensor's permission is not necessary for any reason--for
42
+ example, because of any applicable exception or limitation to
43
+ copyright--then that use is not regulated by the license. Our
44
+ licenses grant only permissions under copyright and certain
45
+ other rights that a licensor has authority to grant. Use of
46
+ the licensed material may still be restricted for other
47
+ reasons, including because others have copyright or other
48
+ rights in the material. A licensor may make special requests,
49
+ such as asking that all changes be marked or described.
50
+ Although not required by our licenses, you are encouraged to
51
+ respect those requests where reasonable. More considerations
52
+ for the public:
53
+ wiki.creativecommons.org/Considerations_for_licensees
54
+
55
+ =======================================================================
56
+
57
+ Creative Commons Attribution-ShareAlike 4.0 International Public
58
+ License
59
+
60
+ By exercising the Licensed Rights (defined below), You accept and agree
61
+ to be bound by the terms and conditions of this Creative Commons
62
+ Attribution-ShareAlike 4.0 International Public License ("Public
63
+ License"). To the extent this Public License may be interpreted as a
64
+ contract, You are granted the Licensed Rights in consideration of Your
65
+ acceptance of these terms and conditions, and the Licensor grants You
66
+ such rights in consideration of benefits the Licensor receives from
67
+ making the Licensed Material available under these terms and
68
+ conditions.
69
+
70
+
71
+ Section 1 -- Definitions.
72
+
73
+ a. Adapted Material means material subject to Copyright and Similar
74
+ Rights that is derived from or based upon the Licensed Material
75
+ and in which the Licensed Material is translated, altered,
76
+ arranged, transformed, or otherwise modified in a manner requiring
77
+ permission under the Copyright and Similar Rights held by the
78
+ Licensor. For purposes of this Public License, where the Licensed
79
+ Material is a musical work, performance, or sound recording,
80
+ Adapted Material is always produced where the Licensed Material is
81
+ synched in timed relation with a moving image.
82
+
83
+ b. Adapter's License means the license You apply to Your Copyright
84
+ and Similar Rights in Your contributions to Adapted Material in
85
+ accordance with the terms and conditions of this Public License.
86
+
87
+ c. BY-SA Compatible License means a license listed at
88
+ creativecommons.org/compatiblelicenses, approved by Creative
89
+ Commons as essentially the equivalent of this Public License.
90
+
91
+ d. Copyright and Similar Rights means copyright and/or similar rights
92
+ closely related to copyright including, without limitation,
93
+ performance, broadcast, sound recording, and Sui Generis Database
94
+ Rights, without regard to how the rights are labeled or
95
+ categorized. For purposes of this Public License, the rights
96
+ specified in Section 2(b)(1)-(2) are not Copyright and Similar
97
+ Rights.
98
+
99
+ e. Effective Technological Measures means those measures that, in the
100
+ absence of proper authority, may not be circumvented under laws
101
+ fulfilling obligations under Article 11 of the WIPO Copyright
102
+ Treaty adopted on December 20, 1996, and/or similar international
103
+ agreements.
104
+
105
+ f. Exceptions and Limitations means fair use, fair dealing, and/or
106
+ any other exception or limitation to Copyright and Similar Rights
107
+ that applies to Your use of the Licensed Material.
108
+
109
+ g. License Elements means the license attributes listed in the name
110
+ of a Creative Commons Public License. The License Elements of this
111
+ Public License are Attribution and ShareAlike.
112
+
113
+ h. Licensed Material means the artistic or literary work, database,
114
+ or other material to which the Licensor applied this Public
115
+ License.
116
+
117
+ i. Licensed Rights means the rights granted to You subject to the
118
+ terms and conditions of this Public License, which are limited to
119
+ all Copyright and Similar Rights that apply to Your use of the
120
+ Licensed Material and that the Licensor has authority to license.
121
+
122
+ j. Licensor means the individual(s) or entity(ies) granting rights
123
+ under this Public License.
124
+
125
+ k. Share means to provide material to the public by any means or
126
+ process that requires permission under the Licensed Rights, such
127
+ as reproduction, public display, public performance, distribution,
128
+ dissemination, communication, or importation, and to make material
129
+ available to the public including in ways that members of the
130
+ public may access the material from a place and at a time
131
+ individually chosen by them.
132
+
133
+ l. Sui Generis Database Rights means rights other than copyright
134
+ resulting from Directive 96/9/EC of the European Parliament and of
135
+ the Council of 11 March 1996 on the legal protection of databases,
136
+ as amended and/or succeeded, as well as other essentially
137
+ equivalent rights anywhere in the world.
138
+
139
+ m. You means the individual or entity exercising the Licensed Rights
140
+ under this Public License. Your has a corresponding meaning.
141
+
142
+
143
+ Section 2 -- Scope.
144
+
145
+ a. License grant.
146
+
147
+ 1. Subject to the terms and conditions of this Public License,
148
+ the Licensor hereby grants You a worldwide, royalty-free,
149
+ non-sublicensable, non-exclusive, irrevocable license to
150
+ exercise the Licensed Rights in the Licensed Material to:
151
+
152
+ a. reproduce and Share the Licensed Material, in whole or
153
+ in part; and
154
+
155
+ b. produce, reproduce, and Share Adapted Material.
156
+
157
+ 2. Exceptions and Limitations. For the avoidance of doubt, where
158
+ Exceptions and Limitations apply to Your use, this Public
159
+ License does not apply, and You do not need to comply with
160
+ its terms and conditions.
161
+
162
+ 3. Term. The term of this Public License is specified in Section
163
+ 6(a).
164
+
165
+ 4. Media and formats; technical modifications allowed. The
166
+ Licensor authorizes You to exercise the Licensed Rights in
167
+ all media and formats whether now known or hereafter created,
168
+ and to make technical modifications necessary to do so. The
169
+ Licensor waives and/or agrees not to assert any right or
170
+ authority to forbid You from making technical modifications
171
+ necessary to exercise the Licensed Rights, including
172
+ technical modifications necessary to circumvent Effective
173
+ Technological Measures. For purposes of this Public License,
174
+ simply making modifications authorized by this Section 2(a)
175
+ (4) never produces Adapted Material.
176
+
177
+ 5. Downstream recipients.
178
+
179
+ a. Offer from the Licensor -- Licensed Material. Every
180
+ recipient of the Licensed Material automatically
181
+ receives an offer from the Licensor to exercise the
182
+ Licensed Rights under the terms and conditions of this
183
+ Public License.
184
+
185
+ b. Additional offer from the Licensor -- Adapted Material.
186
+ Every recipient of Adapted Material from You
187
+ automatically receives an offer from the Licensor to
188
+ exercise the Licensed Rights in the Adapted Material
189
+ under the conditions of the Adapter's License You apply.
190
+
191
+ c. No downstream restrictions. You may not offer or impose
192
+ any additional or different terms or conditions on, or
193
+ apply any Effective Technological Measures to, the
194
+ Licensed Material if doing so restricts exercise of the
195
+ Licensed Rights by any recipient of the Licensed
196
+ Material.
197
 
198
+ 6. No endorsement. Nothing in this Public License constitutes or
199
+ may be construed as permission to assert or imply that You
200
+ are, or that Your use of the Licensed Material is, connected
201
+ with, or sponsored, endorsed, or granted official status by,
202
+ the Licensor or others designated to receive attribution as
203
+ provided in Section 3(a)(1)(A)(i).
204
+
205
+ b. Other rights.
206
+
207
+ 1. Moral rights, such as the right of integrity, are not
208
+ licensed under this Public License, nor are publicity,
209
+ privacy, and/or other similar personality rights; however, to
210
+ the extent possible, the Licensor waives and/or agrees not to
211
+ assert any such rights held by the Licensor to the limited
212
+ extent necessary to allow You to exercise the Licensed
213
+ Rights, but not otherwise.
214
+
215
+ 2. Patent and trademark rights are not licensed under this
216
+ Public License.
217
+
218
+ 3. To the extent possible, the Licensor waives any right to
219
+ collect royalties from You for the exercise of the Licensed
220
+ Rights, whether directly or through a collecting society
221
+ under any voluntary or waivable statutory or compulsory
222
+ licensing scheme. In all other cases the Licensor expressly
223
+ reserves any right to collect such royalties.
224
+
225
+
226
+ Section 3 -- License Conditions.
227
+
228
+ Your exercise of the Licensed Rights is expressly made subject to the
229
+ following conditions.
230
+
231
+ a. Attribution.
232
+
233
+ 1. If You Share the Licensed Material (including in modified
234
+ form), You must:
235
+
236
+ a. retain the following if it is supplied by the Licensor
237
+ with the Licensed Material:
238
+
239
+ i. identification of the creator(s) of the Licensed
240
+ Material and any others designated to receive
241
+ attribution, in any reasonable manner requested by
242
+ the Licensor (including by pseudonym if
243
+ designated);
244
+
245
+ ii. a copyright notice;
246
+
247
+ iii. a notice that refers to this Public License;
248
+
249
+ iv. a notice that refers to the disclaimer of
250
+ warranties;
251
+
252
+ v. a URI or hyperlink to the Licensed Material to the
253
+ extent reasonably practicable;
254
+
255
+ b. indicate if You modified the Licensed Material and
256
+ retain an indication of any previous modifications; and
257
+
258
+ c. indicate the Licensed Material is licensed under this
259
+ Public License, and include the text of, or the URI or
260
+ hyperlink to, this Public License.
261
+
262
+ 2. You may satisfy the conditions in Section 3(a)(1) in any
263
+ reasonable manner based on the medium, means, and context in
264
+ which You Share the Licensed Material. For example, it may be
265
+ reasonable to satisfy the conditions by providing a URI or
266
+ hyperlink to a resource that includes the required
267
+ information.
268
+
269
+ 3. If requested by the Licensor, You must remove any of the
270
+ information required by Section 3(a)(1)(A) to the extent
271
+ reasonably practicable.
272
+
273
+ b. ShareAlike.
274
+
275
+ In addition to the conditions in Section 3(a), if You Share
276
+ Adapted Material You produce, the following conditions also apply.
277
+
278
+ 1. The Adapter's License You apply must be a Creative Commons
279
+ license with the same License Elements, this version or
280
+ later, or a BY-SA Compatible License.
281
+
282
+ 2. You must include the text of, or the URI or hyperlink to, the
283
+ Adapter's License You apply. You may satisfy this condition
284
+ in any reasonable manner based on the medium, means, and
285
+ context in which You Share Adapted Material.
286
+
287
+ 3. You may not offer or impose any additional or different terms
288
+ or conditions on, or apply any Effective Technological
289
+ Measures to, Adapted Material that restrict exercise of the
290
+ rights granted under the Adapter's License You apply.
291
+
292
+
293
+ Section 4 -- Sui Generis Database Rights.
294
+
295
+ Where the Licensed Rights include Sui Generis Database Rights that
296
+ apply to Your use of the Licensed Material:
297
+
298
+ a. for the avoidance of doubt, Section 2(a)(1) grants You the right
299
+ to extract, reuse, reproduce, and Share all or a substantial
300
+ portion of the contents of the database;
301
+
302
+ b. if You include all or a substantial portion of the database
303
+ contents in a database in which You have Sui Generis Database
304
+ Rights, then the database in which You have Sui Generis Database
305
+ Rights (but not its individual contents) is Adapted Material,
306
+ including for purposes of Section 3(b); and
307
+
308
+ c. You must comply with the conditions in Section 3(a) if You Share
309
+ all or a substantial portion of the contents of the database.
310
+
311
+ For the avoidance of doubt, this Section 4 supplements and does not
312
+ replace Your obligations under this Public License where the Licensed
313
+ Rights include other Copyright and Similar Rights.
314
+
315
+
316
+ Section 5 -- Disclaimer of Warranties and Limitation of Liability.
317
+
318
+ a. UNLESS OTHERWISE SEPARATELY UNDERTAKEN BY THE LICENSOR, TO THE
319
+ EXTENT POSSIBLE, THE LICENSOR OFFERS THE LICENSED MATERIAL AS-IS
320
+ AND AS-AVAILABLE, AND MAKES NO REPRESENTATIONS OR WARRANTIES OF
321
+ ANY KIND CONCERNING THE LICENSED MATERIAL, WHETHER EXPRESS,
322
+ IMPLIED, STATUTORY, OR OTHER. THIS INCLUDES, WITHOUT LIMITATION,
323
+ WARRANTIES OF TITLE, MERCHANTABILITY, FITNESS FOR A PARTICULAR
324
+ PURPOSE, NON-INFRINGEMENT, ABSENCE OF LATENT OR OTHER DEFECTS,
325
+ ACCURACY, OR THE PRESENCE OR ABSENCE OF ERRORS, WHETHER OR NOT
326
+ KNOWN OR DISCOVERABLE. WHERE DISCLAIMERS OF WARRANTIES ARE NOT
327
+ ALLOWED IN FULL OR IN PART, THIS DISCLAIMER MAY NOT APPLY TO YOU.
328
+
329
+ b. TO THE EXTENT POSSIBLE, IN NO EVENT WILL THE LICENSOR BE LIABLE
330
+ TO YOU ON ANY LEGAL THEORY (INCLUDING, WITHOUT LIMITATION,
331
+ NEGLIGENCE) OR OTHERWISE FOR ANY DIRECT, SPECIAL, INDIRECT,
332
+ INCIDENTAL, CONSEQUENTIAL, PUNITIVE, EXEMPLARY, OR OTHER LOSSES,
333
+ COSTS, EXPENSES, OR DAMAGES ARISING OUT OF THIS PUBLIC LICENSE OR
334
+ USE OF THE LICENSED MATERIAL, EVEN IF THE LICENSOR HAS BEEN
335
+ ADVISED OF THE POSSIBILITY OF SUCH LOSSES, COSTS, EXPENSES, OR
336
+ DAMAGES. WHERE A LIMITATION OF LIABILITY IS NOT ALLOWED IN FULL OR
337
+ IN PART, THIS LIMITATION MAY NOT APPLY TO YOU.
338
+
339
+ c. The disclaimer of warranties and limitation of liability provided
340
+ above shall be interpreted in a manner that, to the extent
341
+ possible, most closely approximates an absolute disclaimer and
342
+ waiver of all liability.
343
+
344
+
345
+ Section 6 -- Term and Termination.
346
+
347
+ a. This Public License applies for the term of the Copyright and
348
+ Similar Rights licensed here. However, if You fail to comply with
349
+ this Public License, then Your rights under this Public License
350
+ terminate automatically.
351
+
352
+ b. Where Your right to use the Licensed Material has terminated under
353
+ Section 6(a), it reinstates:
354
+
355
+ 1. automatically as of the date the violation is cured, provided
356
+ it is cured within 30 days of Your discovery of the
357
+ violation; or
358
+
359
+ 2. upon express reinstatement by the Licensor.
360
+
361
+ For the avoidance of doubt, this Section 6(b) does not affect any
362
+ right the Licensor may have to seek remedies for Your violations
363
+ of this Public License.
364
+
365
+ c. For the avoidance of doubt, the Licensor may also offer the
366
+ Licensed Material under separate terms or conditions or stop
367
+ distributing the Licensed Material at any time; however, doing so
368
+ will not terminate this Public License.
369
+
370
+ d. Sections 1, 5, 6, 7, and 8 survive termination of this Public
371
+ License.
372
+
373
+
374
+ Section 7 -- Other Terms and Conditions.
375
+
376
+ a. The Licensor shall not be bound by any additional or different
377
+ terms or conditions communicated by You unless expressly agreed.
378
+
379
+ b. Any arrangements, understandings, or agreements regarding the
380
+ Licensed Material not stated herein are separate from and
381
+ independent of the terms and conditions of this Public License.
382
+
383
+
384
+ Section 8 -- Interpretation.
385
+
386
+ a. For the avoidance of doubt, this Public License does not, and
387
+ shall not be interpreted to, reduce, limit, restrict, or impose
388
+ conditions on any use of the Licensed Material that could lawfully
389
+ be made without permission under this Public License.
390
+
391
+ b. To the extent possible, if any provision of this Public License is
392
+ deemed unenforceable, it shall be automatically reformed to the
393
+ minimum extent necessary to make it enforceable. If the provision
394
+ cannot be reformed, it shall be severed from this Public License
395
+ without affecting the enforceability of the remaining terms and
396
+ conditions.
397
+
398
+ c. No term or condition of this Public License will be waived and no
399
+ failure to comply consented to unless expressly agreed to by the
400
+ Licensor.
401
+
402
+ d. Nothing in this Public License constitutes or may be interpreted
403
+ as a limitation upon, or waiver of, any privileges and immunities
404
+ that apply to the Licensor or You, including from the legal
405
+ processes of any jurisdiction or authority.
406
+
407
+
408
+ =======================================================================
409
+
410
+ Creative Commons is not a party to its public
411
+ licenses. Notwithstanding, Creative Commons may elect to apply one of
412
+ its public licenses to material it publishes and in those instances
413
+ will be considered the “Licensor.” The text of the Creative Commons
414
+ public licenses is dedicated to the public domain under the CC0 Public
415
+ Domain Dedication. Except for the limited purpose of indicating that
416
+ material is shared under a Creative Commons public license or as
417
+ otherwise permitted by the Creative Commons policies published at
418
+ creativecommons.org/policies, Creative Commons does not authorize the
419
+ use of the trademark "Creative Commons" or any other trademark or logo
420
+ of Creative Commons without its prior written consent including,
421
+ without limitation, in connection with any unauthorized modifications
422
+ to any of its public licenses or any other arrangements,
423
+ understandings, or agreements concerning use of licensed material. For
424
+ the avoidance of doubt, this paragraph does not form part of the
425
+ public licenses.
426
+
427
+ Creative Commons may be contacted at creativecommons.org.
README.md CHANGED
@@ -1,13 +1,13 @@
1
  ---
2
  title: EcoLogits Calculator
3
- emoji: 🌱
4
- colorFrom: gray
5
- colorTo: blue
6
  sdk: gradio
7
- sdk_version: 4.26.0
8
  app_file: app.py
9
  pinned: true
10
- license: apache-2.0
11
  ---
12
 
13
  Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
@@ -33,5 +33,7 @@ To do:
33
  - [X] Expose more inputs like the electricity mix
34
  - [X] Examples of electricity mixes
35
  - [X] Custom number of parameters
36
- - [ ] Live reload mode (Adrien)
37
- - [ ] Idea : "estimate a given prompt impact" function which allows to enter a prompt in a text field and estimate its impacts
 
 
 
1
  ---
2
  title: EcoLogits Calculator
3
+ emoji: 🧮
4
+ colorFrom: green
5
+ colorTo: indigo
6
  sdk: gradio
7
+ sdk_version: 4.36.1
8
  app_file: app.py
9
  pinned: true
10
+ license: cc-by-sa-4.0
11
  ---
12
 
13
  Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
 
33
  - [X] Expose more inputs like the electricity mix
34
  - [X] Examples of electricity mixes
35
  - [X] Custom number of parameters
36
+ - [x] Live reload mode
37
+ - [ ] Idea : "estimate a given prompt impact" function which allows to enter a prompt in a text field and estimate its impacts
38
+ - [ ] Idea: copy-paste a ChatGPT conversation link and estimate the impacts.
39
+ - [ ] Idea: compare with country electricity consumption
app.py CHANGED
@@ -1,137 +1,85 @@
 
1
  import gradio as gr
2
- from pint import UnitRegistry
3
 
4
- from data.mixes import MIXES, find_mix
5
 
6
  from ecologits.tracers.utils import compute_llm_impacts, _avg
7
  from ecologits.impacts.llm import compute_llm_impacts as compute_llm_impacts_expert
8
  from ecologits.impacts.llm import IF_ELECTRICITY_MIX_GWP, IF_ELECTRICITY_MIX_ADPE, IF_ELECTRICITY_MIX_PE
9
  from ecologits.model_repository import models
10
 
11
- u = UnitRegistry()
12
- u.define('kWh = kilowatt_hour')
13
- u.define('Wh = watt_hour')
14
- u.define('gCO2eq = gram')
15
- u.define('kgCO2eq = kilogram')
16
- u.define('kgSbeq = kilogram')
17
- u.define('MJ = megajoule')
18
- u.define('kJ = kilojoule')
19
- u.define('m = meter')
20
- u.define('km = kilometer')
21
- u.define('episodes = number of episodes')
22
- q = u.Quantity
23
-
24
-
25
- MODELS = [
26
- ("OpenAI / GPT-3.5-Turbo", "openai/gpt-3.5-turbo"),
27
- ("OpenAI / GPT-4", "openai/gpt-4"),
28
- ("Anthropic / Claude 3 Opus", "anthropic/claude-3-opus-20240229"),
29
- ("Anthropic / Claude 3 Sonnet", "anthropic/claude-3-sonnet-20240229"),
30
- ("Anthropic / Claude 3 Haiku", "anthropic/claude-3-haiku-20240307"),
31
- ("Anthropic / Claude 2.1", "anthropic/claude-2.1"),
32
- ("Anthropic / Claude 2.0", "anthropic/claude-2.0"),
33
- ("Anthropic / Claude Instant 1.2", "anthropic/claude-instant-1.2"),
34
- ("Mistral AI / Mistral 7B", "mistralai/open-mistral-7b"),
35
- ("Mistral AI / Mixtral 8x7B", "mistralai/open-mixtral-8x7b"),
36
- ("Mistral AI / Mixtral 8x22B", "mistralai/open-mixtral-8x22b"),
37
- ("Mistral AI / Tiny", "mistralai/mistral-tiny-2312"),
38
- ("Mistral AI / Small", "mistralai/mistral-small-2402"),
39
- ("Mistral AI / Medium", "mistralai/mistral-medium-2312"),
40
- ("Mistral AI / Large", "mistralai/mistral-large-2402"),
41
- ("Meta / Llama 3 8B", "huggingface_hub/meta-llama/Meta-Llama-3-8B"),
42
- ("Meta / Llama 3 70B", "huggingface_hub/meta-llama/Meta-Llama-3-70B"),
43
- ("Meta / Llama 2 7B", "huggingface_hub/meta-llama/Llama-2-7b-hf"),
44
- ("Meta / Llama 2 13B", "huggingface_hub/meta-llama/Llama-2-13b-hf"),
45
- ("Meta / Llama 2 70B", "huggingface_hub/meta-llama/Llama-2-70b-hf"),
46
- ("Cohere / Command Light", "cohere/command-light"),
47
- ("Cohere / Command", "cohere/command"),
48
- ("Cohere / Command R", "cohere/command-r"),
49
- ("Cohere / Command R+", "cohere/command-r-plus"),
50
- ]
51
-
52
- PROMPTS = [
53
- ("Write a Tweet", 50),
54
- ("Write an email", 170),
55
- ("Write an article summary", 250),
56
- ("Small conversation with a chatbot", 400),
57
- ("Write a report of 5 pages", 5000),
58
- ]
59
- PROMPTS = [(s + f" ({v} output tokens)", v) for (s, v) in PROMPTS]
60
-
61
-
62
- def format_indicator(name: str, value: str, unit: str) -> str:
63
- return f"""
64
- ## {name}
65
- $$ \LARGE {value} \ \large {unit} $$
66
- """
67
-
68
-
69
- def form_output(impacts):
70
- energy_ = q(impacts.energy.value, impacts.energy.unit)
71
- eq_energy_ = q(impacts.energy.value * 2, 'km')
72
- if energy_ < q("1 kWh"):
73
- energy_ = energy_.to("Wh")
74
- eq_energy_ = q(impacts.energy.value * 2000, 'm')
75
-
76
- gwp_ = q(impacts.gwp.value, impacts.gwp.unit)
77
- eq_gwp_ = q(impacts.gwp.value / 0.032, 'episodes')
78
- if gwp_ < q("1 kgCO2eq"):
79
- gwp_ = gwp_.to("1 gCO2eq")
80
- eq_gwp_ = q(impacts.gwp.value / 0.032, 'episodes')
81
- adpe_ = q(impacts.adpe.value, impacts.adpe.unit)
82
-
83
- pe_ = q(impacts.pe.value, impacts.pe.unit)
84
- if pe_ < q("1 MJ"):
85
- pe_ = pe_.to("kJ")
86
-
87
- return (
88
- format_indicator("⚡️ Energy", f"{energy_.magnitude:.3g}", energy_.units),
89
- format_indicator("🌍 GHG Emissions", f"{gwp_.magnitude:.3g}", gwp_.units),
90
- format_indicator("🪨 Abiotic Resources", f"{adpe_.magnitude:.3g}", adpe_.units),
91
- format_indicator("⛽️ Primary Energy", f"{pe_.magnitude:.3g}", pe_.units),
92
- format_indicator("🔋 Equivalent energy: distance with a small electric car", f"{eq_energy_.magnitude:.3g}", eq_energy_.units),
93
- format_indicator("🏰 Equivalent emissions for 1000 prompts: watching GoT in streaming", f"{eq_gwp_.magnitude:.3g}", eq_gwp_.units)
94
- )
95
-
96
-
97
- def form(
98
- model_name: str,
99
- prompt_generated_tokens: int
100
- ):
101
- provider, model_name = model_name.split('/', 1)
102
- impacts = compute_llm_impacts(
103
- provider=provider,
104
- model_name=model_name,
105
- output_token_count=prompt_generated_tokens,
106
- request_latency=100000
107
- )
108
- return form_output(impacts)
109
-
110
-
111
- def form_expert(
112
- model_active_params: float,
113
- model_total_params: float,
114
- prompt_generated_tokens: int,
115
- mix_gwp: float,
116
- mix_adpe: float,
117
- mix_pe: float
118
- ):
119
- impacts = compute_llm_impacts_expert(
120
- model_active_parameter_count=model_active_params,
121
- model_total_parameter_count=model_total_params,
122
- output_token_count=prompt_generated_tokens,
123
- request_latency=100000,
124
- if_electricity_mix_gwp=mix_gwp,
125
- if_electricity_mix_adpe=mix_adpe,
126
- if_electricity_mix_pe=mix_pe
127
- )
128
- return form_output(impacts)
129
-
130
 
131
  CUSTOM = "Custom"
132
- def custom():
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
133
  return CUSTOM
134
 
 
135
  def model_active_params_fn(model_name: str, n_param: float):
136
  if model_name == CUSTOM:
137
  return n_param
@@ -139,6 +87,7 @@ def model_active_params_fn(model_name: str, n_param: float):
139
  model = models.find_model(provider=provider, model_name=model_name)
140
  return model.active_parameters or _avg(model.active_parameters_range)
141
 
 
142
  def model_total_params_fn(model_name: str, n_param: float):
143
  if model_name == CUSTOM:
144
  return n_param
@@ -146,82 +95,163 @@ def model_total_params_fn(model_name: str, n_param: float):
146
  model = models.find_model(provider=provider, model_name=model_name)
147
  return model.total_parameters or _avg(model.total_parameters_range)
148
 
 
149
  def mix_fn(country_code: str, mix_adpe: float, mix_pe: float, mix_gwp: float):
150
  if country_code == CUSTOM:
151
  return mix_adpe, mix_pe, mix_gwp
152
- return find_mix(country_code)
153
-
154
- with gr.Blocks() as demo:
155
 
156
- ### TITLE
157
- gr.Markdown("""
158
- # 🌱 EcoLogits Calculator
159
-
160
- **EcoLogits** is a python library that tracks the **energy consumption** and **environmental footprint** of using
161
- **generative AI** models through APIs.
162
 
163
- Read the documentation:
164
- [ecologits.ai](https://ecologits.ai) | ⭐️ us on GitHub: [genai-impact/ecologits](https://github.com/genai-impact/ecologits) |
165
- ✅ Follow us on Linkedin: [GenAI Impact](https://www.linkedin.com/company/genai-impact/posts/?feedView=all)
166
- """)
167
-
168
- ### SIMPLE CALCULATOR
169
- with gr.Tab("Home"):
170
- gr.Markdown("""
171
- ## 😊 Calculator
172
- """)
173
 
 
 
 
174
  with gr.Row():
175
- model = gr.Dropdown(
176
- MODELS,
177
- label="Model name",
178
- value="openai/gpt-3.5-turbo",
179
  filterable=True,
180
- )
181
- prompt = gr.Dropdown(
182
- PROMPTS,
183
- label="Example prompt",
184
- value=50
185
  )
186
 
187
- with gr.Row():
188
- energy = gr.Markdown(
189
- label="energy",
190
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
191
- )
192
- gwp = gr.Markdown(
193
- label="gwp",
194
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
195
- )
196
- adpe = gr.Markdown(
197
- label="adpe",
198
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
199
  )
200
- pe = gr.Markdown(
201
- label="pe",
202
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
 
 
 
203
  )
204
-
205
- gr.Markdown('---')
206
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
207
  with gr.Row():
208
- equivalent_1 = gr.Markdown(
209
- label="eq_energy",
210
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
211
- )
212
- equivalent_2 = gr.Markdown(
213
- label="eq_gwp",
214
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
215
- )
216
-
217
- submit_btn = gr.Button("Submit")
218
- submit_btn.click(fn=form, inputs=[model, prompt], outputs=[energy, gwp, adpe, pe, equivalent_1, equivalent_2])
219
-
220
- ### EXPERT CALCULATOR
221
- with gr.Tab("Expert Mode"):
222
- gr.Markdown("""
223
- ## 🤓 Expert mode
224
- """)
225
  model = gr.Dropdown(
226
  MODELS + [CUSTOM],
227
  label="Model name",
@@ -229,145 +259,140 @@ with gr.Blocks() as demo:
229
  filterable=True,
230
  interactive=True
231
  )
232
- model_active_params = gr.Number(
233
  label="Number of billions of active parameters",
234
  value=45.0,
235
- interactive=True
236
  )
237
- model_total_params = gr.Number(
238
  label="Number of billions of total parameters",
239
  value=45.0,
240
- interactive=True
241
  )
242
-
243
- model.change(fn=model_active_params_fn, inputs=[model, model_active_params], outputs=[model_active_params])
244
- model.change(fn=model_total_params_fn, inputs=[model, model_total_params], outputs=[model_total_params])
245
- model_active_params.input(fn=custom, outputs=[model])
246
- model_total_params.input(fn=custom, outputs=[model])
 
 
 
 
247
 
248
  tokens = gr.Number(
249
- label="Output tokens",
250
  value=100
251
  )
252
 
253
  mix = gr.Dropdown(
254
- MIXES + [CUSTOM],
255
  label="Location",
256
- value="WOR",
257
  filterable=True,
258
  interactive=True
259
  )
260
- mix_adpe = gr.Number(
261
- label="Electricity mix - Abiotic resources [kgSbeq / kWh]",
262
- value=IF_ELECTRICITY_MIX_ADPE,
263
  interactive=True
264
  )
265
- mix_pe = gr.Number(
266
- label="Electricity mix - Primary energy [MJ / kWh]",
267
- value=IF_ELECTRICITY_MIX_PE,
268
  interactive=True
269
  )
270
- mix_gwp = gr.Number(
271
- label="Electricity mix - GHG emissions [kgCO2eq / kWh]",
272
- value=IF_ELECTRICITY_MIX_GWP,
273
  interactive=True
274
  )
275
 
276
- mix.change(fn=mix_fn, inputs=[mix, mix_adpe, mix_pe, mix_gwp], outputs=[mix_adpe, mix_pe, mix_gwp])
277
- mix_adpe.input(fn=custom, outputs=mix)
278
- mix_pe.input(fn=custom, outputs=mix)
279
- mix_gwp.input(fn=custom, outputs=mix)
280
-
281
- with gr.Row():
282
- energy = gr.Markdown(
283
- label="energy",
284
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
285
- )
286
- gwp = gr.Markdown(
287
- label="gwp",
288
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
289
- )
290
- adpe = gr.Markdown(
291
- label="adpe",
292
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
293
- )
294
- pe = gr.Markdown(
295
- label="pe",
296
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
297
- )
298
-
299
- with gr.Row():
300
- energy = gr.Markdown(
301
- label="energy",
302
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
 
 
 
 
 
303
  )
304
- gwp = gr.Markdown(
305
- label="gwp",
306
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
307
- )
308
- adpe = gr.Markdown(
309
- label="adpe",
310
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
311
- )
312
- pe = gr.Markdown(
313
- label="pe",
314
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
315
- )
316
-
317
- gr.Markdown('---')
318
-
319
- with gr.Row():
320
- equivalent_1 = gr.Markdown(
321
- label="eq_energy",
322
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
323
- )
324
- equivalent_2 = gr.Markdown(
325
- label="eq_gwp",
326
- latex_delimiters=[{"left": "$$", "right": "$$", "display": False}]
327
- )
328
-
329
- submit_btn = gr.Button("Submit")
330
- submit_btn.click(
331
- fn=form_expert,
332
- inputs=[model_active_params, model_total_params, tokens, mix_gwp, mix_adpe, mix_pe],
333
- outputs=[energy, gwp, adpe, pe, equivalent_1, equivalent_2]
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
334
  )
335
 
336
- ### METHOD QUICK EXPLANATION
337
- with gr.Tab('Methodology'):
338
- gr.Markdown("""## 📖 Methodology
339
- 🚧 Under construction
340
- """)
341
-
342
- ### INFORMATION ABOUT INDICATORS
343
- with gr.Accordion("📊 More about the indicators", open = False):
344
- gr.Markdown("""
345
- - ⚡️ **Energy**: Final energy consumption,
346
- - 🌍 **GHG Emissions**: Potential impact on global warming (commonly known as GHG/carbon emissions),
347
- - 🪨 **Abiotic Resources**: Impact on the depletion of non-living resources such as minerals or metals,
348
- - ⛽️ **Primary Energy**: Total energy consumed from primary sources.
349
- """)
350
-
351
- ### INFORMATION ABOUT REDUCING IMPACTS
352
- with gr.Accordion("📉 How to reduce / limit these impacts ?", open = False):
353
- gr.Markdown("""
354
-
355
- * ❓ **Fundamental rule**: Show **sobriety** on the uses of (generative) AI
356
- * Questionning the usefulness of the project;
357
- * Estimating impacts of the project;
358
- * Evaluating the project purpose;
359
- * Restricting the use case to the desired purposes.
360
-
361
- * 🦾 On the hardware side
362
- * If you can, try to relocate the computing in low emissions and/or energy efficient datacenters.
363
-
364
- * 🤖 On the ML side :
365
- * Develop a zero-shot learning approach for general tasks;
366
- * Prefer the smaller and yet well-peforming models (using number of parameters for example);
367
- * If a specialization is needed, always prefer fine-tuning an existing model than re-training one from scratch;
368
- * During model inference, try caching the most popular prompts ("hey, tell me a joke about ...").
369
-
370
- """)
371
 
372
  if __name__ == '__main__':
373
  demo.launch()
 
1
+
2
  import gradio as gr
 
3
 
 
4
 
5
  from ecologits.tracers.utils import compute_llm_impacts, _avg
6
  from ecologits.impacts.llm import compute_llm_impacts as compute_llm_impacts_expert
7
  from ecologits.impacts.llm import IF_ELECTRICITY_MIX_GWP, IF_ELECTRICITY_MIX_ADPE, IF_ELECTRICITY_MIX_PE
8
  from ecologits.model_repository import models
9
 
10
+ from src.assets import custom_css
11
+ from src.electricity_mix import COUNTRY_CODES, find_electricity_mix
12
+ from src.content import (
13
+ HERO_TEXT,
14
+ ABOUT_TEXT,
15
+ CITATION_LABEL,
16
+ CITATION_TEXT,
17
+ LICENCE_TEXT, METHODOLOGY_TEXT
18
+ )
19
+ from src.constants import (
20
+ PROVIDERS,
21
+ OPENAI_MODELS,
22
+ ANTHROPIC_MODELS,
23
+ COHERE_MODELS,
24
+ META_MODELS,
25
+ MISTRALAI_MODELS,
26
+ PROMPTS,
27
+ MODELS
28
+ )
29
+ from src.utils import (
30
+ format_impacts,
31
+ format_energy_eq_physical_activity,
32
+ PhysicalActivity,
33
+ format_energy_eq_electric_vehicle,
34
+ format_gwp_eq_streaming, format_energy_eq_electricity_production, EnergyProduction,
35
+ format_gwp_eq_airplane_paris_nyc, format_energy_eq_electricity_consumption_ireland
36
+ )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
37
 
38
  CUSTOM = "Custom"
39
+
40
+
41
+ def model_list(provider: str) -> gr.Dropdown:
42
+ if provider == "openai":
43
+ return gr.Dropdown(
44
+ OPENAI_MODELS,
45
+ label="Model",
46
+ value=OPENAI_MODELS[0][1],
47
+ filterable=True,
48
+ )
49
+ elif provider == "anthropic":
50
+ return gr.Dropdown(
51
+ ANTHROPIC_MODELS,
52
+ label="Model",
53
+ value=ANTHROPIC_MODELS[0][1],
54
+ filterable=True,
55
+ )
56
+ elif provider == "cohere":
57
+ return gr.Dropdown(
58
+ COHERE_MODELS,
59
+ label="Model",
60
+ value=COHERE_MODELS[0][1],
61
+ filterable=True,
62
+ )
63
+ elif provider == "huggingface_hub/meta":
64
+ return gr.Dropdown(
65
+ META_MODELS,
66
+ label="Model",
67
+ value=META_MODELS[0][1],
68
+ filterable=True,
69
+ )
70
+ elif provider == "mistralai":
71
+ return gr.Dropdown(
72
+ MISTRALAI_MODELS,
73
+ label="Model",
74
+ value=MISTRALAI_MODELS[0][1],
75
+ filterable=True,
76
+ )
77
+
78
+
79
+ def custom():
80
  return CUSTOM
81
 
82
+
83
  def model_active_params_fn(model_name: str, n_param: float):
84
  if model_name == CUSTOM:
85
  return n_param
 
87
  model = models.find_model(provider=provider, model_name=model_name)
88
  return model.active_parameters or _avg(model.active_parameters_range)
89
 
90
+
91
  def model_total_params_fn(model_name: str, n_param: float):
92
  if model_name == CUSTOM:
93
  return n_param
 
95
  model = models.find_model(provider=provider, model_name=model_name)
96
  return model.total_parameters or _avg(model.total_parameters_range)
97
 
98
+
99
  def mix_fn(country_code: str, mix_adpe: float, mix_pe: float, mix_gwp: float):
100
  if country_code == CUSTOM:
101
  return mix_adpe, mix_pe, mix_gwp
102
+ return find_electricity_mix(country_code)
 
 
103
 
 
 
 
 
 
 
104
 
105
+ with gr.Blocks(css=custom_css) as demo:
106
+ gr.Markdown(HERO_TEXT)
 
 
 
 
 
 
 
 
107
 
108
+ with gr.Tab("🧮 Calculator"):
109
+ with gr.Row():
110
+ gr.Markdown("# Estimate the environmental impacts of LLM inference")
111
  with gr.Row():
112
+ input_provider = gr.Dropdown(
113
+ PROVIDERS,
114
+ label="Provider",
115
+ value=PROVIDERS[0][1],
116
  filterable=True,
 
 
 
 
 
117
  )
118
 
119
+ input_model = gr.Dropdown(
120
+ OPENAI_MODELS,
121
+ label="Model",
122
+ value=OPENAI_MODELS[0][1],
123
+ filterable=True,
 
 
 
 
 
 
 
124
  )
125
+ input_provider.change(model_list, input_provider, input_model)
126
+
127
+ input_prompt = gr.Dropdown(
128
+ PROMPTS,
129
+ label="Example prompt",
130
+ value=50,
131
  )
132
+
133
+
134
+ @gr.render(inputs=[input_provider, input_model, input_prompt])
135
+ def render_simple(provider, model, prompt):
136
+ if provider.startswith("huggingface_hub"):
137
+ provider = provider.split("/")[0]
138
+ if models.find_model(provider, model) is not None:
139
+ impacts = compute_llm_impacts(
140
+ provider=provider,
141
+ model_name=model,
142
+ output_token_count=prompt,
143
+ request_latency=100000
144
+ )
145
+ impacts = format_impacts(impacts)
146
+
147
+ # Inference impacts
148
+ with gr.Blocks():
149
+ with gr.Row():
150
+ gr.Markdown("""
151
+ ## Environmental impacts
152
+
153
+ To understand how the environmental impacts are computed go to the 📖 Methodology tab.
154
+ """)
155
+ with gr.Row():
156
+ with gr.Column(scale=1, min_width=220):
157
+ gr.Markdown(f"""
158
+ <h2 align="center">⚡️ Energy</h2>
159
+ $$ \Large {impacts.energy.magnitude:.3g} \ \large {impacts.energy.units} $$
160
+ <p align="center"><i>Evaluates the electricity consumption<i></p><br>
161
+ """)
162
+ with gr.Column(scale=1, min_width=220):
163
+ gr.Markdown(f"""
164
+ <h2 align="center">🌍️ GHG Emissions</h2>
165
+ $$ \Large {impacts.gwp.magnitude:.3g} \ \large {impacts.gwp.units} $$
166
+ <p align="center"><i>Evaluates the effect on global warming<i></p><br>
167
+ """)
168
+ with gr.Column(scale=1, min_width=220):
169
+ gr.Markdown(f"""
170
+ <h2 align="center">🪨 Abiotic Resources</h2>
171
+ $$ \Large {impacts.adpe.magnitude:.3g} \ \large {impacts.adpe.units} $$
172
+ <p align="center"><i>Evaluates the use of metals and minerals<i></p><br>
173
+ """)
174
+ with gr.Column(scale=1, min_width=220):
175
+ gr.Markdown(f"""
176
+ <h2 align="center">⛽️ Primary Energy</h2>
177
+ $$ \Large {impacts.pe.magnitude:.3g} \ \large {impacts.pe.units} $$
178
+ <p align="center"><i>Evaluates the use of energy resources<i></p><br>
179
+ """)
180
+
181
+ # Impacts equivalents
182
+ with gr.Blocks():
183
+ with gr.Row():
184
+ gr.Markdown("""
185
+ ---
186
+ ## That's equivalent to...
187
+
188
+ Making this request to the LLM is equivalent to the following actions.
189
+ """)
190
+ with gr.Row():
191
+ physical_activity, distance = format_energy_eq_physical_activity(impacts.energy)
192
+ if physical_activity == PhysicalActivity.WALKING:
193
+ physical_activity = "🚶‍♂️‍➡️ " + physical_activity.capitalize()
194
+ if physical_activity == PhysicalActivity.RUNNING:
195
+ physical_activity = "🏃‍♂️‍➡️ " + physical_activity.capitalize()
196
+ with gr.Column(scale=1, min_width=300):
197
+ gr.Markdown(f"""
198
+ <h2 align="center">{physical_activity} $$ \Large {distance.magnitude:.3g}\ {distance.units} $$ </h2>
199
+ <p align="center"><i>Based on energy consumption<i></p><br>
200
+ """, latex_delimiters=[{"left": "$$", "right": "$$", "display": False}])
201
+
202
+ ev_eq = format_energy_eq_electric_vehicle(impacts.energy)
203
+ with gr.Column(scale=1, min_width=300):
204
+ gr.Markdown(f"""
205
+ <h2 align="center">🔋 Electric Vehicle $$ \Large {ev_eq.magnitude:.3g}\ {ev_eq.units} $$ </h2>
206
+ <p align="center"><i>Based on energy consumption<i></p><br>
207
+ """, latex_delimiters=[{"left": "$$", "right": "$$", "display": False}])
208
+
209
+ streaming_eq = format_gwp_eq_streaming(impacts.gwp)
210
+ with gr.Column(scale=1, min_width=300):
211
+ gr.Markdown(f"""
212
+ <h2 align="center">⏯️ Streaming $$ \Large {streaming_eq.magnitude:.3g}\ {streaming_eq.units} $$ </h2>
213
+ <p align="center"><i>Based on GHG emissions<i></p><br>
214
+ """, latex_delimiters=[{"left": "$$", "right": "$$", "display": False}])
215
+
216
+ # Bigger scale impacts equivalent
217
+ with gr.Blocks():
218
+ with gr.Row():
219
+ gr.Markdown("""
220
+ ## What if 1% of the planet does this everyday for 1 year?
221
+
222
+ If this use case is largely deployed around the world the equivalent impacts would be.
223
+ """)
224
+ with gr.Row():
225
+ electricity_production, count = format_energy_eq_electricity_production(impacts.energy)
226
+ if electricity_production == EnergyProduction.NUCLEAR:
227
+ emoji = "☢️"
228
+ name = "Nuclear power plants"
229
+ if electricity_production == EnergyProduction.WIND:
230
+ emoji = "💨️ "
231
+ name = "Wind turbines"
232
+ with gr.Column(scale=1, min_width=300):
233
+ gr.Markdown(f"""
234
+ <h2 align="center">{emoji} $$ \Large {count:.0f} $$ {name} <span style="font-size: 12px">(yearly)</span></h2>
235
+ <p align="center"><i>Based on electricity consumption<i></p><br>
236
+ """, latex_delimiters=[{"left": "$$", "right": "$$", "display": False}])
237
+
238
+ ireland_count = format_energy_eq_electricity_consumption_ireland(impacts.energy)
239
+ with gr.Column(scale=1, min_width=300):
240
+ gr.Markdown(f"""
241
+ <h2 align="center">🇮🇪 $$ \Large {ireland_count:.2g} $$ x Ireland <span style="font-size: 12px">(yearly ⚡️ cons.)</span></h2>
242
+ <p align="center"><i>Based on electricity consumption<i></p><br>
243
+ """, latex_delimiters=[{"left": "$$", "right": "$$", "display": False}])
244
+
245
+ paris_nyc_airplane = format_gwp_eq_airplane_paris_nyc(impacts.gwp)
246
+ with gr.Column(scale=1, min_width=300):
247
+ gr.Markdown(f"""
248
+ <h2 align="center">✈️ $$ \Large {paris_nyc_airplane:,.0f} $$ Paris ↔ NYC </h2>
249
+ <p align="center"><i>Based on GHG emissions<i></p><br>
250
+ """, latex_delimiters=[{"left": "$$", "right": "$$", "display": False}])
251
+
252
+ with gr.Tab("🤓 Expert Mode"):
253
  with gr.Row():
254
+ gr.Markdown("# 🤓 Expert mode")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
255
  model = gr.Dropdown(
256
  MODELS + [CUSTOM],
257
  label="Model name",
 
259
  filterable=True,
260
  interactive=True
261
  )
262
+ input_model_active_params = gr.Number(
263
  label="Number of billions of active parameters",
264
  value=45.0,
265
+ interactive=True
266
  )
267
+ input_model_total_params = gr.Number(
268
  label="Number of billions of total parameters",
269
  value=45.0,
270
+ interactive=True
271
  )
272
+
273
+ model.change(fn=model_active_params_fn,
274
+ inputs=[model, input_model_active_params],
275
+ outputs=[input_model_active_params])
276
+ model.change(fn=model_total_params_fn,
277
+ inputs=[model, input_model_total_params],
278
+ outputs=[input_model_total_params])
279
+ input_model_active_params.input(fn=custom, outputs=[model])
280
+ input_model_total_params.input(fn=custom, outputs=[model])
281
 
282
  tokens = gr.Number(
283
+ label="Output tokens",
284
  value=100
285
  )
286
 
287
  mix = gr.Dropdown(
288
+ COUNTRY_CODES + [CUSTOM],
289
  label="Location",
290
+ value="WOR",
291
  filterable=True,
292
  interactive=True
293
  )
294
+ input_mix_gwp = gr.Number(
295
+ label="Electricity mix - GHG emissions [kgCO2eq / kWh]",
296
+ value=IF_ELECTRICITY_MIX_GWP,
297
  interactive=True
298
  )
299
+ input_mix_adpe = gr.Number(
300
+ label="Electricity mix - Abiotic resources [kgSbeq / kWh]",
301
+ value=IF_ELECTRICITY_MIX_ADPE,
302
  interactive=True
303
  )
304
+ input_mix_pe = gr.Number(
305
+ label="Electricity mix - Primary energy [MJ / kWh]",
306
+ value=IF_ELECTRICITY_MIX_PE,
307
  interactive=True
308
  )
309
 
310
+ mix.change(fn=mix_fn,
311
+ inputs=[mix, input_mix_gwp, input_mix_adpe, input_mix_pe],
312
+ outputs=[input_mix_gwp, input_mix_adpe, input_mix_pe])
313
+ input_mix_gwp.input(fn=custom, outputs=mix)
314
+ input_mix_adpe.input(fn=custom, outputs=mix)
315
+ input_mix_pe.input(fn=custom, outputs=mix)
316
+
317
+
318
+ @gr.render(inputs=[
319
+ input_model_active_params,
320
+ input_model_total_params,
321
+ input_prompt,
322
+ input_mix_gwp,
323
+ input_mix_adpe,
324
+ input_mix_pe
325
+ ])
326
+ def render_expert(
327
+ model_active_params,
328
+ model_total_params,
329
+ prompt,
330
+ mix_gwp,
331
+ mix_adpe,
332
+ mix_pe
333
+ ):
334
+ impacts = compute_llm_impacts_expert(
335
+ model_active_parameter_count=model_active_params,
336
+ model_total_parameter_count=model_total_params,
337
+ output_token_count=prompt,
338
+ request_latency=100000,
339
+ if_electricity_mix_gwp=mix_gwp,
340
+ if_electricity_mix_adpe=mix_adpe,
341
+ if_electricity_mix_pe=mix_pe
342
  )
343
+ impacts = format_impacts(impacts)
344
+
345
+ with gr.Blocks():
346
+ with gr.Row():
347
+ gr.Markdown("## Environmental impacts")
348
+ with gr.Row():
349
+ with gr.Column(scale=1, min_width=220):
350
+ gr.Markdown(f"""
351
+ <h2 align="center">⚡️ Energy</h2>
352
+ $$ \Large {impacts.energy.magnitude:.3g} \ \large {impacts.energy.units} $$
353
+ <p align="center"><i>Evaluates the electricity consumption<i></p><br>
354
+ """)
355
+ with gr.Column(scale=1, min_width=220):
356
+ gr.Markdown(f"""
357
+ <h2 align="center">🌍️ GHG Emissions</h2>
358
+ $$ \Large {impacts.gwp.magnitude:.3g} \ \large {impacts.gwp.units} $$
359
+ <p align="center"><i>Evaluates the effect on global warming<i></p><br>
360
+ """)
361
+ with gr.Column(scale=1, min_width=220):
362
+ gr.Markdown(f"""
363
+ <h2 align="center">🪨 Abiotic Resources</h2>
364
+ $$ \Large {impacts.adpe.magnitude:.3g} \ \large {impacts.adpe.units} $$
365
+ <p align="center"><i>Evaluates the use of metals and minerals<i></p><br>
366
+ """)
367
+ with gr.Column(scale=1, min_width=220):
368
+ gr.Markdown(f"""
369
+ <h2 align="center">⛽️ Primary Energy</h2>
370
+ $$ \Large {impacts.pe.magnitude:.3g} \ \large {impacts.pe.units} $$
371
+ <p align="center"><i>Evaluates the use of energy resources<i></p><br>
372
+ """)
373
+
374
+ with gr.Tab("📖 Methodology"):
375
+ gr.Markdown(METHODOLOGY_TEXT,
376
+ elem_classes="descriptive-text",
377
+ latex_delimiters=[
378
+ {"left": "$$", "right": "$$", "display": True},
379
+ {"left": "$", "right": "$", "display": False}
380
+ ])
381
+
382
+ with gr.Tab("ℹ️ About"):
383
+ gr.Markdown(ABOUT_TEXT, elem_classes="descriptive-text",)
384
+
385
+ with gr.Accordion("📚 Citation", open=False):
386
+ gr.Textbox(
387
+ value=CITATION_TEXT,
388
+ label=CITATION_LABEL,
389
+ interactive=False,
390
+ show_copy_button=True,
391
+ lines=len(CITATION_TEXT.split('\n')),
392
  )
393
 
394
+ # License
395
+ gr.Markdown(LICENCE_TEXT)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
396
 
397
  if __name__ == '__main__':
398
  demo.launch()
src/assets.py ADDED
@@ -0,0 +1,6 @@
 
 
 
 
 
 
 
1
+ custom_css = """
2
+
3
+ .descriptive-text span {
4
+ font-size: 16px !important;
5
+ }
6
+ """
src/constants.py ADDED
@@ -0,0 +1,82 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ PROVIDERS = [
2
+ ("OpenAI", "openai"),
3
+ ("Anthropic", "anthropic"),
4
+ ("Cohere", "cohere"),
5
+ ("Meta", "huggingface_hub/meta"),
6
+ ("Mistral AI", "mistralai"),
7
+ ]
8
+
9
+ OPENAI_MODELS = [
10
+ ("GPT-3.5-Turbo", "gpt-3.5-turbo"),
11
+ ("GPT-4", "gpt-4"),
12
+ ]
13
+
14
+ ANTHROPIC_MODELS = [
15
+ ("Claude 3 Opus", "claude-3-opus-20240229"),
16
+ ("Claude 3 Sonnet", "claude-3-sonnet-20240229"),
17
+ ("Claude 3 Haiku", "claude-3-haiku-20240307"),
18
+ ("Claude 2.1", "claude-2.1"),
19
+ ("Claude 2.0", "claude-2.0"),
20
+ ("Claude Instant 1.2", "claude-instant-1.2"),
21
+ ]
22
+
23
+ COHERE_MODELS = [
24
+ ("Command Light", "command-light"),
25
+ ("Command", "command"),
26
+ ("Command R", "command-r"),
27
+ ("Command R+", "command-r-plus"),
28
+ ]
29
+
30
+ META_MODELS = [
31
+ ("Llama 3 8B", "meta-llama/Meta-Llama-3-8B"),
32
+ ("Llama 3 70B", "meta-llama/Meta-Llama-3-70B"),
33
+ ("Llama 2 7B", "meta-llama/Llama-2-7b-hf"),
34
+ ("Llama 2 13B", "meta-llama/Llama-2-13b-hf"),
35
+ ("Llama 2 70B", "meta-llama/Llama-2-70b-hf"),
36
+ ]
37
+
38
+ MISTRALAI_MODELS = [
39
+ ("Mistral 7B", "open-mistral-7b"),
40
+ ("Mixtral 8x7B", "open-mixtral-8x7b"),
41
+ ("Mixtral 8x22B", "open-mixtral-8x22b"),
42
+ ("Tiny", "mistral-tiny-2312"),
43
+ ("Small", "mistral-small-2402"),
44
+ ("Medium", "mistral-medium-2312"),
45
+ ("Large", "mistral-large-2402"),
46
+ ]
47
+
48
+ PROMPTS = [
49
+ ("Write a Tweet", 50),
50
+ ("Write an email", 170),
51
+ ("Write an article summary", 250),
52
+ ("Small conversation with a chatbot", 400),
53
+ ("Write a report of 5 pages", 5000),
54
+ ]
55
+ PROMPTS = [(s + f" ({v} output tokens)", v) for (s, v) in PROMPTS]
56
+
57
+ MODELS = [
58
+ ("OpenAI / GPT-3.5-Turbo", "openai/gpt-3.5-turbo"),
59
+ ("OpenAI / GPT-4", "openai/gpt-4"),
60
+ ("Anthropic / Claude 3 Opus", "anthropic/claude-3-opus-20240229"),
61
+ ("Anthropic / Claude 3 Sonnet", "anthropic/claude-3-sonnet-20240229"),
62
+ ("Anthropic / Claude 3 Haiku", "anthropic/claude-3-haiku-20240307"),
63
+ ("Anthropic / Claude 2.1", "anthropic/claude-2.1"),
64
+ ("Anthropic / Claude 2.0", "anthropic/claude-2.0"),
65
+ ("Anthropic / Claude Instant 1.2", "anthropic/claude-instant-1.2"),
66
+ ("Mistral AI / Mistral 7B", "mistralai/open-mistral-7b"),
67
+ ("Mistral AI / Mixtral 8x7B", "mistralai/open-mixtral-8x7b"),
68
+ ("Mistral AI / Mixtral 8x22B", "mistralai/open-mixtral-8x22b"),
69
+ ("Mistral AI / Tiny", "mistralai/mistral-tiny-2312"),
70
+ ("Mistral AI / Small", "mistralai/mistral-small-2402"),
71
+ ("Mistral AI / Medium", "mistralai/mistral-medium-2312"),
72
+ ("Mistral AI / Large", "mistralai/mistral-large-2402"),
73
+ ("Meta / Llama 3 8B", "huggingface_hub/meta-llama/Meta-Llama-3-8B"),
74
+ ("Meta / Llama 3 70B", "huggingface_hub/meta-llama/Meta-Llama-3-70B"),
75
+ ("Meta / Llama 2 7B", "huggingface_hub/meta-llama/Llama-2-7b-hf"),
76
+ ("Meta / Llama 2 13B", "huggingface_hub/meta-llama/Llama-2-13b-hf"),
77
+ ("Meta / Llama 2 70B", "huggingface_hub/meta-llama/Llama-2-70b-hf"),
78
+ ("Cohere / Command Light", "cohere/command-light"),
79
+ ("Cohere / Command", "cohere/command"),
80
+ ("Cohere / Command R", "cohere/command-r"),
81
+ ("Cohere / Command R+", "cohere/command-r-plus"),
82
+ ]
src/content.py ADDED
@@ -0,0 +1,229 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+
2
+ HERO_TEXT = """
3
+ <div align="center">
4
+ <a href="https://ecologits.ai/">
5
+ <img style="max-height: 80px" alt="EcoLogits" src="https://raw.githubusercontent.com/genai-impact/ecologits/main/docs/assets/logo_light.png">
6
+ </a>
7
+ </div>
8
+
9
+ <h1 align="center">🧮 EcoLogits Calculator</h1>
10
+ <div align="center">
11
+ <p style="max-width: 500px; text-align: center">
12
+ <i><b>EcoLogits</b> is a python library that tracks the <b>energy consumption</b> and <b>environmental
13
+ footprint</b> of using <b>generative AI</b> models through APIs.</i>
14
+ </p>
15
+ </div>
16
+ <br>
17
+
18
+ This tool is developed and maintained by [GenAI Impact](https://genai-impact.org/) non-profit. Learn more about
19
+ 🌱 EcoLogits by reading the documentation on [ecologits.ai](https://ecologits.ai).
20
+
21
+ 🩷 Support us by giving a ⭐️ on our [GitHub repository](https://github.com/genai-impact/ecologits) and by following our [LinkedIn page](https://www.linkedin.com/company/genai-impact/).
22
+ """
23
+
24
+ ABOUT_TEXT = r"""
25
+ ## 🎯 Our goal
26
+
27
+ **The main goal of the EcoLogits Calculator is to raise awareness on the environmental impacts of LLM inference.**
28
+
29
+ The rapid evolution of generative AI is reshaping numerous industries and aspects of our daily lives. While these
30
+ advancements offer some benefits, they also **pose substantial environmental challenges that cannot be overlooked**.
31
+ Plus the issue of AI's environmental footprint as been mainly discussed at training stage but rarely at the inference
32
+ stage. That is an issue because **inference impacts for LLMs can largely overcome the training impacts when deployed
33
+ at large scales**.
34
+
35
+ At **[GenAI Impact](https://genai-impact.org/) we are dedicated to understanding and mitigating the environmental
36
+ impacts of generative AI** through rigorous research, innovative tools, and community engagement. Especially, in early
37
+ 2024 we have launched an new open-source tool called [EcoLogits](https://github.com/genai-impact/ecologits) that tracks
38
+ the energy consumption and environmental footprint of using generative AI models through APIs.
39
+
40
+ ## 🙋 FAQ
41
+
42
+ **Which generative AI models or providers are supported?**
43
+
44
+ To see the full list of **generative AI providers** currently supported by EcoLogits, see the following
45
+ [documentation page](https://ecologits.ai/providers/). As of today we only support LLMs but we plan to add support for
46
+ embeddings, image generation, multi-modal models and more. If you are interested don't hesitate to
47
+ [join us](https://genai-impact.org/contact/) and accelerate our work!
48
+
49
+ **How to reduce AI environmental impacts?**
50
+
51
+ * Look at **indirect impacts** of your project. Does the finality of your project is impacting negatively the
52
+ environment?
53
+ * **Be frugal** and question your usage or need of AI
54
+ * Do you really need AI to solve your problem?
55
+ * Do you really need GenAI to solve your problem? (you can read this [paper](https://aclanthology.org/2023.emnlp-industry.39.pdf))
56
+ * Use small and specialized models to solve your problem.
57
+ * Evaluate before, during and after the development of your project the environmental impacts with tools like
58
+ 🌱 [EcoLogits](https://github.com/genai-impact/ecologits) or [CodeCarbon](https://github.com/mlco2/codecarbon)
59
+ (see [more tools](https://github.com/samuelrince/awesome-green-ai))
60
+ * Restrict the use case and limit the usage of your tool or feature to the desired purpose.
61
+ * Do NOT buy new GPUs / hardware
62
+ * Hardware manufacturing for data centers is around 50% of the impact.
63
+ * Use cloud instances that are located in low emissions / high energy efficiency data centers
64
+ (see [electricitymaps.com](https://app.electricitymaps.com/map))
65
+ * Optimize your models for production
66
+ * Quantize your models.
67
+ * Use inference optimization tricks.
68
+ * Prefer fine-tuning of small and existing models over generalist models.
69
+
70
+ **What is the difference between **EcoLogits** and [CodeCarbon](https://github.com/mlco2/codecarbon)?**
71
+
72
+ EcoLogits is focused on estimating the environmental impacts of generative AI (only LLMs for now) used **through API
73
+ providers (such as OpenAI, Anthropic, Cloud APIs...)** whereas CodeCarbon is more general tool to measure energy
74
+ consumption and estimate GHG emissions measurement. If you deploy LLMs locally we encourage you to use CodeCarbon to
75
+ get real numbers of your energy consumption.
76
+
77
+ ## 🤗 Contributing
78
+
79
+ We are eager to get feedback from the community, don't hesitate to engage the discussion with us on this
80
+ [GitHub thread](https://github.com/genai-impact/ecologits/discussions/45) or message us on
81
+ [LinkedIn](https://www.linkedin.com/company/genai-impact/).
82
+
83
+ We also welcome any open-source contributions on 🌱 **[EcoLogits](https://github.com/genai-impact/ecologits)** or on
84
+ 🧮 **EcoLogits Calculator**.
85
+
86
+ ## ⚖️ License
87
+
88
+ <p xmlns:cc="http://creativecommons.org/ns#" >
89
+ This work is licensed under
90
+ <a href="https://creativecommons.org/licenses/by-sa/4.0/?ref=chooser-v1" target="_blank" rel="license noopener noreferrer" style="display:inline-block;">
91
+ CC BY-SA 4.0
92
+ </a>
93
+ <img style="display:inline-block;height:22px!important;margin-left:3px;vertical-align:text-bottom;" src="https://mirrors.creativecommons.org/presskit/icons/cc.svg?ref=chooser-v1" alt="">
94
+ <img style="display:inline-block;height:22px!important;margin-left:3px;vertical-align:text-bottom;" src="https://mirrors.creativecommons.org/presskit/icons/by.svg?ref=chooser-v1" alt="">
95
+ <img style="display:inline-block;height:22px!important;margin-left:3px;vertical-align:text-bottom;" src="https://mirrors.creativecommons.org/presskit/icons/sa.svg?ref=chooser-v1" alt="">
96
+ </p>
97
+
98
+ ## 🙌 Acknowledgement
99
+
100
+ We thank [Data For Good](https://dataforgood.fr/) and [Boavizta](https://boavizta.org/en) for supporting the
101
+ development of this project. Their contributions of tools, best practices, and expertise in environmental impact
102
+ assessment have been invaluable.
103
+
104
+ We also extend our gratitude to the open-source contributions of 🤗 [Hugging Face](git.lnyan.comm) on the LLM-Perf
105
+ Leaderboard.
106
+
107
+ ## 🤝 Contact
108
+
109
+ For general question on the project, please use the [GitHub thread](https://github.com/genai-impact/ecologits/discussions/45).
110
+ Otherwise use our contact form on [genai-impact.org/contact](https://genai-impact.org/contact/).
111
+ """
112
+
113
+
114
+ METHODOLOGY_TEXT = r"""
115
+ ## 📖 Methodology
116
+
117
+ We have developed a methodology to **estimate the energy consumption and environmental impacts for an LLM inference**
118
+ based on request parameters and hypotheses on the data center location, the hardware used, the model architecture and
119
+ more.
120
+
121
+ In this section we will only cover the principles of the methodology related to the 🧮 **EcoLogits Calculator**. If
122
+ you wish to learn more on the environmental impacts modeling of an LLM request checkout the
123
+ 🌱 [EcoLogits documentation page](https://ecologits.ai/methodology/).
124
+
125
+ ### Modeling impacts of an LLM request
126
+
127
+ The environmental impacts of an LLM inference are split into the **usage impacts** $I_{request}^u$ to account for
128
+ electricity consumption and the **embodied impacts** $I_{request}^e$ that relates to resource extraction, hardware
129
+ manufacturing and transportation. In general terms it can be expressed as follow:
130
+
131
+ $$ I_{request} = I_{request}^u + I_{request}^e $$
132
+
133
+ $$ I_{request} = E_{request}*F_{em}+\frac{\Delta T}{\Delta L}*I_{server}^e $$
134
+
135
+ With,
136
+
137
+ * $E_{request}$ the estimated energy consumption of the server and its cooling system.
138
+ * $F_{em}$ the electricity mix that depends on the country and time.
139
+ * $\frac{\Delta T}{\Delta L}$ the hardware usage ratio i.e. the computation time over the lifetime of the hardware.
140
+ * $I_{server}^e$ the embodied impacts of the server.
141
+
142
+ Additionally, to ⚡️ **direct energy consumption** the environmental impacts are expressed in **three dimensions
143
+ (multi-criteria impacts)** that are:
144
+
145
+ * 🌍 **Global Warming Potential** (GWP): Potential impact on global warming in kgCO2eq (commonly known as GHG/carbon
146
+ emissions).
147
+ * 🪨 **Abiotic Depletion Potential for Elements** (ADPe): Impact on the depletion of non-living resources such as
148
+ minerals or metals in kgSbeq.
149
+ * ⛽️ **Primary Energy** (PE): Total energy consumed from primary sources in MJ.
150
+
151
+ ### Principles, Data and Hypotheses
152
+
153
+ We use a **bottom-up methodology** to model impacts, meaning that we will estimate the impacts of low-level physical
154
+ components to then estimate the impacts at software level (in that case an LLM inference). We also rely on **Life
155
+ Cycle Approach (LCA) proxies and approach** to model both usage and embodied phases with multi-criteria impacts.
156
+ If you are interested in this approach we recommend you to read the following [Boavizta](https://boavizta.org/)
157
+ resources.
158
+
159
+ * [Digital & environment: How to evaluate server manufacturing footprint, beyond greenhouse gas emissions?](https://boavizta.org/en/blog/empreinte-de-la-fabrication-d-un-serveur)
160
+ * [Boavizta API automated evaluation of environmental impacts of ICT services and equipments](https://boavizta.org/en/blog/boavizta-api-automated-evaluation-of-ict-impacts-on-the-environment)
161
+ * [Boavizta API documentation](https://doc.api.boavizta.org/)
162
+
163
+ We leverage **open data to estimate the environmental impacts**, here is an exhaustive list of our data providers.
164
+
165
+ * [LLM-Perf Leaderboard](https://huggingface.co/spaces/optimum/llm-perf-leaderboard) to estimate GPU energy consumption
166
+ and latency based on the model architecture and number of output tokens.
167
+ * [Boavizta API](https://github.com/Boavizta/boaviztapi) to estimate server embodied impacts and base energy
168
+ consumption.
169
+ * [ADEME Base Empreinte®](https://base-empreinte.ademe.fr/) for electricity mix impacts per country.
170
+
171
+ Finally here are the **main hypotheses** we have made to compute the impacts.
172
+
173
+ * ⚠️ **We *"guesstimate"* the model architecture of proprietary LLMs when not disclosed by the provider.**
174
+ * Production setup: quantized models running on data center grade servers and GPUs such as A100.
175
+ * Electricity mix does not depend on time (help us enhance EcoLogits and work on this [issue](https://github.com/genai-impact/ecologits/issues/42))
176
+ * Ignore the following impacts: unused cloud resources, data center building, network and end-user devices... (for now)
177
+
178
+ ## Equivalents
179
+
180
+ ### 🚶‍♂️‍➡️ Walking or 🏃‍♂️‍➡️ running distance
181
+
182
+ 🔴 TODO
183
+
184
+ ### 🔋 Electric Vehicle distance
185
+
186
+ 🔴 TODO
187
+
188
+ ### ⏯️ Streaming time
189
+
190
+ 🔴 TODO
191
+
192
+ ### Number of 💨 wind turbines or ☢️ nuclear plants
193
+
194
+ 🔴 TODO
195
+
196
+ ### Multiplier of 🇮🇪 Ireland electricity consumption
197
+
198
+ 🔴 TODO
199
+
200
+ ### Number of ✈️ Paris ↔ New York City flights
201
+
202
+ 🔴 TODO
203
+
204
+ **If you are motivated to help us test and enhance this methodology
205
+ [contact us](https://genai-impact.org/contact/)!** 💪
206
+ """
207
+
208
+ CITATION_LABEL = "BibTeX citation for EcoLogits Calculator and the EcoLogits library:"
209
+ CITATION_TEXT = r"""@misc{ecologits-calculator,
210
+ author={Samuel Rincé, Adrien Banse and Valentin Defour},
211
+ title={EcoLogits Calculator},
212
+ year={2024},
213
+ howpublished= {\url{https://huggingface.co/spaces/genai-impact/ecologits-calculator}},
214
+ }
215
+ @software{ecologits,
216
+ author = {Samuel Rincé, Adrien Banse, Vinh Nguyen and Luc Berton},
217
+ publisher = {GenAI Impact},
218
+ title = {EcoLogits: track the energy consumption and environmental footprint of using generative AI models through APIs.},
219
+ }"""
220
+
221
+ LICENCE_TEXT = """<p xmlns:cc="http://creativecommons.org/ns#" >
222
+ This work is licensed under
223
+ <a href="https://creativecommons.org/licenses/by-sa/4.0/?ref=chooser-v1" target="_blank" rel="license noopener noreferrer" style="display:inline-block;">
224
+ CC BY-SA 4.0
225
+ </a>
226
+ <img style="display:inline-block;height:22px!important;margin-left:3px;vertical-align:text-bottom;" src="https://mirrors.creativecommons.org/presskit/icons/cc.svg?ref=chooser-v1" alt="">
227
+ <img style="display:inline-block;height:22px!important;margin-left:3px;vertical-align:text-bottom;" src="https://mirrors.creativecommons.org/presskit/icons/by.svg?ref=chooser-v1" alt="">
228
+ <img style="display:inline-block;height:22px!important;margin-left:3px;vertical-align:text-bottom;" src="https://mirrors.creativecommons.org/presskit/icons/sa.svg?ref=chooser-v1" alt="">
229
+ </p>"""
{data → src}/electricity_mix.csv RENAMED
File without changes
data/mixes.py → src/electricity_mix.py RENAMED
@@ -1,7 +1,7 @@
1
  from csv import DictReader
2
 
3
  PATH = "data/electricity_mix.csv"
4
- MIXES = [
5
  ("🌎 World", "WOR"),
6
  ("🇪🇺 Europe", "EEE"),
7
  ("🇿🇼 Zimbabwe", "ZWE"),
@@ -143,7 +143,8 @@ MIXES = [
143
  ("🇦🇪 United Arab Emirates", "ARE")
144
  ]
145
 
146
- def find_mix(code: str):
 
147
  # TODO: Maybe more optimal to construct database at the beginning of the app
148
  # in the same fashion as find_model
149
  res = []
@@ -151,4 +152,4 @@ def find_mix(code: str):
151
  csv = DictReader(fd)
152
  for row in csv:
153
  res += [float(row[code])]
154
- return res
 
1
  from csv import DictReader
2
 
3
  PATH = "data/electricity_mix.csv"
4
+ COUNTRY_CODES = [
5
  ("🌎 World", "WOR"),
6
  ("🇪🇺 Europe", "EEE"),
7
  ("🇿🇼 Zimbabwe", "ZWE"),
 
143
  ("🇦🇪 United Arab Emirates", "ARE")
144
  ]
145
 
146
+
147
+ def find_electricity_mix(code: str):
148
  # TODO: Maybe more optimal to construct database at the beginning of the app
149
  # in the same fashion as find_model
150
  res = []
 
152
  csv = DictReader(fd)
153
  for row in csv:
154
  res += [float(row[code])]
155
+ return res
src/utils.py ADDED
@@ -0,0 +1,182 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from dataclasses import dataclass
2
+ from enum import Enum
3
+
4
+ from ecologits.impacts.models import Impacts, Energy, GWP, ADPe, PE
5
+ from pint import UnitRegistry, Quantity
6
+
7
+
8
+ u = UnitRegistry()
9
+ u.define('Wh = watt_hour')
10
+ u.define('kWh = kilowatt_hour')
11
+ u.define('MWh = megawatt_hour')
12
+ u.define('GWh = gigawatt_hour')
13
+ u.define('TWh = terawatt_hour')
14
+ u.define('gCO2eq = gram')
15
+ u.define('kgCO2eq = kilogram')
16
+ u.define('tCO2eq = metricton')
17
+ u.define('kgSbeq = kilogram')
18
+ u.define('kJ = kilojoule')
19
+ u.define('MJ = megajoule')
20
+ u.define('m = meter')
21
+ u.define('km = kilometer')
22
+ u.define('s = second')
23
+ u.define('min = minute')
24
+ u.define('h = hour')
25
+ q = u.Quantity
26
+
27
+
28
+ @dataclass
29
+ class QImpacts:
30
+ energy: Quantity
31
+ gwp: Quantity
32
+ adpe: Quantity
33
+ pe: Quantity
34
+
35
+
36
+ class PhysicalActivity(str, Enum):
37
+ RUNNING = "running"
38
+ WALKING = "walking"
39
+
40
+
41
+ class EnergyProduction(str, Enum):
42
+ NUCLEAR = "nuclear"
43
+ WIND = "wind"
44
+
45
+
46
+ COUNTRIES = [
47
+ ("cook_islands", 38.81, 9_556),
48
+ ("tonga", 51.15, 104_490),
49
+ ("comoros", 100, 821_632),
50
+ ("samoa", 100, 821_632),
51
+ ]
52
+
53
+
54
+ # From https://www.runningtools.com/energyusage.htm
55
+ RUNNING_ENERGY_EQ = q("294 kJ / km") # running 1 km at 10 km/h with a weight of 70 kg
56
+ WALKING_ENERGY_EQ = q("196 kJ / km") # walking 1 km at 3 km/h with a weight of 70 kg
57
+
58
+ # From https://selectra.info/energie/actualites/insolite/consommation-vehicules-electriques-france-2040
59
+ # and https://www.tesla.com/fr_fr/support/power-consumption
60
+ EV_ENERGY_EQ = q("0.17 kWh / km")
61
+
62
+ # From https://impactco2.fr/outils/comparateur?value=1&comparisons=streamingvideo
63
+ STREAMING_GWP_EQ = q("15.6 h / kgCO2eq")
64
+
65
+ # For a 900 MW nuclear plant -> 500 000 MWh / month
66
+ # From https://www.edf.fr/groupe-edf/espaces-dedies/jeunes-enseignants/pour-les-jeunes/lenergie-de-a-a-z/produire-de-lelectricite/le-nucleaire-en-chiffres
67
+ YEARLY_NUCLEAR_ENERGY_EQ = q("6 TWh")
68
+
69
+ # From https://ourworldindata.org/population-growth
70
+ ONE_PERCENT_WORLD_POPULATION = 80_000_000
71
+
72
+ DAYS_IN_YEAR = 365
73
+
74
+ # For a 2MW wind turbine
75
+ # https://www.ecologie.gouv.fr/eolien-terrestre
76
+ YEARLY_WIND_ENERGY_EQ = q("4.2 GWh")
77
+
78
+ # Ireland yearly electricity consumption
79
+ # From https://en.wikipedia.org/wiki/List_of_countries_by_electricity_consumption
80
+ YEARLY_IRELAND_ELECTRICITY_CONSUMPTION = q("33 TWh")
81
+ IRELAND_POPULATION_MILLION = 5
82
+
83
+ # From https://impactco2.fr/outils/comparateur?value=1&comparisons=&equivalent=avion-pny
84
+ AIRPLANE_PARIS_NYC_GWP_EQ = q("1770 kgCO2eq")
85
+
86
+
87
+ def format_energy(energy: Energy) -> Quantity:
88
+ val = q(energy.value, energy.unit)
89
+ if val < q("1 kWh"):
90
+ val = val.to("Wh")
91
+ return val
92
+
93
+
94
+ def format_gwp(gwp: GWP) -> Quantity:
95
+ val = q(gwp.value, gwp.unit)
96
+ if val < q("1 kgCO2eq"):
97
+ val = val.to("gCO2eq")
98
+ return val
99
+
100
+
101
+ def format_adpe(adpe: ADPe) -> Quantity:
102
+ return q(adpe.value, adpe.unit)
103
+
104
+
105
+ def format_pe(pe: PE) -> Quantity:
106
+ val = q(pe.value, pe.unit)
107
+ if val < q("1 MJ"):
108
+ val = val.to("kJ")
109
+ return val
110
+
111
+
112
+ def format_impacts(impacts: Impacts) -> QImpacts:
113
+ return QImpacts(
114
+ energy=format_energy(impacts.energy),
115
+ gwp=format_gwp(impacts.gwp),
116
+ adpe=format_adpe(impacts.adpe),
117
+ pe=format_pe(impacts.pe),
118
+ )
119
+
120
+
121
+ def format_energy_eq_physical_activity(energy: Quantity) -> tuple[PhysicalActivity, Quantity]:
122
+ energy = energy.to("kJ")
123
+ running_eq = energy / RUNNING_ENERGY_EQ
124
+ if running_eq > q("1 km"):
125
+ return PhysicalActivity.RUNNING, running_eq
126
+
127
+ walking_eq = energy / WALKING_ENERGY_EQ
128
+ if walking_eq < q("1 km"):
129
+ walking_eq = walking_eq.to("m")
130
+ return PhysicalActivity.WALKING, walking_eq
131
+
132
+
133
+ def format_energy_eq_electric_vehicle(energy: Quantity) -> Quantity:
134
+ energy = energy.to("kWh")
135
+ ev_eq = energy / EV_ENERGY_EQ
136
+ if ev_eq < q("1 km"):
137
+ ev_eq = ev_eq.to("m")
138
+ return ev_eq
139
+
140
+
141
+ def format_gwp_eq_streaming(gwp: Quantity) -> Quantity:
142
+ gwp = gwp.to("kgCO2eq")
143
+ streaming_eq = gwp * STREAMING_GWP_EQ
144
+ if streaming_eq < q("1 h"):
145
+ streaming_eq = streaming_eq.to("min")
146
+ if streaming_eq < q("1 min"):
147
+ streaming_eq = streaming_eq.to("s")
148
+ return streaming_eq
149
+
150
+
151
+ def format_energy_eq_electricity_production(energy: Quantity) -> tuple[EnergyProduction, float]:
152
+ electricity_eq = energy * ONE_PERCENT_WORLD_POPULATION * DAYS_IN_YEAR
153
+ electricity_eq = electricity_eq.to("TWh")
154
+ if electricity_eq > YEARLY_NUCLEAR_ENERGY_EQ:
155
+ return EnergyProduction.NUCLEAR, electricity_eq / YEARLY_NUCLEAR_ENERGY_EQ
156
+ electricity_eq = electricity_eq.to("GWh")
157
+ return EnergyProduction.WIND, electricity_eq / YEARLY_WIND_ENERGY_EQ
158
+
159
+
160
+ def format_energy_eq_electricity_consumption_ireland(energy: Quantity) -> float:
161
+ electricity_eq = energy * ONE_PERCENT_WORLD_POPULATION * DAYS_IN_YEAR
162
+ electricity_eq = electricity_eq.to("TWh")
163
+ return electricity_eq / YEARLY_IRELAND_ELECTRICITY_CONSUMPTION
164
+
165
+
166
+ def format_gwp_eq_airplane_paris_nyc(gwp: Quantity) -> float:
167
+ gwp_eq = gwp * ONE_PERCENT_WORLD_POPULATION * DAYS_IN_YEAR
168
+ gwp_eq = gwp_eq.to("kgCO2eq")
169
+ return gwp_eq / AIRPLANE_PARIS_NYC_GWP_EQ
170
+
171
+
172
+ if __name__ == '__main__':
173
+ # energy = 5590e-9 # GWh
174
+ # energy = 3.58e-9 # GWh
175
+ # val = q("5.59 kWh") # gpt4
176
+ val = q("0.448 Wh")
177
+ val = val.to("MWh")
178
+ pop = 80_000_000
179
+ days = 365
180
+
181
+ tot = val * pop * days
182
+ print(tot)