Click or drag to resize

DataApiGetLocationData Method

Sends your request for data (for a specified location) to the API servers, returning a response containing data you requested, or throwing an appropriate subclass of DegreeDaysApiException if something goes wrong.

Namespace: DegreeDays.Api.Data
Assembly: DegreeDays (in DegreeDays.dll) Version: 1.4
Syntax
public LocationDataResponse GetLocationData(
	LocationDataRequest request
)

Parameters

request  LocationDataRequest
Specifies the data you want and the location you want it for. Cannot be null.

Return Value

LocationDataResponse
A non-null LocationDataResponse containing the data you requested or as much of it as was available for the location you specified (given the rules explained below).
Exceptions
ExceptionCondition
LocationExceptionThe request failed because of problems relating to the specified Location.
ServiceExceptionThe request failed because of a problem with the API service (sorry!).
RateLimitExceptionYou hit the RateLimit for your account's plan, and need to wait a little while before it's reset.
InvalidRequestExceptionThe request that is sent to the API servers is invalid (e.g. it is authenticated with invalid API access keys).
TransportExceptionA problem sending the request to the API servers, or a problem getting the API's response back.
DegreeDaysApiExceptionThe superclass of all the exceptions listed above.
ArgumentNullExceptionrequest is null.
Remarks

Sample LocationDataRequest/LocationDataResponse code

Here's a simple example showing how to fetch monthly 65°F-base-temperature heating degree days, covering the 12 months of 2024, for an automatically-selected weather station near US zip code 02633 (which is on Cape Cod so you can use the free test API account). The HDD figures are output to the command line:

DegreeDaysApi api = new DegreeDaysApi(
    new AccountKey("test-test-test"),
    new SecurityKey("test-test-test-test-test-test-test-test-test-test-test-test-test"));
DayRange dayRange = new Day(2024, 1, 1).To(new Day(2024, 12, 31));
DatedDataSpec hddSpec = DataSpec.Dated(
    Calculation.HeatingDegreeDays(Temperature.Fahrenheit(65)),
    DatedBreakdown.Monthly(Period.DayRange(dayRange)));
LocationDataRequest request = new LocationDataRequest(
    Location.PostalCode("02532", "US"),
    new DataSpecs(hddSpec));
LocationDataResponse response = api.DataApi.GetLocationData(request);
DatedDataSet hddData = response.DataSets.GetDated(hddSpec);
foreach (DatedDataValue v in hddData.Values) {
    Console.Out.WriteLine(v.FirstDay + ": " + v.Value);
}

And here is a more complex example that fetches HDD, CDD, and hourly temperature data, covering just the latest available day, for a longitude/latitude position on Cape Cod, Massachusetts (again chosen so you can try out this code using the free test API account):

DegreeDaysApi api = new DegreeDaysApi(
    new AccountKey("test-test-test"),
    new SecurityKey("test-test-test-test-test-test-test-test-test-test-test-test-test"));
DatedBreakdown breakdown = DatedBreakdown.Daily(Period.LatestValues(1));
DatedDataSpec hddSpec = DataSpec.Dated(
    Calculation.HeatingDegreeDays(Temperature.Celsius(15.5)),
    breakdown);
DatedDataSpec cddSpec = DataSpec.Dated(
    Calculation.CoolingDegreeDays(Temperature.Celsius(21)),
    breakdown);
TimeSeriesDataSpec hourlyTempsSpec = DataSpec.TimeSeries(
    TimeSeriesCalculation.HourlyTemperature(TemperatureUnit.Celsius),
    breakdown);
LocationDataRequest request = new LocationDataRequest(
    Location.LongLat(new LongLat(-70.305634, 41.695475)),
    new DataSpecs(hddSpec, cddSpec, hourlyTempsSpec));
LocationDataResponse response = api.DataApi.GetLocationData(request);
DatedDataSet hddData = response.DataSets.GetDated(hddSpec);
DatedDataSet cddData = response.DataSets.GetDated(cddSpec);
TimeSeriesDataSet hourlyTempsData =
    response.DataSets.GetTimeSeries(hourlyTempsSpec);
Console.Out.WriteLine("StationID: " + response.StationId);
foreach (DatedDataValue v in hddData.Values) {
    Console.Out.WriteLine(v.FirstDay + " HDD: " + v.Value);
}
foreach (DatedDataValue v in cddData.Values) {
    Console.Out.WriteLine(v.FirstDay + " CDD: " + v.Value);
}
foreach (TimeSeriesDataValue v in hourlyTempsData.Values) {
    Console.Out.WriteLine(v.DateTimeOffset + ": " + v.Value + " C");
}

Both examples above specify a location on Cape Cod, Massachusetts, so you can try them out using the free test API account. To access data for locations worldwide (whether station IDs, postal/zip codes, or longitude/latitude positions), you can sign up for a full API account on our website, swap your own account key and security key into the code samples above, then change the location however you wish.

Expanding on these examples

The examples above are just a starting point...

  • The LocationDataRequest is highly configurable:
    • You can specify the Location you want data for as a weather-station ID or a geographic location (postal/zip code, or longitude/latitude position). For geographic locations the API will automatically select the best weather station to satisfy your request.
    • There are various components that enable you to specify exactly what each set of data should contain. Each DataSpec can be either a DatedDataSpec (for daily/weekly/monthly/yearly/custom degree days), an AverageDataSpec (for average degree days), or a TimeSeriesDataSpec (for hourly temperature data). Each of these is configured with objects that determine the data Calculation (or TimeSeriesCalculation), the Breakdown, and the Period of coverage that you want.
    • You can fetch multiple sets of data for a location in a single request. For example, you might want to fetch HDD and CDD with multiple base temperatures each. To do this just create the DataSpecs in your request with multiple different DataSpec items.
  • The LocationDataResponse also contains information about the weather station(s) used to generate the returned data. If you request data for a geographic location initially, you might want to use the station ID to fetch updates later. If you are specifying geographic locations, but storing data by station ID, you can avoid re-fetching data unnecessarily by using GetLocationInfo(LocationInfoRequest) to get the station ID that would be returned by an equivalent call to GetLocationData(LocationDataRequest). We call this "two-stage data fetching", and you can read more about it in the remarks for the GeographicLocation class.
  • Error handling would be important for production code. Catching DegreeDaysApiException will cover everything that you should be prepared for, but it's often useful to get more detail. Check the list of exceptions further above and the GetXXX methods of DataSets to see exactly what subclasses of DegreeDaysApiException can be thrown.

Rules that govern what you can get in response

It's worth understanding the rules that govern what you can get in response to a request for one or more sets of data for a particular location:

Stations that data can come from:

  • If your request specifies a StationIdLocation (created via Location.StationId(String)) then the API will only ever return data for that station. It will never substitute in data from another station.
  • If your request specifies a GeographicLocation, the API will choose which station(s) to use automatically. The choice will depend on the data you requested as well as the location you requested it for. Some stations have more data than others, and the quality of a station's data can vary over time. The API will choose the station(s) that can best satisfy your specific request.
  • The API will never send a LocationDataResponse for an inactive station. An inactive station is one that hasn't sent any usable weather reports for roughly 10 days or more (10 being an approximate number that is subject to change). See here for more information on inactive stations. If you request data for an inactive station, or for a GeographicLocation for which no active station can be found, you will get a LocationException to indicate that the location is not supported.

When you request more data than is available:

  • If your request specifies data for a location for which an active station exists, you should, barring other failures, get a LocationDataResponse. But, if any of the DataSpec objects that you specified cannot be satisfied (either fully or partially), you will get a SourceDataException each time you try to get the corresponding data set from the DataSets object held by the response.
  • If there's not enough data to fully satisfy your request, the API will return partial sets of data if it can. For example, you might request 10 years of data, but only get 5. Because data is only returned for active stations, you can rely on recent times being covered if requested (usually including yesterday's data in the station's time-zone, but always to within around 10 days or so of that day). But data from further back could be missing.
  • If you'd rather the API gave you a SourceDataException (see above) than any partially-complete data set, make sure to specify the minimum number of values or the minimum day range for the Period objects in your request. Unless you specify minimums, the API will return the best it can from within the specifications you give.

Other data guarantees:

  • Excepting the widening rules that apply when a DayRangePeriod (created with Period.DayRange) is specified imprecisely (see the docs for DayRangePeriod for more on widening), the API will never return more data than you asked for, or data from outside of the range that you asked for.
  • The API will never return data with gaps in it. No gaps, and no special error values like NaN, 0, -1, 9999 etc. If a station has small gaps in its source temperature data, the API will fill those gaps with estimates before calculating any degree days. But larger gaps are not tolerated, and the API will only ever use data from after such gaps. If a larger gap is ongoing (i.e. there is no good data after it), the station will be declared inactive (see above). This approach ensures that active stations will always have contiguous sets of data that run through to recent days.
See Also