OpenWeather: Weather Forecast, Get by Date
OpenWeather: Weather Forecast, Get by Date
Gets weather forecast for the specific date from OpenWeather with specifying latitude and longitude of the world. Not only temperature, humidity and wind speed, but also sunset time and dew point temperature can be obtained.
Configs
  • A: Set API Key *#{EL}
  • B1: Set Unit System (Celsius: “metric”, Fahrenheit: “imperial”)#{EL}
  • B2: Set Lang Code to translate description field (eg “ja” “es”)#{EL}
  • C: Set Date (in local time), Latitude and Longitude in 3 lines *#{EL}
  • D1: Select STRING or DATETIME that stores Sunrise Time (update)
  • D2: Select STRING or DATETIME that stores Sunset Time (update)
  • E1: Select NUMERIC that stores Min Daily Temperature (update)
  • E2: Select NUMERIC that stores Max Daily Temperature (update)
  • E3: Select NUMERIC that stores Day Temp of Perception (update)
  • E4: Select NUMERIC that stores Dew Point (update)
  • F1: Select NUMERIC that stores Probability of Precipitation % (update)
  • F2: Select NUMERIC that stores Humidity % (update)
  • F3: Select NUMERIC that stores Clouds % (update)
  • G1: Select STRING that stores Weather Group (update)
  • G2: Select STRING that stores Weather Condition (update)
  • H1: Select NUMERIC that stores Wind Speed (update)
  • H2: Select NUMERIC that stores Wind Deg coming 0:N 90:E (update)
  • I1: Select NUMERIC that stores Precipitation Volume mm (update)
  • I2: Select NUMERIC that stores Sea Level Pressure (update)
  • I3: Select NUMERIC that stores Max UV Index (update)
Script (click to open)
// GraalJS Script (engine type: 2)

//////// START "main()" /////////////////////////////////////////////////////////////////
main();
function main(){ 

//// == Config Retrieving / 工程コンフィグの参照 ==
const strApiKey      = configs.get( "StrConfA" ); // required
  if( strApiKey    === "" ){
    throw new Error( "\n AutomatedTask ConfigError:" +
                     " Config {A API Key} is empty \n" );
  }
const strUnitSystem  = configs.get( "StrConfB1" );
const strLangCode    = configs.get( "StrConfB2" );
const strTarget3     = configs.get( "StrConfC" ); // required
  if( strTarget3   === "" ){
    throw new Error( "\n AutomatedTask ConfigError:" +
                     " Config {C Date Latitude Longitude} is empty \n" );
  }
  const arrTarget3   = strTarget3.split("\n");
  if( arrTarget3.length < 3 ){
    throw new Error( "\n AutomatedTask ConfigError:" +
                     " Config {C Date Latitude Longitude} Set in 3 lines \n" );
  }
  const strSpecifiedDate = arrTarget3[0].slice(0, 10); // eg "2021-12-31"
  let  dateSpecified = toJsDate( strSpecifiedDate + " 23:59" ); // LastTime in Date (Platform)
  const strLat       = arrTarget3[1];
  const strLon       = arrTarget3[2];
const timePocketSunrise  = configs.getObject( "SelectConfD1" );
const timePocketSunset   = configs.getObject( "SelectConfD2" );
const numPocketMinTemp   = configs.getObject( "SelectConfE1" );
const numPocketMaxTemp   = configs.getObject( "SelectConfE2" );
const numPocketFeelTemp  = configs.getObject( "SelectConfE3" );
const numPocketDewPoint  = configs.getObject( "SelectConfE4" );
const numPocketPop       = configs.getObject( "SelectConfF1" );
const numPocketHumidity  = configs.getObject( "SelectConfF2" );
const numPocketClouds    = configs.getObject( "SelectConfF3" );
const strPocketGroup     = configs.getObject( "SelectConfG1" );
const strPocketCondition = configs.getObject( "SelectConfG2" );
const numPocketWindSpeed = configs.getObject( "SelectConfH1" );
const numPocketWindDeg   = configs.getObject( "SelectConfH2" );
const numPocketRain      = configs.getObject( "SelectConfI1" );
const numPocketPressure  = configs.getObject( "SelectConfI2" );
const numPocketUvi       = configs.getObject( "SelectConfI3" );


//// == Data Retrieving / ワークフローデータの参照 ==
// (Nothing. Retrieved via Expression Language in Config Retrieving)


//// == Calculating / 演算 ==

/// Get all essential weather data for a specific location
/// https://openweathermap.org/api/one-call-api
// request1, prepare
let getUri1  = "https://api.openweathermap.org/data/2.5/onecall";
let request1 = httpClient.begin(); // HttpRequestWrapper
    request1 = request1.queryParam( "appid", strApiKey ); 
    request1 = request1.queryParam( "lat", strLat ); 
    request1 = request1.queryParam( "lon", strLon ); 
    request1 = request1.queryParam( "exclude", "minutely,hourly" ); 
    if( strUnitSystem !== "" ){
      request1 = request1.queryParam( "units", strUnitSystem ); 
    }
    if( strLangCode !== "" ){
      request1 = request1.queryParam( "lang", strLangCode ); 
    }
// request1, try
const response1     = request1.get( getUri1 ); // HttpResponseWrapper
engine.log( " AutomatedTask ApiRequest1 Start: " + getUri1 );
const response1Code = response1.getStatusCode() + "";
const response1Body = response1.getResponseAsString() + "";
engine.log( " AutomatedTask ApiResponse1 Status: " + response1Code );
if( response1Code !== "200"){
  throw new Error( "\n AutomatedTask UnexpectedResponseError: " +
                    response1Code + "\n" + response1Body + "\n" );
}
// response1, parse
// engine.log( response1Body ); // debug
/* response sample
{
  lat: 43.0687,
  lon: 141.3508,
  timezone: "Asia/Tokyo",
  timezone_offset: 32400,
  daily: [
    {
      dt: 1613440800,
      sunrise: 1613424690,
      sunset: 1613462769,
      temp: {
        day: -1.47,
        min: -7.04,
        max: 3.61,
        night: -7.04,
        eve: -6.05,
        morn: 3.39
      },
      feels_like: {
        day: -14.13,
        night: -14.19,
        eve: -15.56,
        morn: -0.52
      },
      pressure: 976,
      humidity: 92,
      dew_point: -5.77,
      wind_speed: 14.75,
      wind_deg: 271,
      weather: [
        {
          id: 616,
          main: "Snow",
          description: "rain and snow",
          icon: "13d"
        }
      ],
      clouds: 100,
      pop: 1,
      rain: 10.85,
      snow: 6.1,
      uvi: 0.74
    },
*/
const response1Obj = JSON.parse( response1Body );
engine.log( " AutomatedTask ApiResponse1 # of Array Daily: " + response1Obj.daily.length );
engine.log( " AutomatedTask ApiResponse1 timezone: " + response1Obj.timezone );
engine.log( " AutomatedTask ApiResponse1 offset: " + (response1Obj.timezone_offset /3600) );
engine.log( " AutomatedTask Workflow Platform offset: " + (engine.getTimeZoneOffsetInMinutes() /60) );

/// Find ID of the specified date
// LastTime in Date (Workflow Platform Time) -> LastTime in Date (Weather Location Time)
dateSpecified.setSeconds( dateSpecified.getSeconds() +
  engine.getTimeZoneOffsetInMinutes() * 60 -
  response1Obj.timezone_offset
  ); 
let numDailyId = 0;
engine.log( "  Last in Date: " + dateSpecified.getTime() +
                " (" + dateSpecified.toISOString() + ")"
          );
for( let i = 0; i < response1Obj.daily.length; i++ ){ // must be sorted
  let dateTmp = new Date( response1Obj.daily[i].dt *1000 );
  if( response1Obj.daily[i].dt *1000 > dateSpecified.getTime() ){
    engine.log( "   daily[" + i + "].dt: " + response1Obj.daily[i].dt +
                " (" + dateTmp.toISOString() + ") is larger"
              );
    break;
  }else{
    engine.log( "   daily[" + i + "].dt: " + response1Obj.daily[i].dt +
                " (" + dateTmp.toISOString() + ")"
              );
    numDailyId = i;
  }
}

/// Extract weather info with Date-ID
let numMsecSunrise = response1Obj.daily[numDailyId].sunrise *1000;
let dateSunrise    = new Date( numMsecSunrise );
let strSunrise     = dateSunrise.toLocaleTimeString();
let numMsecSunset  = response1Obj.daily[numDailyId].sunset *1000;
let dateSunset     = new Date( numMsecSunset );
let strSunset      = dateSunset.toLocaleTimeString();
let numMinTemp     = response1Obj.daily[numDailyId].temp.min;
let numMaxTemp     = response1Obj.daily[numDailyId].temp.max;
let numFeelTemp    = response1Obj.daily[numDailyId].feels_like.day;
let numDewPoint    = response1Obj.daily[numDailyId].dew_point;
let numPop         = response1Obj.daily[numDailyId].pop *100; // "0.51" to "51"%
let numHumidity    = response1Obj.daily[numDailyId].humidity;
let numClouds      = response1Obj.daily[numDailyId].clouds;
let strGroup       = response1Obj.daily[numDailyId].weather[0].main;
let strCondition   = response1Obj.daily[numDailyId].weather[0].description;
let numWindSpeed   = response1Obj.daily[numDailyId].wind_speed;
let numWindDeg     = response1Obj.daily[numDailyId].wind_deg;
let numRain        = 0;
if( response1Obj.daily[numDailyId].hasOwnProperty('rain') ){
    numRain        = response1Obj.daily[numDailyId].rain;
}
let numPressure    = response1Obj.daily[numDailyId].pressure;
let numUvi         = response1Obj.daily[numDailyId].uvi;


//// == Data Updating / ワークフローデータへの代入 ==
if( timePocketSunrise  !== null ){
  if( timePocketSunrise.matchDataType( "STRING" ) ){
    engine.log( " AutomatedTask: Pocket for Sunrise is STRING type" );
    engine.setData( timePocketSunrise, strSunrise );
  }else{
    engine.log( " AutomatedTask: Pocket for Sunrise is DATETIME type" );
    engine.setData( timePocketSunrise, new java.sql.Timestamp( numMsecSunrise ) );
  }
}
if( timePocketSunset   !== null ){
  if( timePocketSunset.matchDataType( "STRING" ) ){
    engine.log( " AutomatedTask: Pocket for Sunset is STRING type" );
    engine.setData( timePocketSunset, strSunset );
  }else{
    engine.log( " AutomatedTask: Pocket for Sunset is DATETIME type" );
    engine.setData( timePocketSunset, new java.sql.Timestamp( numMsecSunset ) );
  }
}
if( numPocketMinTemp   !== null ){
  engine.setData( numPocketMinTemp,   new java.math.BigDecimal( numMinTemp ) );
}
if( numPocketMaxTemp   !== null ){
  engine.setData( numPocketMaxTemp,   new java.math.BigDecimal( numMaxTemp ) );
}
if( numPocketFeelTemp  !== null ){
  engine.setData( numPocketFeelTemp,  new java.math.BigDecimal( numFeelTemp ) );
}
if( numPocketDewPoint  !== null ){
  engine.setData( numPocketDewPoint,  new java.math.BigDecimal( numDewPoint ) );
}
if( numPocketPop       !== null ){
  engine.setData( numPocketPop,       new java.math.BigDecimal( numPop ) );
}
if( numPocketHumidity  !== null ){
  engine.setData( numPocketHumidity,  new java.math.BigDecimal( numHumidity ) );
}
if( numPocketClouds    !== null ){
  engine.setData( numPocketClouds,    new java.math.BigDecimal( numClouds ) );
}
if( strPocketGroup     !== null ){
  engine.setData( strPocketGroup,     strGroup );
}
if( strPocketCondition !== null ){
  engine.setData( strPocketCondition, strCondition );
}
if( numPocketWindSpeed !== null ){
  engine.setData( numPocketWindSpeed, new java.math.BigDecimal( numWindSpeed ) );
}
if( numPocketWindDeg   !== null ){
  engine.setData( numPocketWindDeg,   new java.math.BigDecimal( numWindDeg ) );
}
if( numPocketRain      !== null ){
  engine.setData( numPocketRain,      new java.math.BigDecimal( numRain ) );
}
if( numPocketPressure  !== null ){
  engine.setData( numPocketPressure,  new java.math.BigDecimal( numPressure ) );
}
if( numPocketUvi       !== null ){
  engine.setData( numPocketUvi,       new java.math.BigDecimal( numUvi ) );
}

} //////// END "main()" /////////////////////////////////////////////////////////////////



function toJsDate( bpmsDateOrDatetimeStr ){
  // BPMS Date:     "2020-04-01"  (subtype "Y/M" "M/D" "Y", not supported)
  // BPMS Datetime: "2020-04-01 23:59"
  let year       = 0;
  let monthIndex = 0;
  let day        = 0;
  let hours      = 0;
  let minutes    = 0;

  //  The ECMA/JavaScript Date object has a large number of methods.
  // "Date.parse" is danger (strongly discouraged)
  // - new Date("2014-11-10") // Mon Nov 10 2014 09:00:00 GMT+0900 (JST)
  // - new Date(2014, 10, 10) // Mon Nov 10 2014 00:00:00 GMT+0900 (JST)
  let arrDatetime = bpmsDateOrDatetimeStr.split(" ");
  if( arrDatetime.length === 1 ){
    let arrDateParts = arrDatetime[0].split("-");
    year       = parseInt(arrDateParts[0], 10);
    monthIndex = parseInt(arrDateParts[1], 10) - 1;
    day        = parseInt(arrDateParts[2], 10);
  }
  if( arrDatetime.length === 2 ){
    let arrDateParts = arrDatetime[0].split("-");
    let arrTimeParts = arrDatetime[1].split(":");
    year       = parseInt(arrDateParts[0], 10);
    monthIndex = parseInt(arrDateParts[1], 10) - 1;
    day        = parseInt(arrDateParts[2], 10);
    hours      = parseInt(arrTimeParts[0], 10);
    minutes    = parseInt(arrTimeParts[1], 10);
  }
  return new Date( year, monthIndex, day, hours, minutes );
}



/*
Notes:
- For agriculture, transportation, retail, hotel, restaurant service, etc.
- Weather data in OpenWeatherMap is calculated mechanically based on public info or airport observations.
    - There is a difference from the weather data provided by the weather company.
- The acquired forecast data and historical data can be freely used under the Open Database License.
    - https://openweathermap.org/full-price#licenses
- Dates up to 7 days in advance are valid.
    - If a date outside the range is specified, it will be updated with the data 7 days ahead.
    - Specify with a string starting with "YYYY-MM-DD". (DateTime type is also acceptable)

Notes-ja:
- 農業・運送業の稼働判断や小売・宿泊・飲食における仕入業務の自動化省力化等に活用されます。
- OpenWeatherMap の気象データは、公的情報や空港観測値などを元に機械的に算出されています。
    - 気象会社による気象データとは、違いがあります。
- 取得した予報データや履歴データは、Open Database License 下で自由に利用できます。
    - https://openweathermap.org/full-price#licenses
- 7日先までの日付が指定可能です。
    - 範囲外の日付が指定された場合、7日先のデータで更新されます。
    - "YYYY-MM-DD" で始まる文字列で指定します。(時刻型データでも構いません)
*/


/*
APPENDIX
- Create an API key on the "API keys" page of your personal account beforehand.
    - https://home.openweathermap.org/api_keys
- In this Addon, the weather data is acquired via "One Call API".
    - Available in OpenWeather Free subscription.
- Sunrise and sunset times are displayed with Workflow platform timezone.
    - The UTC offset of weather location time can be confirmed in the log.
    - Storing in string type data, the time format depends on toLocaleTimeString().
    - eg. "06:40:06", "6:40:06 AM", etc
    - https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Date/toLocaleTimeString
- Units of measurement in response
    - (default): temperature in Kelvin and wind speed in meter/sec
    - "metric": temperature in Celsius and wind speed in meter/sec
    - "imperial": temperature in Fahrenheit and wind speed in miles/hour
- Translation samples of weather description field, corresponding language codes
    - eg. "broken clouds: muy nuboso", "overcast clouds: nubes", "light snow: nevada ligera"
    - https://openweathermap.org/api/one-call-api#multi
    - https://openweathermap.org/weather-conditions
- Wind Direction degrees
    - 0 to 11, 349 to 359: N
    - 12 to 33: NNE
    - 34 to 56: NE
    - 57 to 78: ENE
    - 79 to 101: E
    - 102 to 123: ESE
    - 124 to 146: SE
    - 147 to 168: SSE
    - 169 to 191: S
    - 192 to 213: SSW
    - 214 to 236: SW
    - 237 to 258: WSW
    - 259 to 281: W
    - 282 to 303: WNW
    - 304 to 326: NW
    - 327 to 348: NNW
- Latitude Longitude sample
    - Metropolitan Government Building, Tokyo: 35.689472, 139.69175
    - Kiyomizu-dera Temple, Kyoto: 34.994831, 135.785003
    - Waikiki Beach, Hawaii: 21.275278, -157.825
    - Oymyakon, Russia: 63.25, 143.15 (the coldest permanently inhabited settlement on Earth)
    - Use Google Maps, Wikipedia, etc. to obtain the latitude and longitude of any point.
        - https://www.google.co.jp/maps/

APPENDIX-ja
- 個人アカウントの "API keys" ページにて、あらかじめ API Key を生成しておく必要があります。
    - https://home.openweathermap.org/api_keys
- このAddonで、気象データは "One Call API" 経由で取得されます。
    - OpenWeather Free subscription(無料)で利用可能です。
- 日の出、日の入り時刻は、ワークフロー基盤のタイムゾーンで表示されます。
    - 現地時間のUTCオフセット(協定世界時との差)は、ログにて確認可能です。
    - 文字列型データに格納する場合、時刻書式は toLocaleTimeString() に依存します。
    - 例 "06:40:06", "6:40:06 AM", etc (秒まで出力されます)
    - https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Date/toLocaleTimeString
- レスポンス数値の物理単位系
    - (デフォルト): 気温は「ケルビン(絶対温度)」にて、風速は「メートル毎秒」にて表示されます
    - "metric": 気温は「摂氏」、風速は「メートル毎秒」にて表示されます
    - "imperial": 気温は「華氏」、風速は「マイル毎時」にて表示されます
- 天気概況フィールドの翻訳サンプル、および対応言語コード
    - 例 "broken clouds: 曇りがち"、"overcast clouds: 厚い雲"、"light snow: 小雪"
    - https://openweathermap.org/api/one-call-api#multi
    - https://openweathermap.org/weather-conditions
- 風向と角度
    - 0 to 11, 349 to 359: 北の風、北風
    - 12 to 33: 北北東の風
    - 34 to 56: 北東の風
    - 57 to 78: 東北東の風
    - 79 to 101: 東の風
    - 102 to 123: 東南東の風
    - 124 to 146: 南東の風
    - 147 to 168: 南南東の風
    - 169 to 191: 南の風
    - 192 to 213: 南南西の風
    - 214 to 236: 南西の風
    - 237 to 258: 西南西の風
    - 259 to 281: 西の風
    - 282 to 303: 西北西の風
    - 304 to 326: 北西の風
    - 327 to 348: 北北西の風
- 緯度経度サンプル
    - 東京都庁: 35.689472, 139.69175
    - 京都 清水寺: 34.994831, 135.785003
    - ハワイ ワイキキビーチ: 21.275278, -157.825
    - ロシア オイミャコン: 63.25, 143.15 (世界で最も寒い定住地)
    - 任意地点の緯度経度は Google マップや Wikipedia 等で取得してください
        - https://www.google.co.jp/maps/
*/


Download

2021-02-16 (C) Questetra, Inc. (MIT License)
https://support.questetra.com/addons/openweather-weather-forecast-get-by-date/
The Addon-import feature is available with Professional edition.

Notes

  • For agriculture, transportation, retail, hotel, restaurant service, etc.
  • Weather data in OpenWeatherMap is calculated mechanically based on public info or airport observations.
    • There is a difference from the weather data provided by the weather company.
  • The acquired forecast data and historical data can be freely used under the Open Database License.
  • Dates up to 7 days in advance are valid.
    • If a date outside the range is specified, it will be updated with the data 7 days ahead.
    • Specify with a string starting with “YYYY-MM-DD”. (DateTime type is also acceptable)

Capture

Gets weather forecast for the specific date from OpenWeather with specifying latitude and longitude of the world. Not only temperature, humidity and wind speed, but also sunset time and dew point temperature can be obtained.

Appendix

  • Create an API key on the “API keys” page of your personal account beforehand.
  • In this Addon, the weather data is acquired via “One Call API”.
    • Available in OpenWeather Free subscription.
  • Sunrise and sunset times are displayed with Workflow platform timezone.
  • Units of measurement in response
    • (default): temperature in Kelvin and wind speed in meter/sec
    • “metric”: temperature in Celsius and wind speed in meter/sec
    • “imperial”: temperature in Fahrenheit and wind speed in miles/hour
  • Translation samples of weather description field, corresponding language codes
  • Wind Direction degrees
    • 0 to 11, 349 to 359: N
    • 12 to 33: NNE
    • 34 to 56: NE
    • 57 to 78: ENE
    • 79 to 101: E
    • 102 to 123: ESE
    • 124 to 146: SE
    • 147 to 168: SSE
    • 169 to 191: S
    • 192 to 213: SSW
    • 214 to 236: SW
    • 237 to 258: WSW
    • 259 to 281: W
    • 282 to 303: WNW
    • 304 to 326: NW
    • 327 to 348: NNW
  • Latitude Longitude sample
    • Metropolitan Government Building, Tokyo: 35.689472, 139.69175
    • Kiyomizu-dera Temple, Kyoto: 34.994831, 135.785003
    • Waikiki Beach, Hawaii: 21.275278, -157.825
    • Oymyakon, Russia: 63.25, 143.15 (the coldest permanently inhabited settlement on Earth)
    • Use Google Maps, Wikipedia, etc. to obtain the latitude and longitude of any point.

See also

4 thoughts on “OpenWeather: Weather Forecast, Get by Date”

  1. Pingback: OpenWeather: Weather Forecast, Get by Time – Questetra Support

  2. Pingback: OpenWeather: Weather History, Get by Time – Questetra Support

  3. Pingback: Daily report flow-weather record (Add-on) – Questetra Support

  4. Pingback: Daily report flow-weather record (Script Task) – Questetra Support

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.

%d bloggers like this: