-
Notifications
You must be signed in to change notification settings - Fork 0
/
mbwbpi.plugin
214 lines (194 loc) · 6.52 KB
/
mbwbpi.plugin
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
#!/usr/bin/awk -f
#
# mbwbpi.plugin Meteobridge plugin weatherstation to calculate wetbulb temperature
#
# Copyright 2021 by Fred T. Trimble ([email protected])
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
# MA 02110-1301, USA.
#
# Meteobridge user-defined plugin weatherstation to calculate wet-bulb temperature from
# outdoor dry-bulb temperature, outdoor relative humdity and station barometric pressure as a t0 sensor.
# Also outputs a data0 sensor flag value to indicate when snow percipitation is possible.
#
# Written 17-Jan-2021 by Fred T. Trimble Ver 1.0a ([email protected]) and user AlaskaWX on Meteobridge forum
#
# Modified 18-Jan-2021 by Fred T. Trimble Ver 1.1a Added optional snowmaking level output based on wetbulb temp
# to data1 sensor. Output values: 2 good (dry snow), 1 marginal (wet snow), 0 not possible
#
# Modified 23-Jan-2021 by Fred T. Trimble Ver 1.1b Changed data delimiter from a single underscore character
# to a sinble tab character. Must be represented as %09 in URLs used to get data from Meteobridge
#
# Modified 07-May-2021 by Fred T. Trimble Ver 1.1c Cleaned up code
#
# Adapted from java script code found in the source of the web page
# on the NWS web site at:
# https://www.weather.gov/epz/wxcalc_rh
#
# awk lang reference:
# http://www.math.utah.edu/docs/info/gawk_toc.html
# function definitions
function abs(v)
{
return v < 0? -v: v
}
# calculate vapor pressure
function esubs(ct)
{
return(6.112 * exp((17.67 * ct) / (ct + 243.5)))
}
function invertedRH(es, rh)
{
return (es * (rh / 100.0))
}
# calculate wetbulb temperature using Newton-Raphson interative method
# ct: dry-bulb temp in °C
# rh: relative humdity %
# p: barometric pressure mBar
function calcwetbulb(ct, rh, p)
{
Ediff = 1.0
Twguess = 0.0
incr = 10.0
prevsign = 1
E2 = invertedRH(esubs(ct),rh)
Ewguess = 0.0
Eguess = 0.0
cursign = 0
while(abs(Ediff) > 0.005)
{
Ewguess = esubs(Twguess)
Eguess = Ewguess - p * (ct - Twguess) * 0.00066 * (1 + (0.00115 * Twguess))
Ediff = E2 - Eguess
if(Ediff == 0.0)
break
else
{
if(Ediff < 0.0)
{
cursign = -1
if(cursign != prevsign)
{
prevsign = cursign
incr = incr / 10.0
}
else
incr = incr
}
else
{
cursign = 1
if(cursign != prevsign)
{
prevsign = cursign
incr = incr / 10.0
}
else
incr = incr
}
}
Twguess = Twguess + incr * prevsign
}
return(Twguess)
}
# write timestampped message to logfile ala mb style
function writelog(path, name, message)
{
system("echo '"name" ("strftime("%d.%m.%Y %T",systime())"): "message"' >> "path" 2>/dev/null")
}
# main program
BEGIN {
myname = "mbwbpi"
ver = "1.1c" # version
snowposs = 1.2 # threshold wetbulb temp in °C below where snow percipitation is possible
drysnow = -7.0 # threshold wetbulb temp in °C for good, dry snowmaking
wetsnow = -3.0 # threshold wetbulb temp in °C for marginal, wet snowmaking
wb_temp = 0.0
exit_code = -1
# default values to use if no config file
# the os command used to return a tab (the %09 in the ULR) delimited list of temp, humidity and station baro pressure
mb_cmd = "wget -q -O - 'http://localhost/public/template.cgi?template=[th0temp-act]%09[th0hum-act%09[thb0press-act]&contenttype=text/plain;charset=iso-8859-1'"
logfile = "/tmp/log/meteobridge.log"
pollsleep = 60
writetolog = 0
snowmaking = 0
# read plugin config using openwrt uci
conf = "/tmp/mnt/data/scripts" # location of uci config file
uci = "uci -c "conf" get "myname".@"myname"[0].mb_cmd 2>/dev/null"
item = ""
uci | getline item
close(uci)
if(length(item) > 0)
mb_cmd = item
uci = "uci -c "conf" get "myname".@"myname"[0].logfile 2>/dev/null"
item = ""
uci | getline item
close(uci)
if(length(item) > 0)
logfile = item
uci = "uci -c "conf" get "myname".@"myname"[0].pollsleep 2>/dev/null"
item = ""
uci | getline item
close(uci)
if(length(item) > 0)
pollsleep = item + 0.0
uci = "uci -c /tmp/mnt/data/scripts get "myname".@"myname"[0].writetolog 2>/dev/null"
item = ""
uci | getline item
close(uci)
if(length(item) > 0)
writetolog = item + 0.0
uci = "uci -c /tmp/mnt/data/scripts get "myname".@"myname"[0].snowmaking 2>/dev/null"
item = ""
uci | getline item
close(uci)
if(length(item) > 0)
snowmaking = item + 0.0
if(writetolog)
{
writelog(logfile,myname,"wetbulb temp plugin weather station (version "ver") started.")
writelog(logfile,myname,"polling interval "pollsleep" seconds.")
writelog(logfile,myname,"mb logger command line: '"mb_cmd"'")
}
ssm = strftime("%S",systime()) + (strftime("%M",systime()) * 60) + (strftime("%H",systime()) * 3600) # seconds since midnight
if(pollsleep - ((ssm % pollsleep) > 0))
{
if(writetolog)
writelog(logfile,myname,"inital sleep "pollsleep - (ssm % pollsleep)" seconds.")
exit_code = system("sleep "pollsleep - (ssm % pollsleep)" && exit 27") # initial sleep
}
if(exit_code != 0)
{
do # main plugin infinite loop
{
mb_cmd | getline mb_raw # run os cmd to get raw data from mb
close(mb_cmd)
split(mb_raw,mb_vals, "\t") # parse the tab delimited raw data into individual elements
# mb_vals[1] = drybulb temp °C
# mb_vals[2] = rel humidity %
# mb_vals[3] = station baro mbar
wb_temp = calcwetbulb(mb_vals[1],mb_vals[2],mb_vals[3])
printf("t0 %1.0f\n",wb_temp * 10.0)
# uncomment the following line to collect the source values used to calc the wetbulb temp
# printf("thb0 %1.0f %1.0f %1.0f\n",mb_vals[1] * 10,mb_vals[2],mb_vals[3] * 10)
printf("data0 %d\n",wb_temp < snowposs? 100: 0)
if(snowmaking) # output snowmaking level?
printf("data1 %d\n", wb_temp <= drysnow? 200: wb_temp > drysnow && wb_temp <= wetsnow? 100: 0)
system("") # flush all i/o buffers
mb_raw = ""
ssm = strftime("%S",systime()) + (strftime("%M",systime()) * 60) + (strftime("%H",systime()) * 3600) # seconds since midnight
exit_code = system("sleep "pollsleep - (ssm % pollsleep)" && exit 27") # polling sleep
} while(exit_code != 0)
}
}