Wiki source code of 2 Script

Version 79.1 by Leo Wei on 2023/11/30 11:57

Show last authors
1 = **1 General Script Demo** =
2
3 == **1.1 Address Operation** ==
4
5 (((
6 Write/Read data from address A to B**. **For example:transfer D2 to D0
7 )))
8
9 (% style="text-align:center" %)
10 [[image:1624245865976-320.png||height="182" width="1000" class="img-thumbnail"]]
11
12 Depend on diffferent format of data.V-Box use different script functions.
13 for example. addr_setshort(addr,num) Function: Write 16-bit signed decimal address
14 addr_getshort(addr) Function:Read 16-bit signed decimal address
15 addr_getword(string addr)Function: Read 16-bit unsigned decimal address
16 More script function are in the second section of [[“V-BOX Script Interface Manual”>>doc:V-BOX.V-Net.Manual.04 Lua Script.01 Lua Functions.WebHome]]
17
18 == **1.2 Arithmetic** ==
19
20 (% style="text-align:center" %)
21 [[image:1624249623612-177.png||height="337" width="400" class="img-thumbnail"]]
22
23 == **1.3 Set 100 to D0~-~-D19** ==
24
25 (% style="text-align:center" %)
26 [[image:1624249693457-742.png||height="135" width="400" class="img-thumbnail"]]
27
28 == **1.4 Short message** ==
29
30 The following demo shows that when the alarm condition is reached: temp1 > 5 & temp2 >10 & temp3 < 20(lasts more than 5 seconds) , then send an "alarm trigger" sms.
31
32 When the alarm condition is released,then send an  "alarm release" sms. Script is as below:
33
34 {{code language="lua"}}
35 function sms.main()
36 ------send condition------
37 local temp1 = addr_getword("@Temperature1")
38 local temp2 = addr_getword("@Temperature2")
39 local temp3 = addr_getword("@Temperature3")
40 local timer = addr_getword("@Timer")
41 local tag = addr_getbit("@Tag")
42 ------lasting time------
43 if temp1 > 5 and temp2 > 10 and temp3 < 20 then
44 timer = timer + 1
45 addr_setword("@Timer",timer)
46 else
47 timer = 0
48 addr_setword("@Timer",timer)
49 end
50 ------send sms & output Y0------
51 if timer > 5 then
52 if tag == 0 then
53 send_sms_ira("19859254700","alarm trigger")
54 addr_setbit("@Tag",1)
55 end
56 elseif tag == 1 then
57 send_sms_ira("19859254700","alarm release")
58 addr_setbit("@Tag",0)
59 end
60 end
61 {{/code}}
62
63 == **1.5 Telegram notification** ==
64
65 This example shows how to use the Bot API to send message into Telegram group or channel. When monitoring bit "@HDX" changes, it will trigger and send the message. Please replace with your own Token and chat id.
66
67 As for How to get the botToken and chatID, please check the followig videos:
68
69 [[https:~~/~~/www.youtube.com/watch?v=zh6yYlnjX7k>>https://www.youtube.com/watch?v=zh6yYlnjX7k]]
70
71 [[https:~~/~~/www.youtube.com/watch?v=Pj8mwuMZZvg>>https://www.youtube.com/watch?v=Pj8mwuMZZvg]]
72
73 {{info}}
74 ✎Note:
75
76 1.Bots added to Groups or Channels need to be provided with administrator rights.
77
78 2.
79
80
81 {{/info}}
82
83 === 1.Permissions ===
84
85 Bots added to Groups or Channels need to be provided with administrator rights. For example "theodore" is bot I created.
86
87 (% style="text-align:center" %)
88 [[image:telegram test.jpg||height="370" width="470"]]
89
90 === 2.URL check ===
91
92 You can use the URL to test the status of a group or channel.
93
94 url = "https:~/~/api.telegram.org/bot"..telegramBotToken.."/sendMessage?text="..message.."&chat_id="..telegramChatID
95
96 (% style="text-align:center" %)
97 [[image:telegram URL.png]]
98
99 === 3.Script ===
100
101 {{code language="Lua"}}
102 local tempBit = 0
103 local tempWord = 0
104
105 local botToken = "5504549693:AAEy6a5G-sOF3CINONxMNABeYnoS4ABVlfg"
106 local chatID = "-641959124"--The chat id from Channel or Group
107
108 local https = require("https")
109 local json = require("json")
110
111 -- Send http.get request and return response result
112 function getHttpsUrl(url)
113 local body = {}
114 local bodyJson = json.encode(body)
115 local header = {}
116 header["content-type"] = "application/json"
117 local result_table, code, headers, status = https.request(url, bodyJson)
118 print("code:"..code)
119 if code~= 200 then
120 return
121 else
122 return body
123 end
124 end
125
126 function sendAlarm(telegramBotToken, message, telegramChatID)
127 local url = "https://api.telegram.org/bot"..telegramBotToken.."/sendMessage?text="..message.."&chat_id="..telegramChatID
128 --local url = 'http://v-box.net'
129 --local url = 'https://www.google.com/'
130 print("Get the link:"..url)
131 getHttpsUrl(url)
132 end
133
134
135 function AlarmNotificate.main()
136 local bitValue = addr_getbit("@HDX");
137 local message = ''
138 print("b=="..bitValue)
139 if bitValue == 1 and bitValue ~= tempBit then
140 message = 'Alarm triggered, the monitoring point test value is '.. bitValue
141 sendAlarm(botToken, message, chatID)
142 print("Notification pushed of triggering alarm,"..bitValue)
143 elseif bitValue == 0 and bitValue ~= tempBit then
144 message = 'Alarm dismissed, the monitoring point test value is '.. bitValue
145 sendAlarm(botToken, message, chatID)
146 print("Notification pushed of dismissing alarm,"..bitValue)
147 end
148 tempBit = bitValue----Prevent monitoring values from continuous being sent to the platform
149
150 local wordValue = addr_getword("@HDW10")
151 print("w=="..wordValue)
152 --dosomething
153 if wordValue >= 100 and wordValue ~= tempWord and tempWord <= 100 then
154 message = 'Word alarm triggered, the word value is '.. wordValue
155 sendAlarm(botToken, message, chatID)
156 print("Notification pushed of triggering alarm,"..wordValue)
157 elseif wordValue < 100 and wordValue ~= tempWord and tempWord >= 100 then
158 message = 'Word alarm dismissed, the word value is '.. wordValue
159 sendAlarm(botToken, message, chatID)
160 print("Notification pushed of dismissing alarm,"..wordValue)
161 end
162 tempWord = wordValue----Prevent monitoring values from continuous being sent to the platform
163 end
164 {{/code}}
165
166 == **1.6 LINE Notify** ==
167
168 This example shows how to use the LINE Notify to send message into LINE group. When monitoring bit "@test" changes, it will trigger and send the message. Please replace with your own Token.
169
170 {{code language="lua"}}
171 local tempBit = 0
172 local tempWord = 0
173
174 local LineToken = "08XCpubkOdwGdGgRTXF0x8umiyrALtoM0v6lBFUV6PC"
175
176 local https = require("https")
177 local json = require("json")
178 local ltn12 = require("ltn12")
179
180 -- Send http.get request and return response result
181 function getHttpsUrl(url,header,reqbody)
182 local body = {}
183 local bodyJson = json.encode(body)
184 local result_table, code, headers, status = https.request{
185 method = "POST",
186 url = url,
187 source = ltn12.source.string(reqbody),
188 headers = header,
189 sink = ltn12.sink.table(body)
190 }
191 print("code:"..code)
192 if code~= 200 then
193 return
194 else
195 return body
196 end
197 end
198
199 function getMessageUrl(lineMessage)
200 local url = "https://notify-api.line.me/api/notify"
201 local reqMess = "message="..lineMessage
202 local headers =
203 {
204 ["Authorization"] = "Bearer "..LineToken,
205 ["Content-Type"] = "application/x-www-form-urlencoded",
206 ["Content-Length"] = #reqMess
207 }
208
209 print("Get the link:"..url)
210 getHttpsUrl(url, headers, reqMess)
211 end
212
213
214 function linenotify.main()
215 local bitValue = addr_getbit("@test");
216 local message = ''
217 print("b=="..bitValue)
218 if bitValue == 1 and bitValue ~= tempBit then
219 message = 'Alarm V-Box triggered, the output is '.. bitValue
220 getMessageUrl(message)
221 print("Notification pushed of triggering alarm,"..bitValue)
222 elseif bitValue == 0 and bitValue ~= tempBit then
223 message = 'Alarm V-Box dismissed, the output is '.. bitValue
224 getMessageUrl(message)
225 print("Notification pushed of dismissing alarm,"..bitValue)
226 end
227 tempBit = bitValue----Prevent monitoring values from continuous being sent to the platform
228
229 local wordValue = addr_getword("@t2")
230 print("w=="..wordValue)
231 --dosomething
232 if wordValue >= 100 and wordValue ~= tempWord and tempWord <= 100 then
233 message = 'Alarm V-Box triggered, the temperature is '.. wordValue
234 getMessageUrl(message)
235 print("Notification pushed of triggering alarm,"..wordValue)
236 elseif wordValue < 100 and wordValue ~= tempWord and tempWord >= 100 then
237 message = 'Alarm V-Box dismissed, the temperature is '.. wordValue
238 getMessageUrl(message)
239 print("Notification pushed of dismissing alarm,"..wordValue)
240 end
241 tempWord = wordValue----Prevent monitoring values from continuous being sent to the platform
242 end
243 {{/code}}
244
245 == **1.7 Twilio WhatsApp Messaging** ==
246
247 This example shows how to use the Twilio API to send WhatsApp message to private number. When monitoring bit "@testBit" changes, it will trigger and send the message. Please replace with your own SID, Token, twilioPhoneNumber and receiverPhoneNumber.
248
249 About how to register the Twilio API, please check the following video:
250
251 [[https:~~/~~/www.youtube.com/watch?v=Id4lKichauU>>https://www.youtube.com/watch?v=Id4lKichauU]]
252
253 {{code language="Lua"}}
254 local tempBit = 0
255 local tempWord = 0
256
257 local https = require("https")
258 local json = require("json")
259 local ltn12 = require("ltn12")
260
261 local SID = 'AC1703bd710ffa98006d2bcc0b********'
262 local Token = 'd3c11897623c39e538b20263ec19****'
263
264 local twilioPhoneNumber = '+14155238886'
265 local receiverPhoneNumber = '+8615880018277'
266
267 local b='ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'
268 function encodingBase64(data)
269 return ((data:gsub('.', function(x)
270 local r,b='',x:byte()
271 for i=8,1,-1 do r=r..(b%2^i-b%2^(i-1)>0 and '1' or '0') end
272 return r;
273 end)..'0000'):gsub('%d%d%d?%d?%d?%d?', function(x)
274 if (#x < 6) then return '' end
275 local c=0
276 for i=1,6 do c=c+(x:sub(i,i)=='1' and 2^(6-i) or 0) end
277 return b:sub(c+1,c+1)
278 end)..({ '', '==', '=' })[#data%3+1])
279 end
280
281 function encodeUrl(str)
282 str = string.gsub(str, "([^%w%.%- ])", function(c)
283 return string.format("%%%02X", string.byte(c)) end)
284 return string.gsub(str, " ", "+")
285 end
286
287
288
289
290 function requestBodySplice(message, sender, receiver)
291 local reqBody = ''
292 local encodeMess = encodeUrl(message)
293 local encodeSend = encodeUrl(sender)
294 local encodeRece = encodeUrl(receiver)
295 --reqBody = "Body=Hello%20Wecon2&From=whatsapp%3A%2B14155238886&To=whatsapp%3A%2B8615880018277"
296 reqBody = string.format("Body=%s&From=whatsapp:%s&To=whatsapp:%s", encodeMess, encodeSend, encodeRece)
297 print(reqBody)
298 return reqBody
299 end
300
301
302 -- Send http.get request and return response result
303 function getHttpsUrl(url,header,reqbody)
304 local body = {}
305 local bodyJson = json.encode(body)
306 local result_table, code, headers, status = https.request{
307 method = "POST",
308 url = url,
309 source = ltn12.source.string(reqbody),
310 headers = header,
311 sink = ltn12.sink.table(body)
312 }
313 print("code:"..code)
314 if code~= 200 then
315 return
316 else
317 return body
318 end
319 end
320
321 function getMessageUrl(whatsAppMessage)
322 local auth = SID..':'..Token
323 local url = "https://api.twilio.com/2010-04-01/Accounts/"..SID.."/Messages"
324 --local reqMess = "message="..twilioMessage
325 local reqMess = requestBodySplice(whatsAppMessage, twilioPhoneNumber, receiverPhoneNumber)
326 local headers =
327 {
328 ["Authorization"] = "Basic "..encodingBase64(auth),
329 ["Content-Type"] = "application/x-www-form-urlencoded",
330 ["Content-Length"] = #reqMess
331 }
332
333 print("Get the link:"..url)
334 getHttpsUrl(url, headers, reqMess)
335 end
336
337
338
339 function Twilio.main()
340 --dosomething
341 --local auth = SID..':'..Token
342 --print(requestBodySplice("HelloWorld", twilioPhoneNumber, receiverPhoneNumber))
343 --print(encodingBase64(auth))
344 local bitValue = addr_getbit("@testBit");
345 local message = ''
346 print("b=="..bitValue)
347 if bitValue == 1 and bitValue ~= tempBit then
348 message = 'Alarm V-Box triggered, the output is '.. bitValue
349 getMessageUrl(message)
350 print("Notification pushed of triggering alarm,"..bitValue)
351 elseif bitValue == 0 and bitValue ~= tempBit then
352 message = 'Alarm V-Box dismissed, the output is '.. bitValue
353 getMessageUrl(message)
354 print("Notification pushed of dismissing alarm,"..bitValue)
355 end
356 tempBit = bitValue----Prevent monitoring values from continuous being sent to the platform
357
358 local wordValue = addr_getword("@testWord")
359 print("w=="..wordValue)
360 --dosomething
361 if wordValue >= 100 and wordValue ~= tempWord and tempWord <= 100 then
362 message = 'Alarm V-Box triggered, the temperature is '.. wordValue
363 getMessageUrl(message)
364 print("Notification pushed of triggering alarm,"..wordValue)
365 elseif wordValue < 100 and wordValue ~= tempWord and tempWord >= 100 then
366 message = 'Alarm V-Box dismissed, the temperature is '.. wordValue
367 getMessageUrl(message)
368 print("Notification pushed of dismissing alarm,"..wordValue)
369 end
370 tempWord = wordValue----Prevent monitoring values from continuous being sent to the platform
371 end
372 {{/code}}
373
374 == **1.8 HTTP response body** ==
375
376 This example use [[https:~~/~~/www.weatherapi.com/>>https://www.weatherapi.com/]] as example, to show how to parse value from HTTP response body. When we input the city name into address "@HDW5050":
377
378 (% style="text-align:center" %)
379 [[image:InputHTTPparameter.png]]
380
381 Then the response body would be like as following:
382
383 {{code language="json"}}
384 {
385 "location": {
386 "name": "Madrid",
387 "region": "Madrid",
388 "country": "Spain",
389 "lat": 40.4,
390 "lon": -3.68,
391 "tz_id": "Europe/Madrid",
392 "localtime_epoch": 1669022636,
393 "localtime": "2022-11-21 10:23"
394 },
395 "current": {
396 "last_updated_epoch": 1669022100,
397 "last_updated": "2022-11-21 10:15",
398 "temp_c": 13.0,
399 "temp_f": 55.4,
400 "is_day": 1,
401 "condition": {
402 "text": "Partly cloudy",
403 "icon": "//cdn.weatherapi.com/weather/64x64/day/116.png",
404 "code": 1003
405 },
406 "wind_mph": 11.9,
407 "wind_kph": 19.1,
408 "wind_degree": 210,
409 "wind_dir": "SSW",
410 "pressure_mb": 1015.0,
411 "pressure_in": 29.97,
412 "precip_mm": 0.0,
413 "precip_in": 0.0,
414 "humidity": 88,
415 "cloud": 75,
416 "feelslike_c": 10.8,
417 "feelslike_f": 51.4,
418 "vis_km": 10.0,
419 "vis_miles": 6.0,
420 "uv": 3.0,
421 "gust_mph": 22.1,
422 "gust_kph": 35.6
423 }
424 }
425 {{/code}}
426
427 (% class="wikigeneratedid" %)
428 So we decode json into lua object to assign the value into addresses HDW6060(temperature), HDW7070(humidity), the code example like follows:
429
430 {{code language="lua"}}
431 local APIkey = '70faaecf926b4341b1974006221711'
432
433
434 local http = require("socket.http")
435 local json = require("json")
436
437 -- Send http.get request and return response result
438 function getHttpsUrl(url)
439 local result_table, code, headers, status = http.request(url)
440 print("code:"..code)
441 if code~= 200 then
442 return
443 else
444 return result_table
445 end
446 end
447
448 function sendAPI(key, city)
449 local url = "http://api.weatherapi.com/v1/current.json?key="..key.."&q="..city.."&aqi=no"
450 --local url = 'http://v-box.net'
451 --local url = 'https://www.google.com/'
452 --http://api.weatherapi.com/v1/current.json?key=70faaecf926b4341b1974006221711&q=Barcelona&aqi=no
453 print("Get the link:"..url)
454 local body = getHttpsUrl(url)
455 --print(body)
456 local jsonBody = json.decode(body)
457 --print(jsonBody["current"]["temp_c"])
458 --print(type(jsonBody["current"]["temp_c"]))
459 --print(type(jsonBody["current"]["humidity"]))
460 addr_setfloat("@HDW6060", jsonBody["current"]["temp_c"])
461 addr_setword("@HDW7070", jsonBody["current"]["humidity"])
462 end
463
464
465 function Weather.main()
466 local cityName = addr_getstring("@HDW5050",6)
467 print("cityName: "..cityName)
468 sendAPI(APIkey, cityName)
469 end
470 {{/code}}
471
472 == **1.9 High-Low Byte Switch** ==
473
474 The following example is converting the floating number from order 1234 to order 3412, and formating output the number with 2 decimal point. About which high-low word order corresponding to which value, please refer to the [[Address Operation Table>>doc:V-BOX.V-Net.Manual.04 Lua Script.01 Lua Functions.WebHome||anchor="H2Addressoperation"]].
475
476 {{code language="lua"}}
477 function highLowByteSwitch(floatNumber)
478 addr_setfloat("@W_0#HDW23036",floatNumber,0,2)
479 local newFloat = addr_getfloat("@W_0#HDW23036")
480 local formattedFloat = string.format("%.2f",newFloat)
481 print("The formatted float value is the : "..formattedFloat)
482 return formattedFloat
483 end
484 {{/code}}
485
486 == **1.10 Read 64bits Unsigned Value** ==
487
488 In our built-in function library doesn't have the function for reading 64-bit unsigned format value, so the following function is for solve this. But if the number is greater 2^53, the precision will be lost. So the final result will be a little bit different from the original value.
489
490 {{code language="lua"}}
491 function addr_getquatra(address)
492 local highAddress = addr_newnoaddr(address,2)
493 local low32 = addr_getdword(address)
494 local high32 = addr_getdword(highAddress)
495 --print("the low number is "..low32)
496 --print("the high number is "..high32)
497 local formatVal = string.format("%64.0f",2^32*high32+low32)
498 print("the format value is ".. formatVal)
499 return formatVal
500 end
501 {{/code}}
502
503 = **2 Third part server** =
504
505 V-Box have two mode.One is for V-Net,User need to use WECON server to store data.We call this V-NET platform.
506
507 (% class="mark" %)1.Europe server:eu.v-box.net
508
509 (% class="mark" %)2.Asean server:asean.v-box.net
510
511 Second is for OpenCloud mode.It means V-Box data will transfer to third part server and do not want to store data to WECON server.We call OpenCloud paltform
512
513 OpenCloud platform is used in configuring the script.Then V-Box can connect with third part server.
514
515 Both mode can support script  to connect with third part server.the difference:
516
517 (% class="mark" %)1.If you want to store in WECON server ,please use V-NET.
518
519 (% class="mark" %)2.If your server requires SSL certificate to log in,please use OpenCloud.Because only OpenCloud platform can support to upload certificate
520
521 {{info}}
522 **✎Note: **Before program the script of MQTT, please make sure the server(MQTT broker) can be connected through MQTT Client tool.
523 {{/info}}
524
525 (% class="wikigeneratedid" %)
526 Tool link: **[[MQTT.fx>>http://mqttfx.jensd.de/index.php/download]]**
527
528 == **2.1 Test server(General Example)** ==
529
530 The following example is trying to publish to the topic "testtopic/test/no1/7890", and subscribe the topic "testtopic/test/no1/123456".
531
532 And the JSON message is like follows:
533
534 {{code language="JSON"}}
535 {
536 "timestamp": 1631152760,
537 "messageId": 1,
538 "event": "test_data",
539 "mfrs": "HMI/box",
540 "data":
541 {
542 "id" : 1436217747670454274,
543 "waterlevel" : 48,
544 "temperture" : 23
545 }
546 }
547 {{/code}}
548
549 {{code language="lua"}}
550 --MQTT configuration table
551 local MQTT_CFG={}
552 --if there is no need the username and password, please put them as ""
553 MQTT_CFG.username = "weconsupport"
554 MQTT_CFG.password = "123456"
555 MQTT_CFG.netway = 0
556 MQTT_CFG.keepalive = 60
557 MQTT_CFG.cleansession = 1
558 --TCP URL
559 MQTT_URL = "tcp://mq.tongxinmao.com:1883"
560 --Client ID
561 MQTT_CLIENT_ID = "V-BOXH-AG"
562
563 --Generate UUID
564 function uuid()
565 local seed = {'e','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f'}
566 local tb = {}
567 for i=1, 32 do
568 table.insert(tb, seed[math.random(1,16)])
569 end
570 local sid=table.concat(tb)
571 return string.format('%s',
572 string.sub(sid,1,32)
573 )
574 end
575
576
577 --Topic name to subscribed
578 local SUBSCRIBE_TOPIC = 'testtopic/test/no1/123456'
579
580 --Topic name to be published
581 local PUBLISH_TOPIC = 'testtopic/test/no1/7890'
582
583
584 --real time
585 local LAST_TIME = 0
586
587
588 --initialize mqtt
589 function mqtt_init()
590 print(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENT_ID))
591 if g_mq then
592 mqtt.close(g_mq) --Close mqtt object
593 end
594 g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENT_ID) -- create mqtt object,and declare it as a global variable
595 if g_mq then
596 g_mq:on("message", mqtt_msg_callback) -- Register a callback for receiving messages
597 g_mq:on("offline", mqtt_msg_offline) -- Register a callback for offline
598 print("mqtt init success")
599 else
600 print("mqtt init failed:", err)
601 end
602 end
603
604 -- connect to mqtt
605 function mqtt_connect()
606 print("mqtt connecting...")
607 local stat, err = g_mq:connect(MQTT_CFG)
608 if stat == nil then
609 print("mqtt connect failed:", err)
610 return
611 else
612 print("mqtt connected")
613 end
614 g_mq:subscribe(SUBSCRIBE_TOPIC, 0)
615 end
616
617 --Offline callback function
618 function mqtt_msg_offline(cause)
619 print("mqtt offline, cause:", cause)
620 end
621
622 -- Received message callback function
623 function mqtt_msg_callback(topic, msg)
624 print("topic:", topic)
625 print("msg:", msg)
626 local objMsg = json.decode(msg)
627 local water = objMsg.data.waterlevel
628 local temp = objMsg.data.temperature
629 addr_setword("@HDW20",water)
630 addr_setword("@HDW10",temp)
631 end
632
633 --Send data (data upload to platform and encapsulate it with custom functions)
634 function send_data()
635 local pub_data = {
636 timestamp = os.time(),
637 messageId = 1,
638 event = 'test_data',
639 mfrs = 'V-Box',
640 data = {
641 id = uuid(),
642 waterlevel = addr_getword("@HDW10"),
643 temperature = addr_getword("@HDW20")
644 }
645 }
646 return g_mq:publish(PUBLISH_TOPIC, json.encode(pub_data), 0, 0)
647 end
648
649
650 --main function fixed timed execution
651 function MQTT.main()
652 --dosomething
653 print(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " main start")
654 --determine the mqtt object whether exist
655 if g_mq then
656 --determine the mqtt object whether has been connected or not
657 if g_mq:isconnected() then
658 send_data()
659 else
660 --if exceed 5 sec not connect, reconnect once
661 if os.time() - LAST_TIME > 5 then
662 LAST_TIME = os.time()
663 --reinitial the mqtt object
664 mqtt_init()
665 --connect to mqtt or reconnect
666 mqtt_connect()
667 end
668 end
669 else
670 --mqtt object does not exist so create new one
671 mqtt_init()
672 end
673 print(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " main end")
674 end
675 {{/code}}
676
677 == **2.2 Customer server:grouprobotinfo.com** ==
678
679 This demo does not use SSL certification. Script is as below
680
681 Demo1:
682
683 {{code language="lua"}}
684 -- Meta class
685 --main
686 function mq.main()
687 if not mq.m then
688 local err = ""
689
690 mq.m, err = mqtt.create("tcp://grouprobotinfo.com:1883", "ClienID") -- create connection
691 if mq.m then
692 mq.config = {
693 username = "",-- ID
694 password = "",-- password
695 netway = 1, -- Ethernet connection, WIFI=1
696 -- keepalive = 100, -- Optional, set the connection heartbeat interval for 100 seconds.
697 -- cleansession = 0, -- Optional, keep session
698 }
699 mq.m:on("message", function(topic, msg) -- Register for receiving message callbacks
700 local str = string.format("%s:%s", topic, msg)
701 -- print("mqtt msg:", str) -- Print out the received topics and content
702 end)
703 mq.m:on("offline", function (cause) -- Register for lost connection callbacks
704 -- addr_setstring("@xxx", "cause"..(cause or " got nil"))
705 end)
706 mq.m:on("arrived", function() -- Registration for sending messages to callbacks
707 print("msg arrived")
708 end)
709 else
710 print("mqtt create failed:", err) -- Create object failed
711 end
712 else
713 if mq.m:isconnected() then -- If online, post a message
714 local phaseStatus ="unknow"
715 if addr_getbit("@Standby")== 1 then
716 phaseStatus = "Standby"
717 elseif addr_getbit("@Pre-Freeze")==1 then
718 phaseStatus= "Pre-Freeze"
719 elseif addr_getbit("@Prepare")==1 then
720 phaseStatus ="Prepare"
721 elseif addr_getbit("@Primary Dry")==1 then
722 phaseStatus = "Primary dry"
723 elseif addr_getbit("@Secondary Dry")==1 then
724 phaseStatus = "Secondary Dry"
725 end
726 --print(addr_getbit("@Primary Dry"))
727 -------------------------------------------------------------------------------------------------------------------------
728 local activating ="unknow"
729 if addr_getbit("@Compressor")==1 then
730 activating = ",".."Compressor"
731 end
732 if addr_getbit("@Silicone Pump")==1 then
733 activating = activating..",".."Silicone Pump"
734 end
735 if addr_getbit("@Vacuum Pump")==1 then
736 activating = activating..",".."Vacuum Pump"
737 end
738 if addr_getbit("@Root Pump")==1 then
739 activating = activating..",".."Root Pump"
740 end
741 if addr_getbit("@Heater")==1 then
742 activating = activating..",".."Heater"
743 end
744 if addr_getbit("@Valve Silicone")==1 then
745 activating = activating..",".."Valve Silicone"
746 end
747 if addr_getbit("@Valve Ice Condenser")==1 then
748 activating = activating..",".."Valve Ice Condenser"
749 end
750 if addr_getbit("@Valve Vacuum Pump")==1 then
751 activating = activating..",".."Valve Vacuum Pump"
752 end
753 local pr_activating =string.sub(activating,2)
754 -- print(pr_activating)
755 local status_text ="unknow"
756 if addr_getbit("@Status Run")==1 then
757 status_text = "RUNNING"
758 else
759 status_text = "STOP"
760 end
761 -------------------------------------------------------------------------------------------------------------------------
762 local js = {type="status",
763 mc_name ="FD300",
764 status=status_text,
765 elapsed_time={
766 hour=addr_getword("@Elapsed Time (Hour)"),
767 min=addr_getword("@Elapsed Time (Minute)"),
768 sec=addr_getword("@Elapsed Time (Second)")
769 },
770 phase = phaseStatus,
771 step = addr_getword("@Step"),
772 activating_output = pr_activating,
773 sv=addr_getshort("@SV Silicone")/10,
774 pv=addr_getshort("@PV Silicone")/10,
775 product1=addr_getshort("@Product 1")/10,
776
777 product2=addr_getshort("@Product 2")/10,
778 product3=addr_getshort("@Product 3")/10,
779 product4=addr_getshort("@Product 4")/10,
780 ice1=addr_getshort("@Ice condenser 1")/10,
781 ice2=addr_getshort("@Ice condenser 2")/10,
782 vacuum=addr_getfloat("@Vacuum")
783 }
784 local jsAlarm = { HPC = addr_getbit("@B_25395#W0.00"),
785 ODPC = addr_getbit("@B_25395#W0.01"),
786 MTPC=addr_getbit("@B_25395#W0.02"),
787 HTT = addr_getbit("@B_25395#W1.03"),
788 CPC = addr_getbit("@B_25395#W0.08"),
789 CPSP =addr_getbit("@B_25395#W1.00"),
790 CPVP =addr_getbit("@B_25395#W0.10"),
791 CPRP =addr_getbit("@B_25395#W0.11"),
792 HP =addr_getbit("@B_25395#W1.01"),
793 PP= addr_getbit("@B_25395#W1.02"),
794 PO=addr_getbit("@B_25395#W0.07"),
795 FSE=addr_getbit("@B_25395#W2.04"),
796 AVVSVV=addr_getbit("@B_25395#W1.12"),
797 ICHT=addr_getbit("@B_25395#W3.06")
798 }
799 -- ("@B_25395#CIO1.02")
800 mq.m:publish("mqtt-v-box-epsilon-fd300", json.encode(js) , 0, 0)
801 mq.m:publish("mqtt-v-box-epsilon-alarm-fd300", json.encode(jsAlarm) , 0, 0)
802 else
803 local stat, err = mq.m:connect(mq.config) -- connection
804 if stat == nil then --Determine whether to connect
805 print("mqtt connect failed:", err)
806 return -- Connection failed, return directly
807 end
808 mq.m:subscribe("mqtt-v-box-epsilon", 0)-- Subscribe to topics
809
810 end
811 -- mq.m:unsubscribe("stc/test")
812 -- mq.m:disconnect() -- close matt
813 -- mq.m:close() -- close clase
814 end
815 end
816 {{/code}}
817
818 == **2.3 Azure platform** ==
819
820 In this demo,V-Box connects with Azure by SSL certification.
821
822 Video link: [[https:~~/~~/youtu.be/cdI6rIQcpMY?list=PL_Bpnb2RgaksCic9HCcVAZhU9sYwCRKzW>>https://youtu.be/cdI6rIQcpMY?list=PL_Bpnb2RgaksCic9HCcVAZhU9sYwCRKzW]]
823
824 Tool Download link: [[https:~~/~~/wecon-disk.oss-ap-southeast-1.aliyuncs.com/Download/WIKI/V-BOX/Demo/Azure/Azure%20tool.zip>>https://wecon-disk.oss-ap-southeast-1.aliyuncs.com/Download/WIKI/V-BOX/Demo/Azure/Azure%20tool.zip]]
825
826 Script is as below
827
828 {{code language="lua"}}
829 --https://support.huaweicloud.com/qs-IoT/iot_05_0005.html  mqtt.fx monitor to connect azure iot
830 sprint = print
831
832 --Get custom configuration parameters (vbox custom information)
833 --local CUSTOM = bns_get_config("bind")
834 --local DS_ID = CUSTOM.DSID or "60a71ccbbbe12002c08f3a1a_WECON"
835
836
837
838 --Cloud mode interface to obtain the MQTT information configured by the cloud platform: (5 returns, namely the server address, client ID, connection table, last word table, certificate table)
839 local MQTT_URL, MQTT_CLIENTID, MQTT_CFG, MQTT_LWT, MQTT_CART = mqtt.setup_cfg()
840
841 --MQTT_CFG.username = '60a71ccbbbe12002c08f3a1a_WECON'
842 --MQTT_CFG.password='wecon123'
843 --MQTT_CLIENTID = '60a71ccbbbe12002c08f3a1a_WECON_0_0_2021052110usernxame:60a71ccbbbe12002c08f3a1a_WECONpassword:a0a951581855aa8e0262129da6cf1b43f2c0ecfac4fa56117fc5a20c90be169a'
844
845 --publish to topics
846 local pub_RE_TOPIC = string.format('devices/wecon_02/messages/events/')
847 --Subscribe topics
848 local Subscribe_RE_TOPIC1 = string.format('devices/wecon_02/messages/devicebound/#')
849
850 --variable
851 local last_time = 0
852
853
854
855 --Timing main function
856 function Azure.main()
857
858    sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " Azureiot.main start")
859    if g_mq then
860         if g_mq:isconnected() then
861             send_Data()
862         else
863             if os.time() - last_time > 20 then
864                 last_time = os.time()
865                 mymqtt_connect()
866             end
867         end
868     else
869         mymqtt_init()
870     end
871     sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " Azureiot.main end")
872 end
873
874 -- Initialize MQTT
875 function mymqtt_init()
876     sprint(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENTID))
877     g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENTID) -- Create the object and declare it as a global variable
878     if g_mq then
879         g_mq:on("message", mymqtt_msg_callback) -- Register to receive message callbacks
880         sprint("mqtt init success")
881     else
882         sprint("mqtt init failed:", err)
883     end
884 end
885
886 -- Connect to MQTT server
887 function mymqtt_connect()
888     sprint("mqtt connecting...")
889     local stat, err = g_mq:connect(MQTT_CFG,MQTT_LWT, MQTT_CART)
890     if stat == nil then
891         sprint("mqtt connect failed:", err)
892         return
893     else
894         sprint("mqtt connected")
895     end
896     g_mq:subscribe(Subscribe_RE_TOPIC1, 0) 
897 end
898
899 -- Receive MQTT message callback function
900 function mymqtt_msg_callback(topic, msg)
901     print("topic:",topic)
902     print("revdata:",msg)
903    -- local revData = json.decode(msg)
904  --  if topic == Subscribe_RE_TOPIC1 then --Process topic information subscribed from the cloud
905 -- if string.match(topic,Subscribe_RE_TOPIC1) then
906      --   print("topi11:",topic)
907        setValue(revData)
908    -- end
909 end
910
911 --Process the received data
912 --function setValue(revData)
913    -- if revData ~=nil then 
914  --       for i,v in pairs(revData) do
915   --          print("Data received:",i,v)
916   --      end
917    -- end
918 --end
919
920 --Get real-time data
921 function getData()
922     local jdata = {}
923     local addr = bns_get_alldata()
924     print(json.encode(addr))
925     for i,v in pairs(addr) do
926         if v[2] == 1 then
927            jdata[v[3]] = v[4]
928         end
929     end
930     return jdata
931 end 
932
933
934
935 --send data
936 function send_Data()
937     local pub_data = {100
938      --   services={{
939
940             --serviceId ='Temperature',
941            -- properties={
942                -- value = 55
943            -- },
944        -- }}
945 }
946 sprint(json.encode(pub_data))
947 print("..........",pub_RE_TOPIC)
948     return g_mq:publish(pub_RE_TOPIC, json.encode(pub_data), 0, 0)
949 end
950 {{/code}}
951
952 == **2.4 Huawei platform** ==
953
954 {{info}}
955 **✎Note**:**Huawei IOT DA function is only in China area.If you want this function,you need to use chinese mobile to register**
956 {{/info}}
957
958 1.Register a account: [[https:~~/~~/www.huaweicloud.com/intl/en-us/s/JUlPVERNJQ>>https://www.huaweicloud.com/intl/en-us/s/JUlPVERNJQ]]
959
960 2.log in the Huawei IOTDA
961
962 [[https:~~/~~/console.huaweicloud.com/iotdm/?region=cn-north-4&locale=en-us#/dm-portal/home>>https://console.huaweicloud.com/iotdm/?region=cn-north-4&locale=en-us#/dm-portal/home]]
963
964 3.Create product
965
966 (% style="text-align:center" %)
967 [[image:1624433478954-859.png||height="497" width="1100" class="img-thumbnail"]]
968
969 4.Product name,manufacturer,device type and industry,set according to your own needs.
970
971 Protocol: MQTT
972
973 Data Type: JSON
974
975 After finishing configuration,please click "OK"
976
977 (% style="text-align:center" %)
978 [[image:1624433531968-337.png||height="568" width="700" class="img-thumbnail"]]
979
980 5.Device
981
982 After product register,continue to configure "individual register".Click "Device"~-~->"individual register"
983
984 (% style="text-align:center" %)
985 [[image:1624434757597-117.png||class="img-thumbnail"]]
986
987 **Notes for registering device:**
988
989 Product: Previous product registration.
990
991 Node ID, Device Name: set according to your own needs.
992
993 Secret: need to be configured, will be used when connecting later
994
995 After configuration, click OK to generate a device ID and password, which will be used for device access later.
996
997 (% style="text-align:center" %)
998 [[image:1624436421499-613.png||height="499" width="700" class="img-thumbnail"]]
999
1000 (% style="text-align:center" %)
1001 [[image:1624437798012-126.png||height="366" width="500" class="img-thumbnail"]]
1002
1003 6. Connection authentication (use MQTT.fx tool to access the IoT platform)
1004
1005 (1)Open mqttClientIdGenerator tool Java(TM) Platform SE binary
1006
1007 **[[Download>>https://wecon-disk.oss-ap-southeast-1.aliyuncs.com/Download/WIKI/V-BOX/Demo/Huawei/mqttClientIdGenerator-19.2.0.zip]]**
1008
1009 (% style="text-align:center" %)
1010 [[image:1624437573798-815.png||height="351" width="700" class="img-thumbnail"]]
1011
1012 (2)Fill in the device ID and secret (deviceid and secret generated when registering the device) to generate connection message
1013
1014 Client ID, user name, password
1015
1016 (% style="text-align:center" %)
1017 [[image:1624437756866-251.png||height="405" width="700" class="img-thumbnail"]]
1018
1019 (3) Download certificate file"North-Beijing4"
1020
1021 [[https:~~/~~/support.huaweicloud.com/en-us/devg-iothub/iot_02_1004.html>>https://support.huaweicloud.com/en-us/devg-iothub/iot_02_1004.html]]
1022
1023 (% style="text-align:center" %)
1024 [[image:1624438225398-363.png||height="403" width="800" class="img-thumbnail"]]
1025
1026 (% style="text-align:center" %)
1027 [[image:1624438260025-610.png||height="408" width="700" class="img-thumbnail"]]
1028
1029 7.Run MQTTfx tool to connect with Huawei
1030
1031 Download link: [[http:~~/~~/mqttfx.jensd.de/index.php/download>>url:http://mqttfx.jensd.de/index.php/download]]
1032
1033 (1)Click on the setting ICON
1034
1035 (% style="text-align:center" %)
1036 [[image:1624438821280-974.png||height="198" width="500" class="img-thumbnail"]]
1037
1038 (2)Fill in IIOT MQTT device access address, and configure authentication parameters.
1039 First: It is the server and port connected to Huawei IOT, which can be viewed through the overview of the interface.
1040
1041 (% style="text-align:center" %)
1042 [[image:1624439086268-985.png||class="img-thumbnail"]]
1043
1044 Domain name:iot-mqtts.cn-north-4.myhuaweicloud.com
1045
1046 Port: 8883
1047
1048 Client ID: check step 6
1049
1050 (% style="text-align:center" %)
1051 [[image:1624439672168-492.png||height="458" width="600" class="img-thumbnail"]]
1052
1053 (3)Upload SSL certificate file,check step 6
1054
1055 Select folder java~-~->DigiCertGlobalRootCA.crt.pem and click OK or apply button
1056
1057 (% style="text-align:center" %)
1058 [[image:1624439912938-659.png||height="458" width="600" class="img-thumbnail"]]
1059
1060 (4)Connect and test publish and subscribe
1061
1062 (% style="text-align:center" %)
1063 [[image:1624440014872-688.png||height="232" width="700" class="img-thumbnail"]]
1064
1065 (% style="text-align:center" %)
1066 [[image:1624440026937-386.png||height="215" width="700" class="img-thumbnail"]]
1067
1068 Huawei publish topic format: $oc/devices/{device_id}/sys/properties/report
1069
1070 (% style="text-align:center" %)
1071 [[image:1624440404119-815.png||class="img-thumbnail"]]
1072
1073 Huawei subscribe topic format: **$oc/devices/{device_id}/sys/commands/#**
1074
1075 (% style="text-align:center" %)
1076 [[image:1624447157493-672.png||class="img-thumbnail"]]
1077
1078 (% style="text-align:center" %)
1079 [[image:1624447209982-715.png||class="img-thumbnail"]]
1080
1081 (5).How to configure to view the received data format intuitively, multiple products (Huawei) are required to configure the model. The specific steps are as follows:
1082 ①Select the corresponding product from Huawei products to view
1083
1084 (% style="text-align:center" %)
1085 [[image:1624440647663-632.png||class="img-thumbnail"]]
1086
1087 ②Custom model: used to display the service ID name of the configuration report.
1088
1089 (% style="text-align:center" %)
1090 [[image:1624440793982-974.png||height="410" width="700" class="img-thumbnail"]]
1091
1092 (% style="text-align:center" %)
1093 [[image:1624440883015-105.png||height="370" width="600" class="img-thumbnail"]]
1094
1095 ③Add property, ID of monitoring point, and data format:
1096
1097 (% style="text-align:center" %)
1098 [[image:1624441052296-108.png||height="477" width="600" class="img-thumbnail"]]
1099
1100 ④After the configuration is complete, check the received data on the device
1101
1102 (% style="text-align:center" %)
1103 [[image:1624441186851-536.png||height="434" width="700" class="img-thumbnail"]]
1104
1105 === Huawei by SSL certification. ===
1106
1107 1.Create a project access for Huawei IOT
1108
1109 2.configure MQTT configuration
1110
1111 (% style="text-align:center" %)
1112 [[image:1624506363847-661.png||height="507" width="1000" class="img-thumbnail"]]
1113
1114 3.Create a script with the demo as below.
1115
1116 Script is as below
1117
1118 (% class="box infomessage" %)
1119 (((
1120 (% class="box infomessage" %)
1121 (((
1122 ~-~- mqtt.fx simulated access to Huawei Cloud IoT platform refer to 2.4
1123 sprint = print
1124
1125 ~-~-Get custom configuration parameters (gateway customization information)
1126 local CUSTOM = bns_get_config("bind")
1127 local DS_ID = CUSTOM.DSID or "5dfa0700df1ae506179afb9c_wecon"
1128
1129
1130 ~-~-OpenCloud mode interface, obtain MQTT information configured on cloud platform: (5 returned, respectively server address, client ID, connection table, last word table, certificate table)
1131 local MQTT_URL, MQTT_CLIENTID, MQTT_CFG, MQTT_LWT, MQTT_CART = mqtt.setup_cfg()
1132
1133 MQTT_CFG.username =DS_ID
1134 MQTT_CFG.password='d030d92338fcc18cd10fabb3003a4a0f6620fa6822cd3c23b1d9bc790200c6e7'
1135 MQTT_CLIENTID = '5dfa0700df1ae506179afb9c_wecon_0_0_2019121819'
1136
1137 ~-~-publish topic format:$oc/devices/{device id}/sys/properties/report
1138
1139 local pub_RE_TOPIC = string.format('$oc/devices/60a71ccbbbe12002c08f3a1a_WECON/sys/properties/report')
1140
1141 ~-~-variate
1142 local last_time = 0
1143
1144
1145 ~-~-Timing principal function
1146 function hwyiot.main()
1147
1148 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " hwyiot.main start")
1149 if g_mq then
1150 if g_mq:isconnected() then
1151 send_Data()
1152 else
1153 if os.time() - last_time > 20 then
1154 last_time = os.time()
1155 mymqtt_connect()
1156 end
1157 end
1158 else
1159 mymqtt_init()
1160 end
1161 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " hwyiot.main end")
1162 end
1163
1164 ~-~- initializationMQTT
1165 function mymqtt_init()
1166 sprint(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENTID))
1167 g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENTID) ~-~- Create the object and declare it as a global variable
1168 if g_mq then
1169 g_mq:on("message", mymqtt_msg_callback) ~-~- Register to receive message callbacks
1170 sprint("mqtt init success")
1171 else
1172 sprint("mqtt init failed:", err)
1173 end
1174 end
1175
1176 ~-~- Connect to the MQTT server
1177 function mymqtt_connect()
1178 sprint("mqtt connecting...")
1179 local stat, err = g_mq:connect(MQTT_CFG,MQTT_LWT, MQTT_CART)
1180 if stat == nil then
1181 sprint("mqtt connect failed:", err)
1182 return
1183 else
1184 sprint("mqtt connected")
1185 end
1186
1187 ~-~-subscribe topic format:$oc/devices/{device_id}/sys/commands/#
1188
1189 g_mq:subscribe('$oc/devices/60a71ccbbbe12002c08f3a1a_WECON/sys/commands/#', 0) 
1190 end
1191
1192 ~-~- Receive the message callback function
1193 function mymqtt_msg_callback(topic, msg)
1194 sprint("recv data!")
1195 sprint("topic:msg", topic,msg)
1196 print(msg)
1197 local revData = json.decode(msg)
1198 \\end
1199
1200 ~-~-Send data
1201 function send_Data()
1202 local pub_data = {
1203 msgType = 'deviceReq',
1204 data = ~{~{
1205 serviceId ='Battery',
1206 serviceData={
1207 batteryLevel = 55
1208 }
1209 }}
1210 }
1211 return g_mq:publish(pub_RE_TOPIC, json.encode(pub_data), 0, 0)
1212 end
1213 )))
1214 )))
1215
1216 4.Download project access into V-Box to test in debug page
1217
1218 (% style="text-align:center" %)
1219 [[image:1624506710354-406.png||height="658" width="1000" class="img-thumbnail"]]
1220
1221 (% style="text-align:center" %)
1222 [[image:1624506666650-161.png||height="547" width="1000" class="img-thumbnail"]]
1223
1224 == **2.6 AWS platform** ==
1225
1226 === **Log in AWS** ===
1227
1228 Login aws account and click“Connect an IoT device”
1229
1230 [[image:image-20220709165402-1.png]]
1231
1232 [[image:image-20220709165402-2.png]]
1233
1234
1235 === **Create policy** ===
1236
1237 Click “Secure”~-~-->“Policies”~-~-->“Create policy”~-~-->Click “Create”
1238
1239 [[image:image-20220709165402-3.png]]
1240
1241 Name the policy~-~-->Click “JSON”~-~-->Copy the following content~-~-->Click “Create”
1242
1243 [[image:image-20220709165402-5.png]]
1244
1245 [[image:image-20220709165402-4.png]]
1246
1247 {{code language="java"}}
1248 {
1249   "Version": "2012-10-17",
1250   "Statement": [
1251     {
1252       "Effect": "Allow",
1253       "Action": [
1254         "iot:Connect",
1255         "iot:Publish",
1256         "iot:Subscribe",
1257         "iot:Receive",
1258         "greengrass:Discover"
1259       ],
1260       "Resource": "*"
1261     }
1262   ]
1263 }
1264 {{/code}}
1265
1266 === **Create things** ===
1267
1268 Click “Manage”~-~-->“Things”~-~-->“Create things”~-~-->“Create single thing”
1269
1270 [[image:image-20220709165402-6.png]]
1271
1272 [[image:image-20220709165402-7.png]]
1273
1274 Name the thing~-~-->Click “Next”
1275
1276 [[image:image-20220709165402-8.png]]
1277
1278 Select the way to create certificate
1279
1280 [[image:image-20220709165402-9.png]]
1281
1282 Select policy
1283
1284 [[image:image-20220709165402-10.png]]
1285
1286 [[image:image-20220709165402-11.png]]
1287
1288
1289 === **MQTT.fx tool** ===
1290
1291 Click “View Setting” to get the “Broker Adress”
1292
1293 [[image:image-20220709165402-13.png]]
1294
1295 [[image:image-20220709165402-12.png]]
1296
1297 Create one connection in MQTT.fx tool, set broker port as 8883.
1298
1299 [[image:image-20220709165402-14.png]]
1300
1301 Upload the CA File, Client Certificate File, Client Key File
1302
1303 [[image:image-20220709165402-15.png]]
1304
1305 Publish message to topic “TEST”
1306
1307 [[image:image-20220709165402-17.png]]
1308
1309 Click”Test”~-~-->”MQTT test client”~-~-->”Subscrible to a topic”, to get message publish from MQTT.fx tool.
1310
1311 [[image:image-20220709173500-1.png]]
1312
1313 And we can also send message form AWS platform to MQTT.fx tool.
1314
1315 [[image:image-20220709165402-18.png]]
1316
1317 === **CloudTool** ===
1318
1319 Copy the same setting in MQTT.fx to MQTT configuration
1320
1321 [[image:image-20220709165402-19.png]]
1322
1323 Add a lua script and copy the lua demo into it.
1324
1325 [[image:image-20220709165402-20.png]]
1326
1327 {{info}}
1328 **✎Note:** Before using the following demo script, please make sure the V-Box firmware is newer than 22110701
1329 {{/info}}
1330
1331 {{code language="lua"}}
1332 sprint = print
1333
1334 --Cloud mode interface to obtain the MQTT information configured by the cloud platform: (5 returns, namely the server address, client ID, connection table, last word table, certificate table)
1335
1336 local MQTT_URL, MQTT_CLIENTID, MQTT_CFG, MQTT_LWT, MQTT_CART = mqtt.setup_cfg()
1337
1338 --publish to topics
1339
1340 local pub_RE_TOPIC = string.format('TEST')
1341
1342 --Subscribe topics
1343
1344 local Subscribe_RE_TOPIC1 = string.format('TEST')
1345
1346 --variable
1347
1348 local last_time = 0
1349
1350 --Timing main function
1351
1352 function aws.main()
1353
1354 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " aws.main start")
1355
1356 if g_mq then
1357
1358 if g_mq:isconnected() then
1359
1360 send_Data()
1361
1362 else
1363
1364 if os.time() - last_time > 5 then
1365
1366 last_time = os.time()
1367
1368 mymqtt_connect()
1369
1370 end
1371
1372 end
1373
1374 else
1375
1376 mymqtt_init()
1377
1378 end
1379
1380 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " aws.main end")
1381
1382 end
1383
1384
1385
1386 -- Initialize MQTT
1387
1388 function mymqtt_init()
1389
1390 sprint(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENTID))
1391
1392 g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENTID, 1) -- Create the object and declare it as a global variable, 1 means using the domain to connect
1393
1394 if g_mq then
1395
1396 g_mq:on("message", mymqtt_msg_callback) -- Register to receive message callbacks
1397
1398 sprint("mqtt init success")
1399
1400 else
1401
1402 sprint("mqtt init failed:", err)
1403
1404 end
1405
1406 end
1407
1408 -- Connect to MQTT server
1409
1410 function mymqtt_connect()
1411
1412 sprint("mqtt connecting...")
1413
1414 local stat, err = g_mq:connect(MQTT_CFG,MQTT_LWT, MQTT_CART)
1415
1416 if stat == nil then
1417
1418 sprint("mqtt connect failed:", err)
1419
1420 return
1421
1422 else
1423
1424 sprint("mqtt connected")
1425
1426 end
1427
1428 g_mq:subscribe(Subscribe_RE_TOPIC1, 0)
1429
1430 end
1431
1432 -- Receive MQTT message callback function
1433
1434 function mymqtt_msg_callback(topic, msg)
1435
1436 print("topic:",topic)
1437
1438 print("revdata:",msg)
1439
1440 local revData = json.decode(msg)
1441
1442 print (revData)
1443
1444 if topic == Subscribe_RE_TOPIC1 then --Process topic information subscribed from the cloud
1445
1446 if string.match(topic,Subscribe_RE_TOPIC1) then
1447
1448 --if revData ~= nil then
1449
1450 for k,v in pairs (revData) do
1451
1452 print("printing revdata after kv here")
1453
1454 print (k,v)
1455
1456 end
1457
1458 print ("current state is",fanstate)
1459
1460 --end
1461
1462 end
1463
1464 end
1465
1466 end
1467
1468
1469
1470 --Get real-time data
1471
1472 function getData()
1473
1474 local jdata = {}
1475
1476 local addr = bns_get_alldata()
1477
1478 print(json.encode(addr))
1479
1480 for i,v in pairs(addr) do
1481
1482 if v[2] == 1 then
1483
1484 jdata[v[3]] = v[4]
1485
1486 end
1487
1488 end
1489
1490 return jdata
1491
1492 end
1493
1494 --send data
1495
1496 function send_Data()
1497
1498 local pub_data =
1499 {
1500 123
1501 }
1502
1503 sprint(json.encode(pub_data))
1504
1505 print("..........",pub_RE_TOPIC)
1506
1507 return g_mq:publish(pub_RE_TOPIC, json.encode(pub_data), 0, 0)
1508
1509 end
1510 {{/code}}
1511
1512 Get message in AWS
1513
1514 [[image:image-20220709165402-21.png]]
1515
1516 == **2.7 Mysql** ==
1517
1518 In this demo you can use Mysql import the data to the terminal device through the V-box or save the data to the any Mysql database by the V-box.
1519
1520 === 1.Install Mysql ===
1521
1522 version
1523
1524 (% style="text-align:center" %)
1525 [[image:Mysql的软件版本.png]]
1526
1527 === 2.Install Navicat ===
1528
1529 (% class="wikigeneratedid" %)
1530 version
1531
1532 (% style="text-align:center" %)
1533 [[image:navicat 版本.png]]
1534
1535
1536 Connecting to Mysql with navicat.
1537
1538 (% style="text-align:center" %)
1539 [[image:连接到mysql.png]]
1540
1541 === 3.Create database ===
1542
1543 Character set should be choose utf8mb3/utf8mb4 and Collation choose utf8mb3_danish_ci/utf8mb4_danish_ci.
1544
1545 (% style="text-align:center" %)
1546 [[image:创建数据库.png]]
1547
1548 === 4.Create data table ===
1549
1550 Create a table, enter the fields you need.
1551
1552 (% style="text-align:center" %)
1553 [[image:创建表1.png]]
1554
1555
1556 Save, enter table name.
1557
1558 (% style="text-align:center" %)
1559 [[image:创建表2.png]]
1560
1561 === 5.Input Table Data ===
1562
1563 (% style="text-align:center" %)
1564 [[image:输入或者导入数据.png]]
1565
1566 === 6.Script ===
1567
1568 **luaMySql.init(string sourcename, string username, string password, string host, number port, string character)**
1569
1570 **Function:** Configure database connection parameters
1571
1572 **Parameter:**
1573
1574 sourcename: the name of database
1575
1576 username: the username of the connection
1577
1578 password: the password of the connection
1579
1580 host: the host name of the connection
1581
1582 port: the host port of the connection
1583
1584 character: the character set of the connection
1585
1586 **Return:**
1587
1588 Succeed: string
1589
1590 Failed: multi
1591
1592 **luaMySql.exec(string statement)**
1593
1594 **Function:** Execute the given SQL statement without returning the result set (add, delete, change)
1595
1596 **Parameter:**
1597
1598 statement: the given SQL statement
1599
1600 **Return:**
1601
1602 Succeed: status: returns the number of rows affected by SQL statement execution.
1603
1604 Failed: nil, errorString
1605
1606 **luaMySql.execWithResult(string statement)**
1607
1608 **Function:** Execute the given SQL statement returning the result set (check)
1609
1610 **Parameter:**
1611
1612 statement: the given SQL statement
1613
1614 **Return:**
1615
1616 Succeed: table: returns the result set
1617
1618 Failed: nil, errorString
1619
1620 **For example:**
1621
1622
1623 {{code language="LUA"}}
1624 -- Assuming the "mysqlclient" library is properly installed and available
1625 mysql = require("mysqlclient")
1626
1627 function DataInitRight()
1628 local dbName = "excel"
1629 local user = "root"
1630 local pwd = "XXXXX"
1631 local host = "192.168.39.146"
1632 local port = 3306
1633 local character = "utf8mb3"
1634
1635 mysql.init(dbName, user, pwd, host, port, character)
1636 end
1637
1638 function ExecFunc()
1639 status, errorString = mysql.exec("delete from student where Name = 'XXX';") --Delete statement, column name = table element
1640 if nil == status then
1641 print("ExecFunc() error:", errorString)
1642 return -1
1643 else
1644 print("the number of rows affected by the command:", status)
1645 end
1646 return 0
1647 end
1648
1649
1650 function ExecWithResultFunc()
1651 status, errorString = mysql.execWithResult("select * from student;")
1652 if nil == status then
1653 print("ExecWithResultFunc() error:", errorString)
1654 return -1
1655 else
1656 print("ExecWithResultFunc() success : status type = ", type(status))
1657 print("ExecWithResultFunc() success : status len = ", #status)
1658 local num = #status
1659 local i = 1
1660 if num > 0 then
1661 for i = 1, num, 1 do
1662 local var = string.format("select result[%d] :Num = %d,Name = %s,Age = %d", i, status[i].Num, status[i].Name,status[i].Age) --Iterate through the data in the table, noting whether the elements are strings or numbers
1663 print(var)
1664 end
1665 end
1666 print("---------------")
1667 end
1668 return 0
1669 end
1670
1671 function MySQL.main()
1672 print("script running ...")
1673 DataInitRight()
1674
1675 -- use exec demo
1676 if ExecFunc() < 0 then
1677 return
1678 end
1679
1680 -- use execWithResult demo
1681 if ExecWithResultFunc() < 0 then
1682 return
1683 end
1684
1685 print("script running success")
1686 end
1687 {{/code}}
1688
1689 === 7.Debug ===
1690
1691 (% style="text-align:center" %)
1692 [[image:调试结果.png]]
1693
1694 === 8.Problem ===
1695
1696 During our debugging process it may there are some problems about Mysql, such as
1697
1698 * MySQL: Host  192.168.XXX.XXX  is not allowed to connect.
1699 * MySQL: Host  192.168.XXX.XXX  is blocked because of many connection errors.
1700 * MySQL: SSL connection error: unknown error number.
1701 * (((
1702 1449-The user specified as a definer(‘mysql.infoschema‘@localhost‘) does not exist.
1703 )))
1704
1705 This type of problem has nothing to do with scripts or devices, it is a Mysql configuration issue. If you have any of these problems, please look for a solution online.
1706
1707 {{info}}
1708 ✎Note: If you want to use CMD to access Mysql, you need to add the bin file to the environment variable, please check online for details of the operation.
1709 {{/info}}