Wiki source code of 2 Script

Version 82.1 by Devin Chen on 2025/06/01 10:44

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 {{code language="lua"}}
519 function addr_getquatra(address)
520 local highAddress = addr_newnoaddr(address,2)
521 local low32 = addr_getdword(address)
522 local high32 = addr_getdword(highAddress)
523 --print("the low number is "..low32)
524 --print("the high number is "..high32)
525 local formatVal = string.format("%64.0f",2^32*high32+low32)
526 print("the format value is ".. formatVal)
527 return formatVal
528 end
529 {{/code}}
530
531 = **2 Third part server** =
532
533 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.
534
535 (% class="mark" %)1.Europe server:eu.v-box.net
536
537 (% class="mark" %)2.Asean server:asean.v-box.net
538
539 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
540
541 OpenCloud platform is used in configuring the script.Then V-Box can connect with third part server.
542
543 Both mode can support script  to connect with third part server.the difference:
544
545 (% class="mark" %)1.If you want to store in WECON server ,please use V-NET.
546
547 (% class="mark" %)2.If your server requires SSL certificate to log in,please use OpenCloud.Because only OpenCloud platform can support to upload certificate
548
549 {{info}}
550 **✎Note: **Before program the script of MQTT, please make sure the server(MQTT broker) can be connected through MQTT Client tool.
551 {{/info}}
552
553 (% class="wikigeneratedid" %)
554 Tool link: **[[MQTT.fx>>http://mqttfx.jensd.de/index.php/download]]**
555
556 == **2.1 Test server(General Example)** ==
557
558 The following example is trying to publish to the topic "testtopic/test/no1/7890", and subscribe the topic "testtopic/test/no1/123456".
559
560 And the JSON message is like follows:
561
562 {{code language="JSON"}}
563 {
564 "timestamp": 1631152760,
565 "messageId": 1,
566 "event": "test_data",
567 "mfrs": "HMI/box",
568 "data":
569 {
570 "id" : 1436217747670454274,
571 "waterlevel" : 48,
572 "temperture" : 23
573 }
574 }
575 {{/code}}
576
577 {{code language="lua"}}
578 --MQTT configuration table
579 local MQTT_CFG={}
580 --if there is no need the username and password, please put them as ""
581 MQTT_CFG.username = "weconsupport"
582 MQTT_CFG.password = "123456"
583 MQTT_CFG.netway = 0
584 MQTT_CFG.keepalive = 60
585 MQTT_CFG.cleansession = 1
586 --TCP URL
587 MQTT_URL = "tcp://mq.tongxinmao.com:1883"
588 --Client ID
589 MQTT_CLIENT_ID = "V-BOXH-AG"
590
591 --Generate UUID
592 function uuid()
593 local seed = {'e','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f'}
594 local tb = {}
595 for i=1, 32 do
596 table.insert(tb, seed[math.random(1,16)])
597 end
598 local sid=table.concat(tb)
599 return string.format('%s',
600 string.sub(sid,1,32)
601 )
602 end
603
604
605 --Topic name to subscribed
606 local SUBSCRIBE_TOPIC = 'testtopic/test/no1/123456'
607
608 --Topic name to be published
609 local PUBLISH_TOPIC = 'testtopic/test/no1/7890'
610
611
612 --real time
613 local LAST_TIME = 0
614
615
616 --initialize mqtt
617 function mqtt_init()
618 print(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENT_ID))
619 if g_mq then
620 mqtt.close(g_mq) --Close mqtt object
621 end
622 g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENT_ID) -- create mqtt object,and declare it as a global variable
623 if g_mq then
624 g_mq:on("message", mqtt_msg_callback) -- Register a callback for receiving messages
625 g_mq:on("offline", mqtt_msg_offline) -- Register a callback for offline
626 print("mqtt init success")
627 else
628 print("mqtt init failed:", err)
629 end
630 end
631
632 -- connect to mqtt
633 function mqtt_connect()
634 print("mqtt connecting...")
635 local stat, err = g_mq:connect(MQTT_CFG)
636 if stat == nil then
637 print("mqtt connect failed:", err)
638 return
639 else
640 print("mqtt connected")
641 end
642 g_mq:subscribe(SUBSCRIBE_TOPIC, 0)
643 end
644
645 --Offline callback function
646 function mqtt_msg_offline(cause)
647 print("mqtt offline, cause:", cause)
648 end
649
650 -- Received message callback function
651 function mqtt_msg_callback(topic, msg)
652 print("topic:", topic)
653 print("msg:", msg)
654 local objMsg = json.decode(msg)
655 local water = objMsg.data.waterlevel
656 local temp = objMsg.data.temperature
657 addr_setword("@HDW20",water)
658 addr_setword("@HDW10",temp)
659 end
660
661 --Send data (data upload to platform and encapsulate it with custom functions)
662 function send_data()
663 local pub_data = {
664 timestamp = os.time(),
665 messageId = 1,
666 event = 'test_data',
667 mfrs = 'V-Box',
668 data = {
669 id = uuid(),
670 waterlevel = addr_getword("@HDW10"),
671 temperature = addr_getword("@HDW20")
672 }
673 }
674 return g_mq:publish(PUBLISH_TOPIC, json.encode(pub_data), 0, 0)
675 end
676
677
678 --main function fixed timed execution
679 function MQTT.main()
680 --dosomething
681 print(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " main start")
682 --determine the mqtt object whether exist
683 if g_mq then
684 --determine the mqtt object whether has been connected or not
685 if g_mq:isconnected() then
686 send_data()
687 else
688 --if exceed 5 sec not connect, reconnect once
689 if os.time() - LAST_TIME > 5 then
690 LAST_TIME = os.time()
691 --reinitial the mqtt object
692 mqtt_init()
693 --connect to mqtt or reconnect
694 mqtt_connect()
695 end
696 end
697 else
698 --mqtt object does not exist so create new one
699 mqtt_init()
700 end
701 print(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " main end")
702 end
703 {{/code}}
704
705 == **2.2 Customer server:grouprobotinfo.com** ==
706
707 This demo does not use SSL certification. Script is as below
708
709 Demo1:
710
711 {{code language="lua"}}
712 -- Meta class
713 --main
714 function mq.main()
715 if not mq.m then
716 local err = ""
717
718 mq.m, err = mqtt.create("tcp://grouprobotinfo.com:1883", "ClienID") -- create connection
719 if mq.m then
720 mq.config = {
721 username = "",-- ID
722 password = "",-- password
723 netway = 1, -- Ethernet connection, WIFI=1
724 -- keepalive = 100, -- Optional, set the connection heartbeat interval for 100 seconds.
725 -- cleansession = 0, -- Optional, keep session
726 }
727 mq.m:on("message", function(topic, msg) -- Register for receiving message callbacks
728 local str = string.format("%s:%s", topic, msg)
729 -- print("mqtt msg:", str) -- Print out the received topics and content
730 end)
731 mq.m:on("offline", function (cause) -- Register for lost connection callbacks
732 -- addr_setstring("@xxx", "cause"..(cause or " got nil"))
733 end)
734 mq.m:on("arrived", function() -- Registration for sending messages to callbacks
735 print("msg arrived")
736 end)
737 else
738 print("mqtt create failed:", err) -- Create object failed
739 end
740 else
741 if mq.m:isconnected() then -- If online, post a message
742 local phaseStatus ="unknow"
743 if addr_getbit("@Standby")== 1 then
744 phaseStatus = "Standby"
745 elseif addr_getbit("@Pre-Freeze")==1 then
746 phaseStatus= "Pre-Freeze"
747 elseif addr_getbit("@Prepare")==1 then
748 phaseStatus ="Prepare"
749 elseif addr_getbit("@Primary Dry")==1 then
750 phaseStatus = "Primary dry"
751 elseif addr_getbit("@Secondary Dry")==1 then
752 phaseStatus = "Secondary Dry"
753 end
754 --print(addr_getbit("@Primary Dry"))
755 -------------------------------------------------------------------------------------------------------------------------
756 local activating ="unknow"
757 if addr_getbit("@Compressor")==1 then
758 activating = ",".."Compressor"
759 end
760 if addr_getbit("@Silicone Pump")==1 then
761 activating = activating..",".."Silicone Pump"
762 end
763 if addr_getbit("@Vacuum Pump")==1 then
764 activating = activating..",".."Vacuum Pump"
765 end
766 if addr_getbit("@Root Pump")==1 then
767 activating = activating..",".."Root Pump"
768 end
769 if addr_getbit("@Heater")==1 then
770 activating = activating..",".."Heater"
771 end
772 if addr_getbit("@Valve Silicone")==1 then
773 activating = activating..",".."Valve Silicone"
774 end
775 if addr_getbit("@Valve Ice Condenser")==1 then
776 activating = activating..",".."Valve Ice Condenser"
777 end
778 if addr_getbit("@Valve Vacuum Pump")==1 then
779 activating = activating..",".."Valve Vacuum Pump"
780 end
781 local pr_activating =string.sub(activating,2)
782 -- print(pr_activating)
783 local status_text ="unknow"
784 if addr_getbit("@Status Run")==1 then
785 status_text = "RUNNING"
786 else
787 status_text = "STOP"
788 end
789 -------------------------------------------------------------------------------------------------------------------------
790 local js = {type="status",
791 mc_name ="FD300",
792 status=status_text,
793 elapsed_time={
794 hour=addr_getword("@Elapsed Time (Hour)"),
795 min=addr_getword("@Elapsed Time (Minute)"),
796 sec=addr_getword("@Elapsed Time (Second)")
797 },
798 phase = phaseStatus,
799 step = addr_getword("@Step"),
800 activating_output = pr_activating,
801 sv=addr_getshort("@SV Silicone")/10,
802 pv=addr_getshort("@PV Silicone")/10,
803 product1=addr_getshort("@Product 1")/10,
804
805 product2=addr_getshort("@Product 2")/10,
806 product3=addr_getshort("@Product 3")/10,
807 product4=addr_getshort("@Product 4")/10,
808 ice1=addr_getshort("@Ice condenser 1")/10,
809 ice2=addr_getshort("@Ice condenser 2")/10,
810 vacuum=addr_getfloat("@Vacuum")
811 }
812 local jsAlarm = { HPC = addr_getbit("@B_25395#W0.00"),
813 ODPC = addr_getbit("@B_25395#W0.01"),
814 MTPC=addr_getbit("@B_25395#W0.02"),
815 HTT = addr_getbit("@B_25395#W1.03"),
816 CPC = addr_getbit("@B_25395#W0.08"),
817 CPSP =addr_getbit("@B_25395#W1.00"),
818 CPVP =addr_getbit("@B_25395#W0.10"),
819 CPRP =addr_getbit("@B_25395#W0.11"),
820 HP =addr_getbit("@B_25395#W1.01"),
821 PP= addr_getbit("@B_25395#W1.02"),
822 PO=addr_getbit("@B_25395#W0.07"),
823 FSE=addr_getbit("@B_25395#W2.04"),
824 AVVSVV=addr_getbit("@B_25395#W1.12"),
825 ICHT=addr_getbit("@B_25395#W3.06")
826 }
827 -- ("@B_25395#CIO1.02")
828 mq.m:publish("mqtt-v-box-epsilon-fd300", json.encode(js) , 0, 0)
829 mq.m:publish("mqtt-v-box-epsilon-alarm-fd300", json.encode(jsAlarm) , 0, 0)
830 else
831 local stat, err = mq.m:connect(mq.config) -- connection
832 if stat == nil then --Determine whether to connect
833 print("mqtt connect failed:", err)
834 return -- Connection failed, return directly
835 end
836 mq.m:subscribe("mqtt-v-box-epsilon", 0)-- Subscribe to topics
837
838 end
839 -- mq.m:unsubscribe("stc/test")
840 -- mq.m:disconnect() -- close matt
841 -- mq.m:close() -- close clase
842 end
843 end
844 {{/code}}
845
846 == **2.3 Azure platform** ==
847
848 In this demo,V-Box connects with Azure by SSL certification.
849
850 Video link: [[https:~~/~~/youtu.be/cdI6rIQcpMY?list=PL_Bpnb2RgaksCic9HCcVAZhU9sYwCRKzW>>https://youtu.be/cdI6rIQcpMY?list=PL_Bpnb2RgaksCic9HCcVAZhU9sYwCRKzW]]
851
852 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]]
853
854 Script is as below
855
856 {{code language="lua"}}
857 --https://support.huaweicloud.com/qs-IoT/iot_05_0005.html  mqtt.fx monitor to connect azure iot
858 sprint = print
859
860 --Get custom configuration parameters (vbox custom information)
861 --local CUSTOM = bns_get_config("bind")
862 --local DS_ID = CUSTOM.DSID or "60a71ccbbbe12002c08f3a1a_WECON"
863
864
865
866 --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)
867 local MQTT_URL, MQTT_CLIENTID, MQTT_CFG, MQTT_LWT, MQTT_CART = mqtt.setup_cfg()
868
869 --MQTT_CFG.username = '60a71ccbbbe12002c08f3a1a_WECON'
870 --MQTT_CFG.password='wecon123'
871 --MQTT_CLIENTID = '60a71ccbbbe12002c08f3a1a_WECON_0_0_2021052110usernxame:60a71ccbbbe12002c08f3a1a_WECONpassword:a0a951581855aa8e0262129da6cf1b43f2c0ecfac4fa56117fc5a20c90be169a'
872
873 --publish to topics
874 local pub_RE_TOPIC = string.format('devices/wecon_02/messages/events/')
875 --Subscribe topics
876 local Subscribe_RE_TOPIC1 = string.format('devices/wecon_02/messages/devicebound/#')
877
878 --variable
879 local last_time = 0
880
881
882
883 --Timing main function
884 function Azure.main()
885
886    sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " Azureiot.main start")
887    if g_mq then
888         if g_mq:isconnected() then
889             send_Data()
890         else
891             if os.time() - last_time > 20 then
892                 last_time = os.time()
893                 mymqtt_connect()
894             end
895         end
896     else
897         mymqtt_init()
898     end
899     sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " Azureiot.main end")
900 end
901
902 -- Initialize MQTT
903 function mymqtt_init()
904     sprint(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENTID))
905     g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENTID) -- Create the object and declare it as a global variable
906     if g_mq then
907         g_mq:on("message", mymqtt_msg_callback) -- Register to receive message callbacks
908         sprint("mqtt init success")
909     else
910         sprint("mqtt init failed:", err)
911     end
912 end
913
914 -- Connect to MQTT server
915 function mymqtt_connect()
916     sprint("mqtt connecting...")
917     local stat, err = g_mq:connect(MQTT_CFG,MQTT_LWT, MQTT_CART)
918     if stat == nil then
919         sprint("mqtt connect failed:", err)
920         return
921     else
922         sprint("mqtt connected")
923     end
924     g_mq:subscribe(Subscribe_RE_TOPIC1, 0) 
925 end
926
927 -- Receive MQTT message callback function
928 function mymqtt_msg_callback(topic, msg)
929     print("topic:",topic)
930     print("revdata:",msg)
931    -- local revData = json.decode(msg)
932  --  if topic == Subscribe_RE_TOPIC1 then --Process topic information subscribed from the cloud
933 -- if string.match(topic,Subscribe_RE_TOPIC1) then
934      --   print("topi11:",topic)
935        setValue(revData)
936    -- end
937 end
938
939 --Process the received data
940 --function setValue(revData)
941    -- if revData ~=nil then 
942  --       for i,v in pairs(revData) do
943   --          print("Data received:",i,v)
944   --      end
945    -- end
946 --end
947
948 --Get real-time data
949 function getData()
950     local jdata = {}
951     local addr = bns_get_alldata()
952     print(json.encode(addr))
953     for i,v in pairs(addr) do
954         if v[2] == 1 then
955            jdata[v[3]] = v[4]
956         end
957     end
958     return jdata
959 end 
960
961
962
963 --send data
964 function send_Data()
965     local pub_data = {100
966      --   services={{
967
968             --serviceId ='Temperature',
969            -- properties={
970                -- value = 55
971            -- },
972        -- }}
973 }
974 sprint(json.encode(pub_data))
975 print("..........",pub_RE_TOPIC)
976     return g_mq:publish(pub_RE_TOPIC, json.encode(pub_data), 0, 0)
977 end
978 {{/code}}
979
980 == **2.4 Huawei platform** ==
981
982 {{info}}
983 **✎Note**:**Huawei IOT DA function is only in China area.If you want this function,you need to use chinese mobile to register**
984 {{/info}}
985
986 1.Register a account: [[https:~~/~~/www.huaweicloud.com/intl/en-us/s/JUlPVERNJQ>>https://www.huaweicloud.com/intl/en-us/s/JUlPVERNJQ]]
987
988 2.log in the Huawei IOTDA
989
990 [[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]]
991
992 3.Create product
993
994 (% style="text-align:center" %)
995 [[image:1624433478954-859.png||height="497" width="1100" class="img-thumbnail"]]
996
997 4.Product name,manufacturer,device type and industry,set according to your own needs.
998
999 Protocol: MQTT
1000
1001 Data Type: JSON
1002
1003 After finishing configuration,please click "OK"
1004
1005 (% style="text-align:center" %)
1006 [[image:1624433531968-337.png||height="568" width="700" class="img-thumbnail"]]
1007
1008 5.Device
1009
1010 After product register,continue to configure "individual register".Click "Device"~-~->"individual register"
1011
1012 (% style="text-align:center" %)
1013 [[image:1624434757597-117.png||class="img-thumbnail"]]
1014
1015 **Notes for registering device:**
1016
1017 Product: Previous product registration.
1018
1019 Node ID, Device Name: set according to your own needs.
1020
1021 Secret: need to be configured, will be used when connecting later
1022
1023 After configuration, click OK to generate a device ID and password, which will be used for device access later.
1024
1025 (% style="text-align:center" %)
1026 [[image:1624436421499-613.png||height="499" width="700" class="img-thumbnail"]]
1027
1028 (% style="text-align:center" %)
1029 [[image:1624437798012-126.png||height="366" width="500" class="img-thumbnail"]]
1030
1031 6. Connection authentication (use MQTT.fx tool to access the IoT platform)
1032
1033 (1)Open mqttClientIdGenerator tool Java(TM) Platform SE binary
1034
1035 **[[Download>>https://wecon-disk.oss-ap-southeast-1.aliyuncs.com/Download/WIKI/V-BOX/Demo/Huawei/mqttClientIdGenerator-19.2.0.zip]]**
1036
1037 (% style="text-align:center" %)
1038 [[image:1624437573798-815.png||height="351" width="700" class="img-thumbnail"]]
1039
1040 (2)Fill in the device ID and secret (deviceid and secret generated when registering the device) to generate connection message
1041
1042 Client ID, user name, password
1043
1044 (% style="text-align:center" %)
1045 [[image:1624437756866-251.png||height="405" width="700" class="img-thumbnail"]]
1046
1047 (3) Download certificate file"North-Beijing4"
1048
1049 [[https:~~/~~/support.huaweicloud.com/en-us/devg-iothub/iot_02_1004.html>>https://support.huaweicloud.com/en-us/devg-iothub/iot_02_1004.html]]
1050
1051 (% style="text-align:center" %)
1052 [[image:1624438225398-363.png||height="403" width="800" class="img-thumbnail"]]
1053
1054 (% style="text-align:center" %)
1055 [[image:1624438260025-610.png||height="408" width="700" class="img-thumbnail"]]
1056
1057 7.Run MQTTfx tool to connect with Huawei
1058
1059 Download link: [[http:~~/~~/mqttfx.jensd.de/index.php/download>>url:http://mqttfx.jensd.de/index.php/download]]
1060
1061 (1)Click on the setting ICON
1062
1063 (% style="text-align:center" %)
1064 [[image:1624438821280-974.png||height="198" width="500" class="img-thumbnail"]]
1065
1066 (2)Fill in IIOT MQTT device access address, and configure authentication parameters.
1067 First: It is the server and port connected to Huawei IOT, which can be viewed through the overview of the interface.
1068
1069 (% style="text-align:center" %)
1070 [[image:1624439086268-985.png||class="img-thumbnail"]]
1071
1072 Domain name:iot-mqtts.cn-north-4.myhuaweicloud.com
1073
1074 Port: 8883
1075
1076 Client ID: check step 6
1077
1078 (% style="text-align:center" %)
1079 [[image:1624439672168-492.png||height="458" width="600" class="img-thumbnail"]]
1080
1081 (3)Upload SSL certificate file,check step 6
1082
1083 Select folder java~-~->DigiCertGlobalRootCA.crt.pem and click OK or apply button
1084
1085 (% style="text-align:center" %)
1086 [[image:1624439912938-659.png||height="458" width="600" class="img-thumbnail"]]
1087
1088 (4)Connect and test publish and subscribe
1089
1090 (% style="text-align:center" %)
1091 [[image:1624440014872-688.png||height="232" width="700" class="img-thumbnail"]]
1092
1093 (% style="text-align:center" %)
1094 [[image:1624440026937-386.png||height="215" width="700" class="img-thumbnail"]]
1095
1096 Huawei publish topic format: $oc/devices/{device_id}/sys/properties/report
1097
1098 (% style="text-align:center" %)
1099 [[image:1624440404119-815.png||class="img-thumbnail"]]
1100
1101 Huawei subscribe topic format: **$oc/devices/{device_id}/sys/commands/#**
1102
1103 (% style="text-align:center" %)
1104 [[image:1624447157493-672.png||class="img-thumbnail"]]
1105
1106 (% style="text-align:center" %)
1107 [[image:1624447209982-715.png||class="img-thumbnail"]]
1108
1109 (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:
1110 ①Select the corresponding product from Huawei products to view
1111
1112 (% style="text-align:center" %)
1113 [[image:1624440647663-632.png||class="img-thumbnail"]]
1114
1115 ②Custom model: used to display the service ID name of the configuration report.
1116
1117 (% style="text-align:center" %)
1118 [[image:1624440793982-974.png||height="410" width="700" class="img-thumbnail"]]
1119
1120 (% style="text-align:center" %)
1121 [[image:1624440883015-105.png||height="370" width="600" class="img-thumbnail"]]
1122
1123 ③Add property, ID of monitoring point, and data format:
1124
1125 (% style="text-align:center" %)
1126 [[image:1624441052296-108.png||height="477" width="600" class="img-thumbnail"]]
1127
1128 ④After the configuration is complete, check the received data on the device
1129
1130 (% style="text-align:center" %)
1131 [[image:1624441186851-536.png||height="434" width="700" class="img-thumbnail"]]
1132
1133 === Huawei by SSL certification. ===
1134
1135 1.Create a project access for Huawei IOT
1136
1137 2.configure MQTT configuration
1138
1139 (% style="text-align:center" %)
1140 [[image:1624506363847-661.png||height="507" width="1000" class="img-thumbnail"]]
1141
1142 3.Create a script with the demo as below.
1143
1144 Script is as below
1145
1146 (% class="box infomessage" %)
1147 (((
1148 (% class="box infomessage" %)
1149 (((
1150 ~-~- mqtt.fx simulated access to Huawei Cloud IoT platform refer to 2.4
1151 sprint = print
1152
1153 ~-~-Get custom configuration parameters (gateway customization information)
1154 local CUSTOM = bns_get_config("bind")
1155 local DS_ID = CUSTOM.DSID or "5dfa0700df1ae506179afb9c_wecon"
1156
1157
1158 ~-~-OpenCloud mode interface, obtain MQTT information configured on cloud platform: (5 returned, respectively server address, client ID, connection table, last word table, certificate table)
1159 local MQTT_URL, MQTT_CLIENTID, MQTT_CFG, MQTT_LWT, MQTT_CART = mqtt.setup_cfg()
1160
1161 MQTT_CFG.username =DS_ID
1162 MQTT_CFG.password='d030d92338fcc18cd10fabb3003a4a0f6620fa6822cd3c23b1d9bc790200c6e7'
1163 MQTT_CLIENTID = '5dfa0700df1ae506179afb9c_wecon_0_0_2019121819'
1164
1165 ~-~-publish topic format:$oc/devices/{device id}/sys/properties/report
1166
1167 local pub_RE_TOPIC = string.format('$oc/devices/60a71ccbbbe12002c08f3a1a_WECON/sys/properties/report')
1168
1169 ~-~-variate
1170 local last_time = 0
1171
1172
1173 ~-~-Timing principal function
1174 function hwyiot.main()
1175
1176 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " hwyiot.main start")
1177 if g_mq then
1178 if g_mq:isconnected() then
1179 send_Data()
1180 else
1181 if os.time() - last_time > 20 then
1182 last_time = os.time()
1183 mymqtt_connect()
1184 end
1185 end
1186 else
1187 mymqtt_init()
1188 end
1189 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " hwyiot.main end")
1190 end
1191
1192 ~-~- initializationMQTT
1193 function mymqtt_init()
1194 sprint(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENTID))
1195 g_mq, err = mqtt.create(MQTT_URL, MQTT_CLIENTID) ~-~- Create the object and declare it as a global variable
1196 if g_mq then
1197 g_mq:on("message", mymqtt_msg_callback) ~-~- Register to receive message callbacks
1198 sprint("mqtt init success")
1199 else
1200 sprint("mqtt init failed:", err)
1201 end
1202 end
1203
1204 ~-~- Connect to the MQTT server
1205 function mymqtt_connect()
1206 sprint("mqtt connecting...")
1207 local stat, err = g_mq:connect(MQTT_CFG,MQTT_LWT, MQTT_CART)
1208 if stat == nil then
1209 sprint("mqtt connect failed:", err)
1210 return
1211 else
1212 sprint("mqtt connected")
1213 end
1214
1215 ~-~-subscribe topic format:$oc/devices/{device_id}/sys/commands/#
1216
1217 g_mq:subscribe('$oc/devices/60a71ccbbbe12002c08f3a1a_WECON/sys/commands/#', 0) 
1218 end
1219
1220 ~-~- Receive the message callback function
1221 function mymqtt_msg_callback(topic, msg)
1222 sprint("recv data!")
1223 sprint("topic:msg", topic,msg)
1224 print(msg)
1225 local revData = json.decode(msg)
1226 \\end
1227
1228 ~-~-Send data
1229 function send_Data()
1230 local pub_data = {
1231 msgType = 'deviceReq',
1232 data = ~{~{
1233 serviceId ='Battery',
1234 serviceData={
1235 batteryLevel = 55
1236 }
1237 }}
1238 }
1239 return g_mq:publish(pub_RE_TOPIC, json.encode(pub_data), 0, 0)
1240 end
1241 )))
1242 )))
1243
1244 4.Download project access into V-Box to test in debug page
1245
1246 (% style="text-align:center" %)
1247 [[image:1624506710354-406.png||height="658" width="1000" class="img-thumbnail"]]
1248
1249 (% style="text-align:center" %)
1250 [[image:1624506666650-161.png||height="547" width="1000" class="img-thumbnail"]]
1251
1252 == **2.6 AWS platform** ==
1253
1254 === **Log in AWS** ===
1255
1256 Login aws account and click“Connect an IoT device”
1257
1258 [[image:image-20220709165402-1.png]]
1259
1260 [[image:image-20220709165402-2.png]]
1261
1262
1263 === **Create policy** ===
1264
1265 Click “Secure”~-~-->“Policies”~-~-->“Create policy”~-~-->Click “Create”
1266
1267 [[image:image-20220709165402-3.png]]
1268
1269 Name the policy~-~-->Click “JSON”~-~-->Copy the following content~-~-->Click “Create”
1270
1271 [[image:image-20220709165402-5.png]]
1272
1273 [[image:image-20220709165402-4.png]]
1274
1275 {{code language="java"}}
1276 {
1277   "Version": "2012-10-17",
1278   "Statement": [
1279     {
1280       "Effect": "Allow",
1281       "Action": [
1282         "iot:Connect",
1283         "iot:Publish",
1284         "iot:Subscribe",
1285         "iot:Receive",
1286         "greengrass:Discover"
1287       ],
1288       "Resource": "*"
1289     }
1290   ]
1291 }
1292 {{/code}}
1293
1294 === **Create things** ===
1295
1296 Click “Manage”~-~-->“Things”~-~-->“Create things”~-~-->“Create single thing”
1297
1298 [[image:image-20220709165402-6.png]]
1299
1300 [[image:image-20220709165402-7.png]]
1301
1302 Name the thing~-~-->Click “Next”
1303
1304 [[image:image-20220709165402-8.png]]
1305
1306 Select the way to create certificate
1307
1308 [[image:image-20220709165402-9.png]]
1309
1310 Select policy
1311
1312 [[image:image-20220709165402-10.png]]
1313
1314 [[image:image-20220709165402-11.png]]
1315
1316
1317 === **MQTT.fx tool** ===
1318
1319 Click “View Setting” to get the “Broker Adress”
1320
1321 [[image:image-20220709165402-13.png]]
1322
1323 [[image:image-20220709165402-12.png]]
1324
1325 Create one connection in MQTT.fx tool, set broker port as 8883.
1326
1327 [[image:image-20220709165402-14.png]]
1328
1329 Upload the CA File, Client Certificate File, Client Key File
1330
1331 [[image:image-20220709165402-15.png]]
1332
1333 Publish message to topic “TEST”
1334
1335 [[image:image-20220709165402-17.png]]
1336
1337 Click”Test”~-~-->”MQTT test client”~-~-->”Subscrible to a topic”, to get message publish from MQTT.fx tool.
1338
1339 [[image:image-20220709173500-1.png]]
1340
1341 And we can also send message form AWS platform to MQTT.fx tool.
1342
1343 [[image:image-20220709165402-18.png]]
1344
1345 === **CloudTool** ===
1346
1347 Copy the same setting in MQTT.fx to MQTT configuration
1348
1349 [[image:image-20220709165402-19.png]]
1350
1351 Add a lua script and copy the lua demo into it.
1352
1353 [[image:image-20220709165402-20.png]]
1354
1355 {{info}}
1356 **✎Note:** Before using the following demo script, please make sure the V-Box firmware is newer than 22110701
1357 {{/info}}
1358
1359 {{code language="lua"}}
1360 sprint = print
1361
1362 --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)
1363
1364 local MQTT_URL, MQTT_CLIENTID, MQTT_CFG, MQTT_LWT, MQTT_CART = mqtt.setup_cfg()
1365
1366 --publish to topics
1367
1368 local pub_RE_TOPIC = string.format('TEST')
1369
1370 --Subscribe topics
1371
1372 local Subscribe_RE_TOPIC1 = string.format('TEST')
1373
1374 --variable
1375
1376 local last_time = 0
1377
1378 --Timing main function
1379
1380 function aws.main()
1381
1382 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " aws.main start")
1383
1384 if g_mq then
1385
1386 if g_mq:isconnected() then
1387
1388 send_Data()
1389
1390 else
1391
1392 if os.time() - last_time > 5 then
1393
1394 last_time = os.time()
1395
1396 mymqtt_connect()
1397
1398 end
1399
1400 end
1401
1402 else
1403
1404 mymqtt_init()
1405
1406 end
1407
1408 sprint(os.date("%Y-%m-%d %H:%M %S", os.time()) .. " aws.main end")
1409
1410 end
1411
1412
1413
1414 -- Initialize MQTT
1415
1416 function mymqtt_init()
1417
1418 sprint(string.format("mqtt init mqtt_url:%s mqtt_clientid:%s", MQTT_URL, MQTT_CLIENTID))
1419
1420 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
1421
1422 if g_mq then
1423
1424 g_mq:on("message", mymqtt_msg_callback) -- Register to receive message callbacks
1425
1426 sprint("mqtt init success")
1427
1428 else
1429
1430 sprint("mqtt init failed:", err)
1431
1432 end
1433
1434 end
1435
1436 -- Connect to MQTT server
1437
1438 function mymqtt_connect()
1439
1440 sprint("mqtt connecting...")
1441
1442 local stat, err = g_mq:connect(MQTT_CFG,MQTT_LWT, MQTT_CART)
1443
1444 if stat == nil then
1445
1446 sprint("mqtt connect failed:", err)
1447
1448 return
1449
1450 else
1451
1452 sprint("mqtt connected")
1453
1454 end
1455
1456 g_mq:subscribe(Subscribe_RE_TOPIC1, 0)
1457
1458 end
1459
1460 -- Receive MQTT message callback function
1461
1462 function mymqtt_msg_callback(topic, msg)
1463
1464 print("topic:",topic)
1465
1466 print("revdata:",msg)
1467
1468 local revData = json.decode(msg)
1469
1470 print (revData)
1471
1472 if topic == Subscribe_RE_TOPIC1 then --Process topic information subscribed from the cloud
1473
1474 if string.match(topic,Subscribe_RE_TOPIC1) then
1475
1476 --if revData ~= nil then
1477
1478 for k,v in pairs (revData) do
1479
1480 print("printing revdata after kv here")
1481
1482 print (k,v)
1483
1484 end
1485
1486 print ("current state is",fanstate)
1487
1488 --end
1489
1490 end
1491
1492 end
1493
1494 end
1495
1496
1497
1498 --Get real-time data
1499
1500 function getData()
1501
1502 local jdata = {}
1503
1504 local addr = bns_get_alldata()
1505
1506 print(json.encode(addr))
1507
1508 for i,v in pairs(addr) do
1509
1510 if v[2] == 1 then
1511
1512 jdata[v[3]] = v[4]
1513
1514 end
1515
1516 end
1517
1518 return jdata
1519
1520 end
1521
1522 --send data
1523
1524 function send_Data()
1525
1526 local pub_data =
1527 {
1528 123
1529 }
1530
1531 sprint(json.encode(pub_data))
1532
1533 print("..........",pub_RE_TOPIC)
1534
1535 return g_mq:publish(pub_RE_TOPIC, json.encode(pub_data), 0, 0)
1536
1537 end
1538 {{/code}}
1539
1540 Get message in AWS
1541
1542 [[image:image-20220709165402-21.png]]
1543
1544 == **2.7 Mysql** ==
1545
1546 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.
1547
1548 (% class="wikigeneratedid" id="H1.InstallMysql" %)
1549 **1.Install Mysql**
1550
1551 version
1552
1553 (% style="text-align:center" %)
1554 [[image:Mysql的软件版本.png]]
1555
1556 (% class="wikigeneratedid" id="H2.InstallNavicat" %)
1557 **2.Install Navicat**
1558
1559 (% class="wikigeneratedid" %)
1560 version
1561
1562 (% style="text-align:center" %)
1563 [[image:navicat 版本.png]]
1564
1565
1566 Connecting to Mysql with navicat.
1567
1568 (% style="text-align:center" %)
1569 [[image:连接到mysql.png]]
1570
1571 (% class="wikigeneratedid" id="H3.Createdatabase" %)
1572 **3.Create database**
1573
1574 Character set should be choose utf8mb3/utf8mb4 and Collation choose utf8mb3_danish_ci/utf8mb4_danish_ci.
1575
1576 (% style="text-align:center" %)
1577 [[image:创建数据库.png]]
1578
1579 (% class="wikigeneratedid" id="H4.Createdatatable" %)
1580 **4.Create data table**
1581
1582 Create a table, enter the fields you need.
1583
1584 (% style="text-align:center" %)
1585 [[image:创建表1.png]]
1586
1587
1588 Save, enter table name.
1589
1590 (% style="text-align:center" %)
1591 [[image:创建表2.png]]
1592
1593 (% class="wikigeneratedid" id="H5.InputTableData" %)
1594 **5.Input Table Data**
1595
1596 (% style="text-align:center" %)
1597 [[image:输入或者导入数据.png]]
1598
1599 (% class="wikigeneratedid" id="H6.Script" %)
1600 **6.Script**
1601
1602 **luaMySql.init(string sourcename, string username, string password, string host, number port, string character)**
1603
1604 **Function:** Configure database connection parameters
1605
1606 **Parameter:**
1607
1608 sourcename: the name of database
1609
1610 username: the username of the connection
1611
1612 password: the password of the connection
1613
1614 host: the host name of the connection
1615
1616 port: the host port of the connection
1617
1618 character: the character set of the connection
1619
1620 **Return:**
1621
1622 Succeed: string
1623
1624 Failed: multi
1625
1626 **luaMySql.exec(string statement)**
1627
1628 **Function:** Execute the given SQL statement without returning the result set (add, delete, change)
1629
1630 **Parameter:**
1631
1632 statement: the given SQL statement
1633
1634 **Return:**
1635
1636 Succeed: status: returns the number of rows affected by SQL statement execution.
1637
1638 Failed: nil, errorString
1639
1640 **luaMySql.execWithResult(string statement)**
1641
1642 **Function:** Execute the given SQL statement returning the result set (check)
1643
1644 **Parameter:**
1645
1646 statement: the given SQL statement
1647
1648 **Return:**
1649
1650 Succeed: table: returns the result set
1651
1652 Failed: nil, errorString
1653
1654 **For example:**
1655
1656
1657 {{code language="LUA"}}
1658 -- Assuming the "mysqlclient" library is properly installed and available
1659 mysql = require("mysqlclient")
1660
1661 function DataInitRight()
1662 local dbName = "excel"
1663 local user = "root"
1664 local pwd = "XXXXX"
1665 local host = "192.168.39.146"
1666 local port = 3306
1667 local character = "utf8mb3"
1668
1669 mysql.init(dbName, user, pwd, host, port, character)
1670 end
1671
1672 function ExecFunc()
1673 status, errorString = mysql.exec("delete from student where Name = 'XXX';") --Delete statement, column name = table element
1674 if nil == status then
1675 print("ExecFunc() error:", errorString)
1676 return -1
1677 else
1678 print("the number of rows affected by the command:", status)
1679 end
1680 return 0
1681 end
1682
1683
1684 function ExecWithResultFunc()
1685 status, errorString = mysql.execWithResult("select * from student;")
1686 if nil == status then
1687 print("ExecWithResultFunc() error:", errorString)
1688 return -1
1689 else
1690 print("ExecWithResultFunc() success : status type = ", type(status))
1691 print("ExecWithResultFunc() success : status len = ", #status)
1692 local num = #status
1693 local i = 1
1694 if num > 0 then
1695 for i = 1, num, 1 do
1696 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
1697 print(var)
1698 end
1699 end
1700 print("---------------")
1701 end
1702 return 0
1703 end
1704
1705 function MySQL.main()
1706 print("script running ...")
1707 DataInitRight()
1708
1709 -- use exec demo
1710 if ExecFunc() < 0 then
1711 return
1712 end
1713
1714 -- use execWithResult demo
1715 if ExecWithResultFunc() < 0 then
1716 return
1717 end
1718
1719 print("script running success")
1720 end
1721 {{/code}}
1722
1723 (% class="wikigeneratedid" id="H7.Debug" %)
1724 **7.Debug**
1725
1726 (% style="text-align:center" %)
1727 [[image:调试结果.png]]
1728
1729 (% class="wikigeneratedid" id="H8.Problem" %)
1730 8.Problem
1731
1732 During our debugging process it may there are some problems about Mysql, such as
1733
1734 * MySQL: Host  192.168.XXX.XXX  is not allowed to connect.
1735 * MySQL: Host  192.168.XXX.XXX  is blocked because of many connection errors.
1736 * MySQL: SSL connection error: unknown error number.
1737 * (((
1738 1449-The user specified as a definer(‘mysql.infoschema‘@localhost‘) does not exist.
1739 )))
1740
1741 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.
1742
1743 {{info}}
1744 ✎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.
1745 {{/info}}