Green ELEPHPANT
Carsten Windler
:)
vs.
Carsten Windler
Principal Backend Engineer
Worldwide greenhouse gas emissions
Information and communications technology
OUR PROBLEM
Solutions(?)
Compensation
CCS
Renewables
https://www.pexels.com/photo/green-pine-trees-1179229/
https://www.boell.de/en/2015/11/10/carbon-capture-and-storage-problems-depth
https://www.pexels.com/photo/alternative-energy-blade-blue-clouds-414928/
...but...
https://unsplash.com/photos/iy8h-Cl8MLc
https://www.pexels.com/photo/man-in-white-coat-doing-an-experiment-8326464/
https://www.coursehero.com/study-guides/physics/15-5-applications-of-thermodynamics-heat-pumps-and-refrigerators/
Green IT
GREEN SOFTWARE ENGINEERING
SHIFT
RETHINK
REDUCE
GREEN SOFTWARE ENGINEERING
SHIFT
RETHINK
REDUCE
CPU usage =
Power consumption =
Carbon emissions
How to reduce emissions?
Network usage =
Power consumption =
Carbon emissions
How to reduce emissions?
Storage usage =
Power consumption =
Carbon emissions
How to reduce emissions?
2 Bytes
1,900 Bytes
:)
vs.
200,000 Bytes
Lean software =
Less waste =
Less emissions
Embodied 83%
Network and
data centres
15%
Electricity use 2%
Embodied carbon
≈ 500 kgCO2e
How do we achieve that with PHP?
?
Algorithms
- How to chose the right algorithm
- Big O Notation:
O(1)
,O(N)
,O(N²)
,O(2^N)
,O(log N)
👉 Use native functions, since compiled
👉 Use the right function for the job
Performance Measurement
class StringPositionBench
{
#[Bench\Revs(1000)]
#[Bench\Iterations(5)]
public function benchStrContains()
{
str_contains('string contains PHP', 'PHP');
}
#[Bench\Revs(1000)]
#[Bench\Iterations(5)]
public function benchPregMatch()
{
preg_match("/php/i", 'string contains PHP');
}
}
Performance Measurement
Debugging & Profiling
Debugging & Profiling
Performance Improvements
- Caching
- In-Memory-Caching (i.e. storing values in variables)
- Redis, Memcached
- ....
- Optimize code execution
- Avoid costly operation
- Move costly operations out of the loop
- Order of conditions in
if
clauses - ....
Danger zone: Packages
Are packages always necessary?
Danger zone: Packages
class DateFormatBench
{
public function benchDate()
{
date('D M d Y H:m:s');
}
public function benchDateTime()
{
(new \DateTime())->format('D M d Y H:m:s');
}
public function benchCarbon()
{
(new Carbon\Carbon())->format('D M d Y H:m:s');
}
}
Database
- Use the right tool for the job
- SQL for logging or unstructured data?
- Learn about performance tweaks
- Indexes!!!1
- Slow query log
-
EXPLAIN
statement - ...
- Use large test data locally
- Spot problems early
Danger zone: ORM
Danger zone: ORM
PerformanceTest::where('some_flag', '=', 1)->get();
// Time: 2.10s
// Memory Peak: 372.92 MB
DB::select(
'SELECT * FROM performance_tests WHERE some_flag = 1'
);
// Time: 0.95s (=> 0.45x)
// Memory Peak: 246.06 MB
Test setup:
-
performance_tests
with 500.000 rows - half of them have
some_flag = 1
-
PerformanceTest
model
Danger zone: ORM
PerformanceTest::where('some_flag', '=', 1)->cursor();
// Time: 2.640s (=> 1.25x)
// Memory Peak: 81.64 MB
DB::cursor(
'SELECT * FROM performance_tests WHERE some_flag = 1'
);
// Time: 0.70s (=> 0.38x)
// Memory Peak: 85.88 MB
Danger zone: ORM
PerformanceTest::get()->where('some_flag', '=', 1);
// Time: 5.05s
// Memory Peak: 701.77 MB
PerformanceTest::where('some_flag', '=', 1)->get();
// Time: 2.10s
// Memory Peak: 372.92 MB
Danger zone: ORM
DB::cursor(
'SELECT id, first_name, last_name
FROM performance_tests WHERE some_flag = 1'
);
// Time: 0.60s
// Memory Peak: 66.49 MB
https://www.pexels.com/photo/stopwatch-on-smartphone-4114778/
APIs
Source: Cloudflare
APIs
- Reduce amount of data transferred
- Split up endpoints
GET /users/12
GET /users/34/address
- Specify fields
GET /users/56?fields=id,last_name
- Caching
- Client- and server-side
- GraphQL
Storage
- Log only what is necessary
- Data retention
- Compression / file formats
- Garbage collectors
https://www.pexels.com/photo/black-trash-bin-with-full-of-trash-3806764/
We can only optimize code so much.
What else can we do?
?
GREEN SOFTWARE ENGINEERING
SHIFT
RETHINK
REDUCE
gCO2eq/kWh
Let's become CARBON AWARE
!
Temporal Shifting
Temporal Shifting
Do things WHEN carbon intensity is LOW
!
Temporal Shifting
...but how do we know?
Temporal Shifting
use GreenElephpant\CarbonAware\Connector\Co2Signal;
use GreenElephpant\CarbonAware\CarbonAwareService;
$co2SignalConnector = new Co2Signal('my_apikey');
$carbonAwareService = new CarbonAwareService($co2SignalConnector);
if ($carbonAwareService->isLow()) {
$schedule
->command('reports:generate')
->everyHour();
}
https://unsplash.com/photos/D0y9rNIN-IE
Carbon Forecast
Demand Shaping
Demand Shaping
Do LESS when the carbon intensity is HIGH
!
Demand Shaping
if ($carbonAwareService->isLow()) {
$schedule
->command('dashboard:update')
->everyFiveMinutes();
} else {
$schedule
->command('dashboard:update')
->everyTenMinutes();
}
Geospatial Shifting
Geospatial Shifting
Do things WHERE the carbon intensity is LOW
!
Green OPS
GREEN SOFTWARE ENGINEERING
SHIFT
RETHINK
REDUCE
Past: production followed consumption
!
Future: consumption follows production
Cloud
https://unsplash.com/photos/aBGYL-ue5xo
How do we measure
carbon emissions
of software?
?
https://www.pexels.com/photo/cancer-15834506/
Measuring carbon emissions
Measuring carbon emissions
Bild Sustainable web design
Think twice
- Event-Driven Architecture vs. API Polling
- Dynamic vs. Static
- Serverless
- Frameworkless
- Challenge everything
Danger zone: Carbon
Danger zone: Carbon
180+ language files
Danger zone: Carbon
- Carbon has 200,000 daily installs
- 3 MB language files downloaded in vain
- 200,000 x 3 MB x 365 = 213,687 GB
- 0.81 kWh/GB of data traffic*
- 442 gCO2e/kWh*
- 213,687 GB × 0.81 kWh/GB = 173,086 kWh
- 173,086 kWh × 442 gCO2e/kWh = 76,504,219 gCO2e
70+ tCO2e per year
wasted
Is it worth it?
?
Everyone
can do
something
about the
climate crisis
💚 THANK YOU! 💚
Green ElePHPant (PDF + Sources)
By Carsten Windler
Green ElePHPant (PDF + Sources)
- 208