ESP32--通过网络获取北京时间的Python脚本

环境不同,代码仅供参考

 ESP32、ESP8266等小设备没有本地时钟芯片,时间经常会有偏差。通过 MicroPython 可以很方便的复用python代码 。

获取 网络时间 的代码如下:

# 使用 MicroPython的 urequests 库
import urequests


def getBeijingTime():
    try:
        # 设置头信息,没有访问会错误400!!!
        headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.25 Safari/537.36 Core/1.70.3775.400 QQBrowser/10.6.4209.400'}
        # 设置访问地址,我们分析到的;
        url = r'http://time1909.beijing-time.org/time.asp'
        # 用requests get这个地址,带头信息的;
        r = urequests.get(url=url, headers=headers)
        # 检查返回的通讯代码,200是正确返回;
        if r.status_code == 200:
            # 定义result变量存放返回的信息源码;
            result = r.text
            # 通过;分割文本;
            data = result.split(";")
            # ======================================================

            # 以下是数据文本处理:切割、取长度,最最基础的东西就不描述了;

            year = data[1][len("nyear") + 3: len(data[1])]

            month = data[2][len("nmonth") + 3: len(data[2])]
            day = data[3][len("nday") + 3: len(data[3])]
            wday = data[4][len("nwday") + 3: len(data[4])]
            hrs = data[5][len("nhrs") + 3: len(data[5])]
            minute = data[6][len("nmin") + 3: len(data[6])]
            sec = data[7][len("nsec") + 3: len(data[7])]
            # ======================================================
            # 这个也简单把切割好的变量拼到beijinTimeStr变量里;
            #beijingTimeStr = "%s/%s/%s %s:%s:%s" % (year, month, day, hrs, minute, sec)
            # 把时间打印出来看看;
            #print(beijingTimeStr)
            # 将beijingTimeStr转为时间戳格式;
            #beijingTime = time.mktime(time.strptime(beijingTimeStr, "%Y/%m/%d %X"))
            # 返回时间戳;
            beijingTime = [int(year), int(month), int(day), int(wday), int(hrs), int(minute), int(sec)]
            return (beijingTime)
    except Exception as e:
      return ('getBeijingTime() Exception Error! Info: ', e)

用到的 urquests 库:   

# usocket 内置
import usocket

class Response:

    def __init__(self, f):
        self.raw = f
        self.encoding = "utf-8"
        self._cached = None

    def close(self):
        if self.raw:
            self.raw.close()
            self.raw = None
        self._cached = None

    @property
    def content(self):
        if self._cached is None:
            try:
                self._cached = self.raw.read()
            finally:
                self.raw.close()
                self.raw = None
        return self._cached

    @property
    def text(self):
        return str(self.content, self.encoding)

    def json(self):
        import ujson
        return ujson.loads(self.content)


def request(method, url, data=None, json=None, headers={}, stream=None):
    try:
        proto, dummy, host, path = url.split("/", 3)
    except ValueError:
        proto, dummy, host = url.split("/", 2)
        path = ""
    if proto == "http:":
        port = 80
    elif proto == "https:":
        import ussl
        port = 443
    else:
        raise ValueError("Unsupported protocol: " + proto)

    if ":" in host:
        host, port = host.split(":", 1)
        port = int(port)

    ai = usocket.getaddrinfo(host, port, 0, usocket.SOCK_STREAM)
    ai = ai[0]

    s = usocket.socket(ai[0], ai[1], ai[2])
    try:
        s.connect(ai[-1])
        if proto == "https:":
            s = ussl.wrap_socket(s, server_hostname=host)
        s.write(b"%s /%s HTTP/1.0\r\n" % (method, path))
        if not "Host" in headers:
            s.write(b"Host: %s\r\n" % host)
        # Iterate over keys to avoid tuple alloc
        for k in headers:
            s.write(k)
            s.write(b": ")
            s.write(headers[k])
            s.write(b"\r\n")
        if json is not None:
            assert data is None
            import ujson
            data = ujson.dumps(json)
            s.write(b"Content-Type: application/json\r\n")
        if data:
            s.write(b"Content-Length: %d\r\n" % len(data))
        s.write(b"\r\n")
        if data:
            s.write(data)

        l = s.readline()
        #print(l)
        l = l.split(None, 2)
        status = int(l[1])
        reason = ""
        if len(l) > 2:
            reason = l[2].rstrip()
        while True:
            l = s.readline()
            if not l or l == b"\r\n":
                break
            #print(l)
            if l.startswith(b"Transfer-Encoding:"):
                if b"chunked" in l:
                    raise ValueError("Unsupported " + l)
            elif l.startswith(b"Location:") and not 200 <= status <= 299:
                raise NotImplementedError("Redirects not yet supported")
    except OSError:
        s.close()
        raise

    resp = Response(s)
    resp.status_code = status
    resp.reason = reason
    return resp


def head(url, **kw):
    return request("HEAD", url, **kw)

def get(url, **kw):
    return request("GET", url, **kw)

def post(url, **kw):
    return request("POST", url, **kw)

def put(url, **kw):
    return request("PUT", url, **kw)

def patch(url, **kw):
    return request("PATCH", url, **kw)

def delete(url, **kw):
    return request("DELETE", url, **kw)

获取北京时间并修改 ESP 本地时钟:

# 导入相关数据包
from machine import RTC
  
# 获取当前时间
gettime = getBeijingTime()

# 初始化RTC()
rtc = RTC()

# 格式化后写入 ESP 本地时钟
#rtc.datetime((2017, 8, 23, 1, 12, 48, 0, 0))(年,月,日,星期几,时,分,秒,微秒)
rtc.datetime((gettime[0], gettime[1], gettime[2], gettime[3], gettime[4], gettime[5], gettime[6], 0))

  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值