National Weather Service (NWS) new API

NWS API has a bunch of changes coming 2017. The documentation is a little light right now, but it sounds like the old DWML/XML feeds are going away.  We will have to pull the data using the new api.weather.gov API. Here is what I have learned about this new API so far while replacing the digitalDWML FcstType feed for my Illustrated Weather tool.

If you are using a Weather Service XML feed today and need someone to update it to api.weather.gov, drop me an email.

National Weather Service API Streaming Setup

To stream anything from https://api.weather.gov you must first set the stream header to include the Accept, Version and User-Agent. If you do not set the header the stream will return empty. NWS asks that you include your website and email address in the User-Agent so the they can contact you if need be.

$UserAgent = "YOURWEBSITE (your@emailaddress.com)";

// HTTP stream options:
$opts = array(
 'http'=>array(
 'method'=>"GET",
 'header'=>"Accept: application/geo+json;version=1\r\n" .
 "User-agent: $UserAgent\r\n"
 )
);
$context = stream_context_create($opts);

After the header is set you can stream the /points/lat,lng URL into a json object and pull forecastGridData, which is the /gridpoints/office/x/y URL. If you do not need a detailed gridded forecast take a look at the /points/lat,lng/forecast/ or /points/lat,lng/forecast/hourly in the documentation.

$lat = 43.0204;
$lng = -71.6002;
$pointMetaUrl = "https://api.weather.gov/points/$lat,$lng";
$pointMetaFile = file_get_contents($pointMetaUrl, false, $context);
$pointMetaArray = json_decode($pointMetaFile, true);
$forecastGridData = $pointMetaArray["properties"]["forecastGridData"];

Now stream the detailed gridded forecast using the forecastGridData /gridpoints/office/x/y URL. Then start pulling the data you want.

$gridDataFile = file_get_contents($forecastGridData, false, $context);
$gridDataArray = json_decode($gridDataFile, true);
$temp = $gridDataArray["properties"]["temperature"]["values"];

Just about all weather elements returned, like temperature, are an array of arrays including a time and value (e.g. temperature). The time format is ISO 8601, plus a PHP  DateInterval. “PT2H”  is a 2 hour interval.  Temperatures are in Celsius.

"values": [
                {
                    "validTime": "2017-02-17T08:00:00+00:00/PT2H",
                    "value": -6.1111111111111
                },

Now all I have to do is retool my Illustrated Weather functions to deal with this new format. UGH!

Published by

Kimball

Kimball is a website designer and developer in Goffstown, NH.

6 comments on:
“National Weather Service (NWS) new API”

  1. I’m trying to do this same thing in VBA, but all I’m getting is “Method Not Allowed” responses when I try to POST or PUT:

    Dim xmlhttp As Object
    ‘Set xmlhttp = CreateObject(“WinHttp.WinHttpRequest.5.1”)
    Set xmlhttp = CreateObject(“MSXML2.serverXMLHTTP”)
    xmlhttp.Open “GET”, “https://api.weather.gov/alerts/active/zone/PZZ530”
    ‘xmlhttp.Open “PUT”, “https://api.weather.gov/products/types/CWF/locations/MTR”, False
    xmlhttp.setRequestHeader “Accept”, “application/vnd.noaa.dwml+xml;version=1”
    xmlhttp.setRequestHeader “User-Agent”, “OCSCSailing chris@ocsc.com
    xmlhttp.Send

    ‘xmlhttp.Open “GET”, “https://api.weather.gov/products/types/CWF/locations/MTR”
    ‘ Send Request.
    ‘xmlhttp.Send
    ‘And we get this response
    MsgBox xmlhttp.responseText

    1. Not sure but perhaps the issue is you are calling for a format the endpoint does not support. application/vnd.noaa.dwml is only available at /points/{point}/forecast.

      The available formats are listed on the API Reference tab.

  2. Can you explain Noaa’s point in adding php DateInterval to validTime?
    Could it mean for example PT2H – for this hour and next the value is the same?

    1. Yes, exactly. Below is a sample of temperatures pulled from https://api.weather.gov/gridpoints/GYX/36,21

      In the sample you will see:
      [validTime] => 2017-10-25T07:00:00+00:00/PT2H covers 2 hours (7AM, 8AM)
      [validTime] => 2017-10-25T09:00:00+00:00/PT3H covers 3 hours (9AM, 10AM, 11AM)
      [validTime] => 2017-10-25T12:00:00+00:00/PT1H covers 1 hour (12PM)

      "temperature": {
      "sourceUnit": "F",
      "uom": "unit:degC",
      "values": [
      {
      "validTime": "2017-10-25T07:00:00+00:00/PT2H",
      "value": 16.666666666667
      },
      {
      "validTime": "2017-10-25T09:00:00+00:00/PT3H",
      "value": 16.111111111111
      },
      {
      "validTime": "2017-10-25T12:00:00+00:00/PT1H",
      "value": 17.222222222222
      },

Leave a Reply

Your email address will not be published. Required fields are marked *