How to make RTC clock with NTP



  • How to make RTC clock with NTP Sync for M5StickC in in python (UIflow 1.4.4) ?
    the code below gives an error "RTC' object has no atribute 'ntp_sync"

    import machine
    import utime

    rtc = machine.RTC()
    rtc.ntp_sync(server="hr.pool.ntp.org", tz="CET-1CEST")
    rtc.synced()
    True
    utime.gmtime()
    (2018, 1, 29, 16, 3, 18, 2, 29)
    utime.localtime()
    (2018, 1, 29, 17, 3, 30, 2, 29)


  • M5Stack

    Hey @lilianz I regret to inform you that ntp_sync hasn't been present in the RTC module since firmware v1.2.3 I'm not entirely sure why, but thats the way it is. Perhaps you will find some clues on controlling the RTC from one of the many watch projects on our hackster page https://www.hackster.io/m5stack/projects



  • Got tired of waiting for M5Stack MicroPython to support rtc.ntp_sync, so I came up with a simple workaround, assuming you have access to a webserver:

    On your webserver, just create a tiny datetime.php file as follows:


    <html><body>
    <?php echo '[' . getDatetimeNow() . ']';

    function getDatetimeNow() {
    $tz_object = new DateTimeZone('Canada/Pacific');
    $datetime = new DateTime();
    $datetime->setTimezone($tz_object);
    return $datetime->format('Y-m-d\ H:i:s');
    }
    ?>
    </body></html>


    Change the TimeZone to your own timezone.
    When this PHP code runs, it simply takes the webserver's internal date and time (which should be fairly accurate) and displays the text [yyyy-mm-dd hh:mm:ss]

    Now in your MicroPython code, do the following:

    from micropython import const
    from m5stack import *
    from m5ui import *
    from uiflow import *
    import utime as time
    import machine
    import urequests
    import wifiCfg
    
    RTC_YYYY = const(0)
    RTC_MM   = const(1)
    RTC_DD   = const(2)
    RTC_HH   = const(4)
    RTC_MN   = const(5)
    RTC_SS   = const(6)
    
    WIFI_SSID      = 'YourSSID'
    WIFI_PASSWORD  = 'YourPassword'
    URL            = 'http://api.pushingbox.com/pushingbox?devid=v883AAC5A2DE4A5A&location='
    DATETIME_URL   = 'http://stdenissoftware.com/datetime.php'
    
    
    #==================================================================
    # Set internal RTC clock based on calling a URL that returns the current local time
    # as '[yyyy-mm-dd hh:mm:ss]'. Function must be connected to internet.
    # Parameters:
    #   WIFI_SSID: the SSID to connect to
    #   WIFI_PASSWORD: Wifi Password
    #   DATETIME_URL: the URL to call to return the current time 
    def setRTC(WIFI_SSID,WIFI_PASSWORD,DATETIME_URL):
      rtc = machine.RTC()
      while wifiCfg.wlan_sta.isconnected() != True:
        wifiCfg.doConnect(WIFI_SSID,WIFI_PASSWORD)
        if wifiCfg.wlan_sta.isconnected() != True:
          time.sleep(1)
        #end if
      #wend
      if wifiCfg.wlan_sta.isconnected():
        #lblWiFi.setText('WiFi Connected')
        try:
          req = urequests.request(method='GET', url=DATETIME_URL,headers='')
          httpData = req.text
          iPos1 = httpData.find("[")
          iPos2 = httpData.find("]")
          if iPos2 > iPos1:
            DateTime = httpData[iPos1+1:iPos2]
            YYYY = int(DateTime[0:4])
            MM   = int(DateTime[5:7])
            DD   = int(DateTime[8:10])
            HH   = int(DateTime[11:13])
            MN   = int(DateTime[14:16])
            SS   = int(DateTime[17:19])
            # Set RTC using: Year,Month,Day,WeekDay,Hour,Min,Sec,MS
            rtc.datetime((YYYY,MM,DD,0,HH,MN,SS,0))
          else:
            DateTime = ''
          #end if
        except:
          DateTime = ''
      else:
        #lblWiFi.setText('WiFi not connected')
        DateTime = ''
      #end if
      return DateTime
    #------------------------------------------------------------------
    
    RightNow = rtc.datetime()
    CurrentYear   = int(newDateTime[RTC_YYYY])
    CurrentMonth  = int(newDateTime[RTC_MM])
    CurrentDay    = int(newDateTime[RTC_DD])
    CurrentHour   = int(newDateTime[RTC_HH])
    CurrentMinute = int(newDateTime[RTC_MN])
    CurrentSecond = int(newDateTime[RTC_SS])
    
    

    So, once the RTC is set, it will keep pretty accurate time until the M5Stack gets reset or powered off. Or you can just call the routine every day to resync it. Note that the PHP code is currently set for Canadian Pacific Time.
    Also note that the above URL is my personal webserver - you can use it for quick testing, but not long term please.



  • Sorry, the last few lines should read:

    CurrentYear   = int(RightNow[RTC_YYYY])
    CurrentMonth  = int(RightNow[RTC_MM])
    CurrentDay    = int(RightNowRTC_DD])
    CurrentHour   = int(RightNow[RTC_HH])
    CurrentMinute = int(RightNow[RTC_MN])
    CurrentSecond = int(RightNow[RTC_SS])
    

    Sorry, this is my first MicroPython program and just learning it.
    Ray