该项目试图对洛拉传输技术进行小型测试,以收集CTIC基金会可以使用的信息。信息将从最终设备(节点或客户)发送,此信息将由网关设备收集,然后将其转发到服务器以存储它。
洛拉(Lora)是一种使用Semtech申请专利的射频调制类型的无线技术(例如WiFi,蓝牙,LTE,Sigfox或Zigbee)。
目前,该技术是由联盟洛拉(Lora)管理的,该联盟证明了所有试图使用该技术的硬件制造商。
洛拉(Lora)对干扰具有很高的耐受性,对接收数据(-168DB)的敏感性很高,消耗量非常低(该设备可以持续十年,单个电池可以持续十年),范围为10至20 km (取决于直接视觉或土地拓扑是否可用)。另一方面,我们发现数据传输非常低(高达255个字节)。
所有这些使该转移技术对于不需要或无法访问电流的大距离或物联网网络有用。
洛拉(Lora)以自由频率工作(欧洲为868MHz ,在美国为916MHz,例如在亚洲为433MHz),这些频率为433MHz),他们收集了不需要的不需要的电力网络供应商和电信提供商(我们使用放射性频率),因此可以将信息发出和发送信息。
我们可以通过Loremac(也通过Lora知道)或Lorawan与设备通信。
Loramac :用来互相通信两个设备,并指向点,一个人发送信息,另一个则收集信息(反之亦然)。
Lorawan :用于传达设备网络。在这种方法中,出现网关的图(收集一个或多个设备的信息并将其转发到服务器的设备)。在Lorawan中,必须对信息进行过滤,以了解您应该收听网关的设备以及要忽略的设备,但这将在以后看到。这种方法使用恒星拓扑。
另一方面,在洛万(Lorawan)中,还有三种类型的最终设备或节点:
*在示例中仅支持A类和B节点(由所使用的库支持),但仅实现类型A。
如果使用欧洲的自由频带(868MHz),则必须考虑一些限制:
在每个频带中,有几个通道或子频带,就欧洲(868MHz)而言,我们发现10个从0到9的通道。但是,例如,在美国(915MHz)中,我们可以找到多达64个。
通过一个或另一个渠道发送信息是库通常促进使用的任务。
在某些最终问题中,可以修改Datartate或设备播放器。
Datartate和expreadFactor与:0的数据指示为SF12和5的Datartate指示SF7。所有的频率为125kHz,具有以下例外:6的数据量表表示为250kHz的SF7。
两个设备(一个用于节点的设备,另一个用于网关,也必须具有WiFi连接性),在TTS( Things Network Network )或Chirpstack中有一个关联的帐户(能够在家中使用自己的服务器)。在此示例中,使用Arduino节点和Pycom Gateway的Loremac和Lorawan示例。
首先,克隆存储库是足够的:
git clone https://github.com/Javieral95/Getting_Started_With_LoRa.git
然后将相关项目上传到设备
为什么要有两个IDS?简单的Pymakr扩展几乎无法在Visual Studio代码中起作用。随意使用最舒适的工作空间。
两种设备都有与它们连接的Antera Lora。
注意:Arduinomkr1300的代码(诸如Lora End-Device的使用更多)和使用Pysense或Pytrack作为端evex的代码也包括在存储库中。

Loramac示例(在同型文件夹中找到)是使用Arduino最终设备和PYCOM Gateway的功能。
该节点仅发送硬码信息,而网关仅连接到Lora和Wifi,接收PYCOM信息并打印读取的数据(尽管它已经实现了将数据发送到网络的功能)。
使用网络服务器的使用。
要了解更多信息,您可以访问文件夹/Loramac 。
为了使用这些示例(使用Arduino最终设备和PYCOM网关的功能性制作)需要服务器来可视化数据。在此示例中,已经解决了Things Network和Chirpstack (以前称为Loraserver)的使用。
要了解更多信息,您可以访问文件夹/Lorawan ,然后继续咨询此文档。
Lorawan中有两种类型的身份验证:
*目前只有OTAA。
如前所述,我们将需要一台服务器。在此示例中,已经使用了Things Network的免费版本,PYCOM拥有的CHIRPSTACK服务器以及在家中部署的另一个。
它是最可靠,最安全,有影响的替代方案。但是,一切都表明它将停止打开(每个应用程序的限制为50个节点)。
创建应用程序很简单,访问菜单,然后单击 +按钮。一旦我们指出了应用程序的名称,唯一的ID和描述。
创建应用程序时,我们可以添加最终设备(节点)单击 +按钮。
网关是负责发送来自几个最终设备(属于多个应用程序)并将其转发到服务器的设备。创建网关也很简单,单击 +按钮并填写表格,请注意以下概念:
为了能够读取节点已发送到服务器的数据,有必要解码有效载荷,在TTN的情况下,我们将为每个设备(在有效载荷格式化)选项卡中执行此操作。我们选择formatter如何键入JavaScript选项和:
function Decoder(bytes, port) {
// Decode plain text; for testing only
return {
myTestValue: String.fromCharCode.apply(null, bytes)
};
}
arduino_ttn_decoder.js 已经确定,网络事物的所有十六进制地址都在市长中,在对设备进行编程但错误时遭受了错误时并不重要。
这是开源替代方案,它仍在开发中,其文档并不是那么好。但是,它有效并允许启动服务器。
PYCOM提供了Chirpstack服务器来连接您的网关设备。
该应用程序类似于事物网络部分中的详细信息。
您必须转到服务器部分的设备填充,一旦IT访问该配置文件(在这种情况下为OTAA)并修改版本:
要创建网关,请访问同名,然后单击 +按钮。填写表格,特别注意网关ID字段(在识别网关的十六进制中的64位),您可以使Chirpstack为您生成它们,但通常使用设备的MAC(如果您在网关上不知道它的部分,则可以详细说明它的详细信息)。
您可以留下其余的默认值。
为了读取节点已发送到服务器的数据,有必要解码有效载荷,在Chirpstack的情况下,我们将为每个设备配置文件执行此操作,在设备Propiles_中,我们访问了感兴趣的配置文件(在这种情况下为OTAA),我们访问CODECEC TAB:
我们在自定义DECIPT编解码器函数中选择:
function Decode(fPort, bytes) {
var tempObj = new Object();
tempObj.data=bytes;
tempObj.decodedData = String.fromCharCode.apply(null, bytes);
tempObj.message = "Informacion recibida del nodo";
return tempObj;
}
arduino_chirpstark_decoder.js 可以确定,Chirpstack的所有十六进制地址都在负曲线中,在编程设备但错误中遭受了错误时并不重要。
Chirpstack提供了一种OpenSource替代方案,可以在Lorawan启动我们自己的专用服务器,并允许我们以简单的方式和通过容器进行操作。
这就是为什么允许此操作的Chirpstack(Brocar)创始人拥有的另一个存储库:Chirpstack-Docker已在当前的存储库中克隆。我们在chirpstack-docker文件夹中找到它。
Chirpstack在其体系结构中具有各种组件,可以使服务能够运行,它们是以下内容:

以容器形式显示服务器的方法使我们能够抽象许多体系结构组件,但是它们已详细介绍:
在部署之前,必须在配置板中存储的配置文件中配置所有必要的参数。
您可以咨询以下官方文件:
注意:配置文件对空白空间或空线很敏感(它们已经在蚊帐中找到),检查文件并消除以避免错误。
如前所述,容器中的部署很简单,位于chirpstack-docker目录中。
一旦已经配置了必要的内容,就足以将其放置在Chirpstack-Docker目录中并启动:
docker-compose up
使用默认配置,您可以在本地方向访问服务器:8080 。用户将是管理员和管理密码。
让我们开始添加基本配置:
配置服务器后,我们将必须注册我们的网关并创建应用程序以记录我们的最终设备。此过程类似于本文档的上一节中所述的过程:Chirpstack(Lora Server)。
此外,必须指示收到的信息的解码和编码的函数,也可以在上一节中说明。
用于启动网关的代码在下面详细介绍了PYCOM(带Pytrack的Fipy)。该代码位于Lorawan/Lorapycomgateway 。
已经使用了Nanogateway PY库,该库可以在几分钟内启动网关。
Nano-Gateway将PYCOM设备转换为一个仅听到频带(单字节)通道的简单网关,以聆听PYCOM中更多的频段,因此可能需要商业网关。
在配置文件中,自定义网关所需的一切:
WIFI_MAC = ubinascii.hexlify(machine.unique_id()) #.toUpper() para TTS
SERVER = 'loraserver.pycom.io' #(or url of your server)
GATEWAY_ID = WIFI_MAC[:6] + "ffff" + WIFI_MAC[6:12] #Minusculas: Chirpstack
NTP = "es.pool.ntp.org"
NTP_PERIOD_S = 3600
#WiFi settings (change it)
WLAN_SSID = "MyAwesomeWiFi" #"pycom-wifi"
WLAN_PASS = "CheckOutThisGoodPassword" #"securepassword"
WLAN_TIMEOUT_MS = 180000
### LoRaWAN for EU868 ###
LORA_FREQUENCY = 868500000
#Spreading Factor: (Higher value in SF=More distance but less speed transmision)
LORA_GW_DR = "SF7BW125" # DR_5,Can change in range: SF7 to SF15 (SF7B250 also exists)
LORA_NODE_DR = 5 #5 (6 uses 250Khz) for SF7, 4 for SF6.. all using 125Khz
###
def get_gateway_id():
print("Your gateway_id is: {}".format(GATEWAY_ID)) #The gateway is b'THIS_STRING'
return GATEWAY_ID
注意:如果您将网关连接到没有Internet连接的本地网络,则在同步手表时会返回错误。您可以在nanogateway.py文件的启动(self)函数中对以下代码的以下代码的评论中脱离步骤,如以下示例所示:
# get a time sync
self._log('Syncing time with {} ...', self.ntp_server)
#self.rtc.ntp_sync(self.ntp_server, update_period=self.ntp_period)
#while not self.rtc.synced():
# utime.sleep_ms(50)
self._log("RTC NTP sync complete")
不使用几个主要文件功能,只需要如下启动网关,并且已经在工作。
def init_loraWAN_gateway():
print("Initializing LoRaWAN nano Gateway")
nanogw = NanoGateway(
id=config.GATEWAY_ID,
frequency=config.LORA_FREQUENCY,
datarate=config.LORA_GW_DR,
ssid=config.WLAN_SSID,
password=config.WLAN_PASS,
server=config.SERVER,
port=config.PORT,
ntp_server=config.NTP,
ntp_period=config.NTP_PERIOD_S
)
print("Ok! Now you have a LoRaWAN Gateway! Lets start it, wait . . .")
pycom.rgbled(0xAA0000)
nanogw.start()
nanogw._log('. . . Yeah! Nano gateway is connected and running, enjoy the log:')
pycom.rgbled(0x000000)
PYCOM将保持红灯直到设法连接,一旦倾听设备的设备,将闪烁其绿色LED。
详细详细介绍了使用Arduino操作类节点A。
理论使用频带中所有可用的通道,后来只能看到一种力量(不建议)。
使用McCi Arduino Lorawan库,可让您抽象Lora通信的许多方面。它已由Platformio Library Manager安装。
基本上,Arduino客户端使用的代码是库的ttn-otaa.ino示例中找到的代码,除了进行了一些修改。
配置是在两个不同的文件中进行的:
如上所述,所有与Lorawan相关的配置均在lorawan.cpp文件中指示。在文档的开头,详细说明了数据应显示: app_eui , dev_eui和app_key (目光调整下面指示的格式)。
然后是Chirpstack中的示例:
static const u1_t PROGMEM APPEUI[8] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
static const u1_t PROGMEM DEVEUI[8] = {0x7b, 0x6b, 0xff, 0x2c, 0x7b, 0x2c, 0x19, 0x5a};
static const u1_t PROGMEM APPKEY[16] = {0xbd, 0x21, 0x5a, 0x82, 0xb2, 0xf7, 0x92, 0xf3, 0xc7, 0xcb, 0xb2, 0x88, 0xc7, 0x55, 0x33, 0xe7};
在整个密钥配置下,在loraWan.cpp文件中,我们可以选择是从温度和湿度传感器中发送平面文本还是数据。解释所需的选项:
/******* Send data config *******/
// Use this to send a Hello world in plain text
// static uint8_t mydata[] = "Hello World!";
// Use this to send sensor data
const int neededBytes = 4; // 4 bytes: 2 for temperature and 2 for humidity, can change this value
static byte mydata[neededBytes];
static LoraEncoder encoder(mydata);
根据发送的信息,必须使用发送或其他功能,如事物网络和Chirpstack的各个部分所示。
如前所述,纳米门户PYCOM板只能在Arduino Final设备能够在所有乐队频道上广播(例如,在欧洲乐队中有10个频道)时能够在通道上读取。尽管不建议使用(可能会违反1%的规则)仅由于开发和测试问题而仅使用频道和频率。
为此,有必要修改库代码,更具体地说是lorabase_eu868.h (在使用欧洲频率的情况下),并强迫所需的频率如下(观察所有值都被硬编码以指示频率868.mhz):
enum {
EU868_F1 = 868500000, // g1 SF7-12
EU868_F2 = 868500000, // g1 SF7-12 FSK SF7/250
EU868_F3 = 868500000, // g1 SF7-12
EU868_F4 = 868500000, // g2 SF7-12
EU868_F5 = 868500000, // g2 SF7-12
EU868_F6 = 868500000, // g3 SF7-12
EU868_J4 = 868500000, // g2 SF7-12 used during join
EU868_J5 = 868500000, // g2 SF7-12 ditto
EU868_J6 = 868500000, // g2 SF7-12 ditto
};
enum {
EU868_FREQ_MIN = 868500000,
EU868_FREQ_MAX = 868500000
};
还应在Lora( Lorawan_startjob()函数:
// Define the single channel and data rate (SF) to use
void disableChannels(int selectedChannel, int dr)
{
// Disable all channels, except for the one defined above.
// ONLY FOR TESTING AND DEVELOPING!
for (int i = 0; i < 9; i++)
{ // For EU; for US use i<71
if (i != selectedChannel)
{
LMIC_disableChannel(i);
}
}
// Set data rate (SF) and transmit power for uplink
LMIC_setDrTxpow(dr, 14);
}
频道和要配置的供应的渠道位于文件的开头(默认情况下:频道0和值为5的传播因子7的所需数据):
/******* Channel config (only change if you want to uses a single channel) *******/
const int channel = 0; // Use if you want to use only one Band's Channel.
const int dr = DR_SF7; // Use if you want to use a specific datarate (The spreading factor mark the dr's value).
尽管仍然有一些网关未收到的一些,但这将大大减少包装的损失。
只需将项目复制到您的Arduino板上即可。
书店按事件进行工作,在这种情况下,最重要的是身份验证(完成时,您将在控制台中看到钥匙)和数据运输。
发送数据的事件将在lorawan.cpp文件的void OneVent函数(EV_T EV)中进行EV_TXCOMPLETE ,观察到该事件包括“ RX窗口”,此时设备会在设备上听。
case EV_TXCOMPLETE:
Serial.println(F("EV_TXCOMPLETE (includes waiting for RX windows)"));
if (LMIC.txrxFlags & TXRX_ACK)
Serial.println(F("Received ack"));
if (LMIC.dataLen)
{
Serial.print(F("Received "));
Serial.print(LMIC.dataLen);
Serial.println(F(" bytes of payload"));
}
// Schedule next transmission
os_setTimedCallback(&sendjob, os_getTime() + sec2osticks(TX_INTERVAL), do_send);
break;
该函数在同一文件中,将详细介绍发送的数据是do_send (如果要发送平面文本,请评论或decoments编码信息的行):
void do_send(osjob_t *j)
{
// Check if there is not a current TX/RX job running
if (LMIC.opmode & OP_TXRXPEND)
{
Serial.println(F("OP_TXRXPEND, not sending"));
}
else
{
// Leer datos de sensor y codificar (Libreria LoRa_Serialization).
am2315_readedData data = readAM2315Data();
encoder.writeTemperature(data.temp);
encoder.writeHumidity(data.hum);
// Comentar las dos lineas "encoder" para enviar texto plano
// Send packet
LMIC_setTxData2(1, mydata, sizeof(mydata), 0);
if (isLoopRunning)
{
freq = String(LMIC.freq);
Serial.println("-->Packet queued using freq = " + freq);
// Prepare upstream data transmission at the next possible time.
printSensorInfoInDisplay(data.temp, data.hum);
printLoraSentInDisplay(freq);
}
}
// Next TX is scheduled after TX_COMPLETE event.
}
注意:遇到了一个错误,该错误阻止了节点接收后套件,因此无法对服务器前面的设备进行身份验证。已在客户设置()中添加了它(更具体地说,在lorawan_startjob() lorawan.cpp文件的函数中)以下代码行将最大时钟错误增加10%:
LMIC_setClockError(MAX_CLOCK_ERROR * 10 / 100);
Chirpstack和Things Network都提供了一系列集成,以将服务器收到的数据发送给其他服务。例如:我们可以将数据发送到影响数据库,使用MQTT,连接到AWS服务或Azure ...
在本节中,将看到一个实际情况,在该情况下,我们可以使用HTTP (事物网络中的Webhooks)和MQTT的集成来发送我们的设备发送的数据,并且我们的服务器收到了自己的应用程序。
访问集成:
如果使用Chirpstack ,我们很感兴趣
在这两个服务器中,此集成都以类似的方式工作:每次应用程序设备发送信息时启动事件(在TTN的情况下,我们必须标记上行链路消息框),并且使用此信息,将邮政-Type HTTP请求的延迟启动到我们指出的URL。
注意:一个很好的做法,要么验证事件是否正确启动,要么可视化数据格式是访问邮政局服务,我们可以在其中创建一个垃圾箱(临时URL以接收请求)。
Note2:如果您要启动的应用程序将请愿书包含在Localhost和Chirpstack Server(如本文档中所示)(如本文档所示),您将不得不表示URL如下:
http://host.docker.internal:PUERTO/uri
该文档仅涵盖Chirpstack和TTN的使用以发送数据(请愿书中具有不同的格式)。
如果数据已用此存储库的示例(文件夹Decoders-Integrations )进行解码,则我们将在请求中的构造中获得类似的主体:
{
"applicationID": 0,
"applicationName": "Name",
"deviceName": "DeviceName",
"devEUI": "BYTES_EUI",
"txInfo": [Object object],
"adr": true,
"dr": 5,
"fCnt": 24,
"fPort": 1,
"data": "DATA_WITHOUT_DECODE",
"objectJSON": {
"data":"DATA_WITHOUT_DECODE==",
"decodedData":{
"humidity":37,"temperature":23
},
"message":"Informacion recibida del nodo"
},
"tags": [Object object],
"confirmedUplink": false,
"devAddr": "BYTES_DEV_ADDR"
}
Objectjson是我们解码器函数返回的对象。
要读取它,例如,在JavaScript应用程序中,要做类似于以下操作的操作(在file /Decoders-Integrations/arduino_Chirpstack_Http_Integration.js中更多)
const { deviceName, objectJSON, devAddr} = req.body;
var sensorData = JSON.parse(objectJSON);
//devAddr esta codificado!
var temperature = sensorData.decodedData.temperature;
var humidity = sensorData.decodedData.humidity;
实际上,除非我们使用MQTTS(带有TLS的MQTT),否则不需要从服务器Web应用程序访问任何集成。
在此示例中,我们将签署我们的应用程序将最终设备发送数据的主题。
如果我们的应用程序是在家中启动的,并且还在Chirpstack服务器(如我们在本文档中显示的那样对DOCKERING),则经纪人主机将是WSL机器的IP。要了解这些数据,我们将启动:
wsl hostname -I
您还必须通过启动以下命令来做出一些配置(1883是蚊子的港口,如果另一种修改已使用):
netsh interface portproxy add v4tov4 listenport=1883 listenaddress=0.0.0.0 connectport=1883 connectaddress=127.0.0.1
我们可以在Docker的示例中使用MQTT,并带有带有TRU值的匿名参数(不使用任何类型的密码或用户列表),或者我们可以配置用户列表(每个都有可以读取或写入其各自密码的主题)(如以下文档所示)。
为此,我们将启动以下命令(我们可以从WSL启动它们),每个命令都会要求我们为每个用户介绍一个密码(在此示例中已使用所有用户):
# Create a password file, with users chirpstack_gw, chirpstack_ns, chirpstack_as, bob and nodeApp
sudo mosquitto_passwd -c /etc/mosquitto/passwd chirpstack_gw
sudo mosquitto_passwd /etc/mosquitto/passwd chirpstack_ns
sudo mosquitto_passwd /etc/mosquitto/passwd chirpstack_as
sudo mosquitto_passwd /etc/mosquitto/passwd bob
sudo mosquitto_passwd /etc/mosquitto/passwd nodeApp
# Optional, Secure the password file
sudo chmod 600 /etc/mosquitto/passwd
这将创建包含所有用户和密码的passwd文件,我们现在可以在同义文件中配置ACLS列表,如以下内容:
user chirpstack_gw
topic write gateway/+/event/+
topic read gateway/+/command/+
user chirpstackns
topic read gateway/+/event/+
topic write gateway/+/command/+
user chirpstack_as
topic write application/+/device/+/event/+
topic read application/+/device/+/command/+
user bob
topic read application/123/device/+/event/+
topic write application/123/device/+/command/+
user nodeApp
topic read application/+/device/#
topic write application/+/device/#
现在,我们必须修改服务器配置以使用这些凭据来修改/chirpstack-docker/configuration中的文件:
[application_server.integration.mqtt]
server="tcp://mosquitto:1883"
username="chirpstack_as"
password="pass"
[integration.mqtt.auth.generic]
servers=["tcp://mosquitto:1883"]
username="chirpstack_gw"
password="pass"
[network_server.gateway.backend.mqtt]
server="tcp://mosquitto:1883"
username="chirpstack_ns"
password="pass"
listener 1883
password_file /mosquitto/config/passwd
acl_file /mosquitto/config/acls
allow_anonymous false
mosquitto:
image: eclipse-mosquitto:2
ports:
- 1883:1883
volumes:
- ./configuration/eclipse-mosquitto/mosquitto.conf:/mosquitto/config/mosquitto.conf
- ./configuration/eclipse-mosquitto/passwd:/mosquitto/config/passwd
- ./configuration/eclipse-mosquitto/acls:/mosquitto/config/acls
在此示例中,我们将使用nodejs应用程序连接到我们本地的Chirpstack本地服务器。所有代码都可以在/Decoders-Integrations/arduino_Chirpstack_mqtt_Integration.js文件中找到。
首先,我们将必须安装MQTT软件包
npm install mqtt --save
与他一起,我们已经可以连接到经纪人:
var mqtt = require('mqtt')
const host = 'WSL_IP'
const port = '1883' //or your port
const clientId = 'mqtt_NodeApp_' + Math.random().toString(16).slice(3)
const connectUrl = 'mqtt://' + host + ':' + port;
const client = mqtt.connect(connectUrl, {
clientId,
clean: true,
//username: "nodeApp", //Descomentar si usamos contraseñas y acls
//password: "pass", //Colocar el usuario y contraseña correspondiente
connectTimeout: 4000,
reconnectPeriod: 1000,
debug: true
})
并订阅所需的主题( #字符是多级通配符,这意味着我们读取任何siptopian,而字符+是单一级别的通配符)。
const chirpstackApplicationID = 1; //Check url, for example: http://localhost:8080/#/organizations/1/applications. /1/ is the ID
const chirpstackDeviceID = "DEV_EUI";
const chirpstackReadAppTopic = "application/" + chirpstackApplicationID + "/device/#";
const chirpstackWriteAppTopic = "application/" + chirpstackApplicationID + "/device/"+chirpstackDeviceID+"/EXAMPLE";
我们将使用以下事件为此:
//Evento al conectarse
client.on('connect', function () {
console.log("Connected")
client.subscribe(chirpstackReadAppTopic, function (err) {
if (!err) {
console.log("Subscribed to topic: "+chirpstackReadAppTopic)
//client.publish(chirpstackWriteAppTopic, 'Hello mqtt') //Podemso enviar un mensaje para debugear
}
else {
console.log("Error in connection:")
console.log(err)
}
})
})
//Evento al recibir un mensaje
client.on('message', function (topic, message) {
// El mensaje es un buffer, convertimos a String.
var stringMsg = message.toString();
console.log(topic + " - " + stringMsg)
insertSensorEntry_Mqtt(topic, stringMsg); //Funcion que lee el mensaje e inserta en base de datos
})
在两个服务器(Chirpstack和Things Network)中,集成称为MQTT ,是的,在进行任何集成之前,我们必须配置证书。
A continuación se documentará como realizar la integración con MQTT en un servidor local de Chirpstack (para más info revisar el apartado ChirpStack privado en local de esta documentación).
Antes de generar los certificados, debemos tener instalado CFSSL & CFSSLJSON. Tras ello, clonaremos el siguiente repositorio propiedad del creador de Chirpstack y seguiremos los pasos de su documentación: Chirpstack-Certificates.
NOTA: Si se usa Windows, instalar los pre-requisitos en la máquina WSL pues se necesitará hacer uso del comando make .
Colocamos la carpeta certs generada con el proyecto Chirpstack-Certificates en nuestro proyecto Chirpstack-Docker . Después modificados el archivo docker-compose.yml para añadir a cada contenedor el volumen que contendrá los certificados correspondientes.
Seguimos siguiendo la documentación del proyecto Chirpstack-Certificates para realizar todas las modificaciones pertinentes en la configuración del servidor:
Como hemos visto anteriormente, el evento que se lanza al recibir un mensaje llama a una función que lee el mensaje recibido y lo descodifica.
El formato del mensaje recibido (si hemos usado los descodificadores del ejemplo) es una cadena de texto con el siguiente contenido:
{"applicationID":"1","applicationName":"APP_NAME","deviceName":"DEV_NAME","devEUI":"DEV_ADDRESS", "txInfo":{"frequency":868500000,"dr":5},"adr":true,"fCnt":2, "fPort":1,"data":"DATA","object":{"data":"DATA","decodedData":{"humidity":0,"temperature":-327},"message":"Informacion recibida del nodo"}}
Y es lo que buscamos leer en la siguiente función:
function insertSensorEntry_Mqtt(topic, msg){
console.log("INSERTAMOS DATO DE SENSOR RECIBIDO POR MQTT EN TOPICO: "+topic);
const parseMsg = JSON.parse(msg); //Recordar haber hecho un ToString al buffer antes!
var deviceName = parseMsg.deviceName;
var devAddr = parseMsg.devEUI; //No codificado
var temperature = parseMsg.object.decodedData.temperature;
var humidity = parseMsg.object.decodedData.humidity;
var success = true;
}
object es el objeto retornado por nuestra función Decoder .
Como bien se sabe, la tasa de transferencia de LoRA es muy baja, lo que provoca una gran perdida de paquetes y una enorme latencia cuando se envía información:
Algunos expertos indican que es necesario cierta distancia entre los dispositivos (30m y preferiblemente algún obstaculo entre ellos) para que la comunicación sea más fluida. No ha sido probado y solo se ha lanzado con las dos tarjetas en un extremo cada una de un piso.
Por otro lado se hace uso de versiones antiguas de LoRaWAN (1.0.2 y 1.0.3) que tienen problemas de seguridad que se solventan en parte en las siguientes versiones (1.0.4 y 1.1.0, esta última también implementa re-conectividad en caso de desconectarse de la red LoRaWAN), pero no se dispone de librerias para trabajar con ellas.
Esto no quita que esta técnología pueda ser muy interesante y útil en el futuro debido a no depender de proveedores externos (de comunicaciones y electricidad), siendo una opción ecónomica y muy llamativa para utilizar en proyectos IoT de grandes ciudades o entornos rurales.
Este proyecto ha sido realizado para la Fundación CTIC, su uso es libre y no es necesarío ningún crédito en su uso (Revisar las licencia de las librerias utilizadas).