/ scripts / weather.sh
weather.sh
 1  #!/usr/bin/env bash
 2  # setting the locale, some users have issues with different locales, this forces the correct one
 3  export LC_ALL=C.utf8
 4  
 5  fahrenheit=$1
 6  location=$2
 7  fixedlocation=$3
 8  
 9  # emulate timeout command from bash - timeout is not available by default on OSX
10  if [ "$(uname)" == "Darwin" ]; then
11    timeout() {
12        perl -e 'alarm shift; exec @ARGV' "$duration" "$@"
13    }
14  fi
15  
16  display_location()
17  {
18    if $location && [[ ! -z "$fixedlocation" ]]; then
19      echo " $fixedlocation"
20    elif $location; then
21      city=$(curl -s https://ipinfo.io/city 2> /dev/null)
22      region=$(curl -s https://ipinfo.io/region 2> /dev/null)
23      echo " $city, $region"
24    else
25      echo ''
26    fi
27  }
28  
29  fetch_weather_information()
30  {
31    display_weather=$1
32    # it gets the weather condition textual name (%C), and the temperature (%t)
33    api_response=$(curl -sL wttr.in/${fixedlocation// /%20}\?format="%C+%t$display_weather")
34  
35    if [[ $api_response = "Unknown location;"* ]]; then
36      echo "Unknown location error"
37    else
38      echo $api_response
39    fi
40  }
41  
42  #get weather display
43  display_weather()
44  {
45    if $fahrenheit; then
46      display_weather='&u' # for USA system
47    else
48      display_weather='&m' # for metric system
49    fi
50    weather_information=$(fetch_weather_information $display_weather)
51  
52    weather_condition=$(echo "$weather_information" | awk -F' -?[0-9]' '{print $1}' | xargs) # Extract condition before temperature, e.g. Sunny, Snow, etc
53    temperature=$(echo "$weather_information" | grep -oE '[-+]?[0-9]+°[CF]') # Extract temperature, e.g. +31°C, -3°F, etc
54    unicode=$(forecast_unicode $weather_condition)
55  
56    # Mac Only variant should be transparent on Linux
57    if [[ "${temperature/+/}" == *"===="* ]]; then
58      temperature="error"
59    fi
60  
61    if [[ "${temperature/+/}" == "error" ]]; then
62      # Propagate Error
63      echo "error"
64    else
65      echo "$unicode ${temperature/+/}" # remove the plus sign to the temperature
66    fi
67  }
68  
69  forecast_unicode()
70  {
71    weather_condition=$(echo $weather_condition | awk '{print tolower($0)}')
72  
73    if [[ $weather_condition =~ 'snow' ]]; then
74      echo '❄ '
75    elif [[ (($weather_condition =~ 'rain') || ($weather_condition =~ 'shower')) ]]; then
76      echo '☂ '
77    elif [[ (($weather_condition =~ 'overcast') || ($weather_condition =~ 'cloud')) ]]; then
78      echo '☁ '
79    elif [[ $weather_condition = 'NA' ]]; then
80      echo ''
81    else
82      echo '☀ '
83    fi
84  }
85  
86  main()
87  {
88    # process should be cancelled when session is killed
89    if timeout 1 bash -c "</dev/tcp/ipinfo.io/443" && timeout 1 bash -c "</dev/tcp/wttr.in/443" && [[ "$(display_weather)" != "error" ]]; then
90      echo "$(display_weather)$(display_location)"
91    else
92      echo "Weather Unavailable"
93    fi
94  }
95  
96  #run main driver program
97  main