【问题标题】:Accessing device on local network through server hosted webhook通过服务器托管的 webhook 访问本地网络上的设备
【发布时间】:2017-12-27 14:21:24
【问题描述】:

我有一个充当 webhook 的 python 脚本。一部分如下:

import json
import os
import urllib
import socket
import _thread
from flask import Flask
from flask import request
from flask import make_response
app=Flask(__name__)

ip = ('192.168.1.75', 9050)

@app.route('/webhook',methods=['GET','POST'])
    def webhook():
        _thread.start_new_thread(sendDataToDevice,(ip))
        req = request.get_json(silent=True,force=True)
        print("Request:")
        print(json.dumps(req,indent=4))
        res=makeWebHookResult(req)
        res=json.dumps(res,indent=4)
        r=make_response(res)
        r.headers['Content-Type']='application/json'
        return r

if __name__ == '__main__':
    app.run(port=8080,host='localhost')

脚本的功能是向连接到本地网络的设备发送一些数据。 当我打开我的网络浏览器并在 url 栏上输入以下内容时,它可以完美运行:

http://localhost:8080/webhook

我想在服务器上托管脚本,例如。赫罗库。这种情况下如何访问本地设备?

注意:我知道我可以在本地计算机上运行该脚本并使用 ngrok 使其对 Internet 可见,但我希望即使在我的计算机关闭时也可以访问它。另外,想要一个固定的链接,并且 ngrok 给出的链接在每次运行时都会改变。

【问题讨论】:

  • 如果我错了,请纠正我。在您的示例中,您有一些设备在本地网络上的 device_ip, device_port = "192.168.1.75", 9050 上运行。当您将应用程序托管在远程服务器(例如 Heroku)上时,您想要的是能够获得 device_ip 和 device_port?另外你能告诉我这是什么设备吗?它是计算机、智能手机还是嵌入式系统?
  • 没错。该设备是一个嵌入式系统,具体来说是一个带有esp8266 WiFi模块的Arduino Uno板。
  • 我可以假设您对本地网络上的 WiFi 路由器具有管理员访问权限吗?
  • 是的,我有管理员权限。

标签: python networking flask iot


【解决方案1】:

我之前在使用 IoT 时遇到过类似的问题。不幸的是,没有简单的方法可以使设备在线可见。这是我使用的一个简单的解决方案。它可能不是最好的,但它确实有效。

DDNS+端口转发+静态IP

如果您可以访问本地 WiFi 路由器,则可以设置称为 DDNS(动态域名系统)的东西。然后,您的路由器将连接到像 no-ip (www.noip.com) 这样的 DDNS 服务提供商,并且它将在互联网上可见。您可以提供自定义 URL,例如 susmit-home.noip.com

但是,susmit-home.noip.com 现在将仅指向您的 WiFi 路由器,而不是您的 WiFi 网络。因此,如果您想访问本地的device_ipdevice_port,例如“192.168.1.75”、9050。那么您可以在路由器上为该本地 IP-端口组合设置端口转发。通常设置如下所示:

  • 本地 IP:device_ip(例如 192.168.1.75)
  • 本地端口:device_port(例如 9050)
  • 出站端口:any_port(例如 9050)

确保您的 device_ip 是 WiFi 路由器上的静态 IP,这样它就不会改变。

最后,在您的代码中,您只需将行 ip = ('192.168.1.75', 9050) 替换为 ip = ('susmit-home.noip.com', 9050)

其他解决方案:

  1. 一个稍微复杂一点的解决方案是设置 VPN,这样您的本地网络和远程服务器(例如 Heroku)就可以互相使用,就好像它们在同一个本地网络中一样。
  2. 如果您的设备是计算机或 Raspberry Pi,那么您可以使用 SSH 远程端口转发从远程服务器访问您的本地设备。

【讨论】:

  • 它对我不起作用,但我找到了另一种解决方法。我在脚本中添加了一个新的 webhook 函数。我一直使用设备轮询它并处理结果。这基本上消除了获取设备 IP 或端口的需要。我会用你的方法看看我哪里出错了。
  • 是的,即使在生产过程中,轮询也是最首选的解决方案 :) 我曾经尝试过的另一种解决方案是保持连接始终打开并将结果转储到连接上。它提供实时连接,但非常不可靠,尤其是在嵌入式系统上。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-08-11
  • 1970-01-01
  • 2019-11-20
  • 2016-01-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多