Extract historical climate data from the Norwegian Meteorological Institute (MET)

colab github

Author: Willeke A’Campo

Description: This notebook extracts historical climate data from the Norwegian Meteorological Institute (MET) using the FROST API. The data is stored in a pandas dataframe and saved as a csv file. The data is used to detect the hottest summer on record in Bærum, Bodø, Kristiansand, and Oslo.

Data source: Documentation Frost MET

Result Summary:

The table shows hottest summer on record in Bærum, Bodø, Kristiansand, and Oslo.

City

Station

SourceID

Coordinates

Hottest Summer during Landsat-8 observation period

Temperature

Hottest Summer on record

Temperature

Bærum

Oslo (Blindern)

SN18700

10.723072, 59.940625

2018

18.8

1997

18.8

Bodø

Bodø (Lufthavn)

SN82310

14.375128, 67.282669

2023

14.1

2023

14.1

Kristiansand

Kristiansand (Lufthavn)

SN39040

7.995733, 58.14615

2018

17.5

2018

17.5

Oslo

Oslo (Blindern)

SN18700

10.723072, 59.940625

2018

18.8

1997

18.8

[1]:
import requests
import pandas as pd
import yaml
import os
from pathlib import Path

project_path= Path.cwd().parents[0]
credentials_file = os.path.join(project_path, 'conf/local/credentials.yml')

# read client id from conf/local/credentials.yml
with open(credentials_file, 'r') as f:
    credentials = yaml.safe_load(f)
    client_id = credentials['frost_api']['client_id']
    client_key = credentials['frost_api']['client_key']

Stations Request

[3]:
# Define stations endpoint
endpoint_stations = 'https://frost.met.no/locations/v0.jsonld'
# Issue an HTTP GET request
r = requests.get(endpoint_stations, auth=(client_id,''))
# Extract JSON data
json_stations = r.json()
[4]:
# search for station with name Oslo, Kristiansand, Bodø and Bæerum
for station in json_stations['data']:
    # print station name and coordinates
    if station['name'] == 'Oslo':
        print(station['name'], station['geometry']['coordinates'])
    if station['name'] == 'Kristiansand':
        print(station['name'], station['geometry']['coordinates'])
    if station['name'] == 'Bodø':
        print(station['name'], station['geometry']['coordinates'])
    if station['name'] == 'Blindern':
        print(station['name'], station['geometry']['coordinates'])
Blindern [10.723072, 59.940625]
Bodø [14.375128, 67.282669]
Kristiansand [7.995733, 58.14615]
Oslo [10.746092, 59.912728]

Observations Request

[5]:
# Define endpoint and parameters
endpoint_observations = 'https://frost.met.no/observations/v0.jsonld'

parameters = {
    'sources': 'SN18700,SN39040,SN82310', # oslo/bærum, kristiansand, bodø
    'elements': 'mean(air_temperature P3M)', # best_estimate_mean(air_temperature P3M)
    'referencetime': '1900-01-01/2023-10-01',
}
r = requests.get(endpoint_observations, parameters, auth=(client_id,''))
json = r.json()
[6]:
# Check if the request worked, print out any errors
if r.status_code == 200:
    data = json['data']
    print('Data retrieved from frost.met.no!')
else:
    print('Error! Returned status code %s' % r.status_code)
    print('Message: %s' % json['error']['message'])
    print('Reason: %s' % json['error']['reason'])
Data retrieved from frost.met.no!
[7]:
# Return a Dataframe with all of the observations in a table format
df = pd.DataFrame()
for i in range(len(data)):
    row = pd.DataFrame(data[i]['observations'])
    row['referenceTime'] = data[i]['referenceTime']
    row['sourceId'] = data[i]['sourceId']
    df = pd.concat([df, row], ignore_index=True)

df = df.reset_index()
[8]:
# These columns will be kept
columns = ['sourceId','referenceTime','elementId','value','unit','timeOffset']
df2 = df[columns].copy()
# Convert the time value to Python standard datetime format
df2['referenceTime'] = pd.to_datetime(df2['referenceTime'])
[9]:
# only show the data for the summer months
df_summer = df2[(df2['referenceTime'].dt.month >= 6) & (df2['referenceTime'].dt.month <= 8)]

Oslo and Bærums Hottest Summer on Record

The hottes summer on record for Bærum and Oslo during Landsat 8 observation period (2013 - present) is 2018.

[13]:
# separate df for oslo
df_oslo = df_summer[df_summer['sourceId'] == 'SN18700:0'].copy()
df_oslo = df_oslo.reset_index()
# sort by warmest summer
df_oslo.sort_values(by=['value'], inplace=True, ascending=False)
display(df_oslo.head(3))
index sourceId referenceTime elementId value unit timeOffset
60 241 SN18700:0 1997-06-01 00:00:00+00:00 mean(air_temperature P3M) 18.8 degC PT0H
81 325 SN18700:0 2018-06-01 00:00:00+00:00 mean(air_temperature P3M) 18.8 degC PT0H
10 41 SN18700:0 1947-06-01 00:00:00+00:00 mean(air_temperature P3M) 18.7 degC PT0H

Kristiansand Hottest summer on record

The hottest summer on record for Kristiansand during Landsat 8 observation period (2013 - present) is 2018.

[14]:
# separate df for kristiansand
df_kristiansand = df_summer[df_summer['sourceId'] == 'SN39040:0'].copy()
df_kristiansand = df_kristiansand.reset_index()
# sort by warmest summer
df_kristiansand.sort_values(by=['value'], inplace=True, ascending=False)
display(df_kristiansand.head(3))

index sourceId referenceTime elementId value unit timeOffset
77 655 SN39040:0 2018-06-01 00:00:00+00:00 mean(air_temperature P3M) 17.5 degC PT0H
56 572 SN39040:0 1997-06-01 00:00:00+00:00 mean(air_temperature P3M) 17.4 degC PT0H
6 372 SN39040:0 1947-06-01 00:00:00+00:00 mean(air_temperature P3M) 17.2 degC PT0H

Bodø Hottest summer on record

The hottest summer on record for Bodø during Landsat 8 observation period (2013 - present) is 2023.

[15]:
# separate df for bodø
df_bodø = df_summer[df_summer['sourceId'] == 'SN82310:0'].copy()
df_bodø = df_bodø.reset_index()
# sort by warmest summer
df_bodø.sort_values(by=['value'], inplace=True, ascending=False)
display(df_bodø.head(3))
index sourceId referenceTime elementId value unit timeOffset
5 697 SN82310:0 2023-06-01 00:00:00+00:00 mean(air_temperature P3M) 14.1 degC PT0H
3 689 SN82310:0 2020-06-01 00:00:00+00:00 mean(air_temperature P3M) 13.5 degC PT0H
2 685 SN82310:0 2019-06-01 00:00:00+00:00 mean(air_temperature P3M) 13.2 degC PT0H