Wiki source code of 2 Script

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