check if consol avaible and user input timeout (SOLVED)



  • Hello there!
    For my project I would like to have some basic configuration options on startup.

    • Check if console is avaible. How can I do that? (is it connected to a pc or just the wall plug or running from battery?)
    • Then wait for the user for few sec.
    • Also is it possible to store a value like index on the device, what stays there after restart without power? For file names it would be nice to not over ride the logs every time. So if I could store an index on my lopy4 i could add that index to my file name (or on the SD card).
      Thanks in advance!

    My code is below:

    from machine import SD
    import os
    import time
    
    class SDLogger:
        
        def __init__(self):
            sd = SD()
            os.mount(sd,'/sd') 
    		# TODO: Check if console is avaible, if not use some predifined values for file names
    		# TODO: throw error if SD is not avaible 
            sdformat()
    
        # def createFolder(self):
        #     #TODO: implement, with folder include the currenct time(ex: from the GPS) or just increasing index
    
    
        def creatLogFile(self, header, filename):
            #TODO: create a check for valid header, and raise exeption if not
            with open(str("/sd/"+filename+".csv"), 'w')as ds:
                ds.write(header)
                ds.close()
        
        def insertRecordToLogFile(self, log):
            #TODO: create a check for valid input based on the header , and raise exeption if not
            with open("/sd/data.csv", 'a')as ds:
                ds.write(log)
                ds.close()
    
        def sdFormat(self):
            text = input("Do you want to format the sd card? (Y/N)")
    		#TODO: wait for user input 3 seconds, if no input continue with no
            if text == "Y" or text == "y" or text == "yes":
                print("Formatting SD card")
                os.mkfs("/sd")
            elif text == "N" or text == "n" or text == "no":
                print("Sd wont be formatted.")
    


  • @robert-hh Thank you, It works like a charm! :)



  • @tttadam using UART0 works, and here is a skeleton of what you might use:

    from machine import UART, Timer
    import time
    uart = UART(0, 115200)
    clock = Timer.Chrono()
    
    def sdFormat():
            print("Do you want to format the sd card? (Y/N) ", end="")
            clock.start()
            while uart.any() <= 0 and clock.read() < 10:
                time.sleep_ms(10)  #waiting
            clock.stop()
            if uart.any() > 0:
                text = uart.read(1)
            else:
                text = b""
            if text.lower() == b"y":
                print("\nFormatting SD card")
                # os.mkfs("/sd")
            else:
                print("\nSD wont be formatted.")
    


  • @tttadam Input() is indeed blocking.

    About the rtc bug: you have to assign it as a class member, like

    self.rtc = RTC()

    and then you can reference it as self.rtc in a class method.



  • @robert-hh Well, I just tested the code. It stuck at
    " text = input("Do you want to format the sd card? (Y/N)")"
    So the timer never starts.
    And I also get an error for rtc is not defined. But I define it in init

    def sdFormat(self):
            text = input("Do you want to format the sd card? (Y/N)")
    		#TODO: wait for user input 3 seconds
    		#TODO: test
            rtc.alarm(id=1, time=30000, repeat=False)
            while uart.any() <= 0 or rtc.alarm_left(alarm_id=1) > 0: 
    			time.sleep_ms(10)  #waiting
            if text == "Y" or text == "y" or text == "yes":
                print("Formatting SD card")
                os.mkfs("/sd")
            elif text == "N" or text == "n" or text == "no" or text == "":
                print("Sd wont be formatted.")
    
    from machine import SD, UART, RTC
    import os
    import time
    
    class SDLogger:
        def __init__(self, uart):
            sd = SD()
            os.mount(sd,'/sd') 
    		# TODO: Check if console is avaible, if not use some predifined values for file names
    		# TODO: throw error if SD is not avaible 
            rtc = RTC()
            rtc.init((2014, 5, 1, 4, 13, 0, 0, 0)) #TODO make sure that the real time gets here, from GPS
    


  • @tttadam I might get lost in the various micropython variants and modules, but it might be that you cannot use UART0 if it is assigned to the console. and then, uart.any() will not work. I have to check myself this evening. If yes, your code should be like:

    while (uart.any() <= 0) OR (RTC.alarm_left(alarm_id=1)>0): 
        sleep_ms(10)  #waiting	
    

    uart.any() returns 0 if no char is available, and busy wait loops should always include a short sleep, as that helps with task scheduling



  • @robert-hh Actually for my project a I am using the pytrack board with lopy4.



  • @psychogenic Thank you, .nvs_set() is exactly what I need.
    Regarding to uart.any() I will check it this evening, but I am not sure about that. Did it work if I am connected to pc over usb cable?
    Do you think something like this?

        def sdFormat(self):
            text = input("Do you want to format the sd card? (Y/N)")
    		#TODO: wait for user input 3 seconds
    		
    	rtc.alarm(id=1, time=30000, repeat=False)
    	while (uart.any()<0) OR (RTC.alarm_left(alarm_id=1)>0): 
                     #waiting	
    
            if text == "Y" or text == "y" or text == "yes":
                print("Formatting SD card")
                os.mkfs("/sd")
            elif text == "N" or text == "n" or text == "no":
                print("Sd wont be formatted.")
    


  • @tttadam You could connect one of the USB(UART status lines to a GPIO, which indicate a connection being present. When using the expansion boards, RTS could be used, which according to some specs is connected to P19. For Expansion board 3 and the sensor boards, no wiring of the modem control lines is documented. Sp we have the usual trouble of sparse documentation, which includes the schematics.
    Note: Using an expansion Board 2, this would be an issue when using a FiPy board, which also uses P19/P20 for its modem control lines.



  • Hi,

    I think you could loop around checks for uart.any() to see if anything's been received from the serial line, and eventually time out of there.

    As for storing index value in NVRAM, the pycom.nvs_set()/nvs_get() are a little disappointing in only supporting integers but seem perfect for your application.



Pycom on Twitter