0

I ported my Somfy sketch to Python with the help of the very good pigpio library, so that my Raspberry Pi can open the blinds in the morning and close them after sunset.

Everything works and I'm happy with it.

To add a bit of interactivity, I would like to be able to control the blinds via a webpage served by the Raspberry Pi. This would mean launching a Python script when a button is pressed on the webpage.

There would be n blinds, so 3*n buttons ({UP, STOP, DOWN} for every blind) on the page. They could either trigger the same script with two arguments (the blind and the command) or trigger a different script for each button (I don't mind).

But I've never set up a webserver. I barely know any HTML and I've never used a CGI, nor do I precisely understand what it is.

So, my questions are:

  1. What's the simplest (will have to deliver one page and trigger scripts) webserver I can use?
  2. What HTML code to use?
  3. The most important: how a click on a button/link will start a script (possibly passing two arguments)?
  4. How to make sure this will only work locally (checking the IP of the host, or downloading a certificate on my smartphone, the easiest route)?

The script is in the somfy directory. The same goes for the text files keeping track of the rolling code and remote address. Maybe the page could be placed there as well? If you really feel like you need the code, I'm giving it to you but I'm not sure it's necessary:

def envoi_commande(telco, bouton):
   checksum = 0

   with open("somfy/" + telco + ".txt", 'r') as file:
      data = file.readlines()

   teleco = int(data[0], 16)
   code = int(data[1])
   data[1] = str(code + 1)

   print hex(teleco)
   print code

   with open("somfy/" + telco + ".txt", 'w') as file:
      file.writelines(data)

   pi = pigpio.pi() # connect to Pi

   if not pi.connected:
      exit()

   pi.wave_add_new()
   pi.set_mode(TXGPIO, pigpio.OUTPUT)


   print "Remote  :      " + "0x%0.2X" % teleco
   print "Button  :      " + "0x%0.2X" % bouton
   print "Rolling code : " + str(code)
   print ""

   frame[0] = 0xA7;       # Encryption key. Doesn't matter much
   frame[1] = bouton << 4 # Which button did  you press? The 4 LSB will be the checksum
   frame[2] = code >> 8               # Rolling code (big endian)
   frame[3] = (code & 0xFF)           # Rolling code
   frame[4] = teleco >> 16            # Remote address
   frame[5] = ((teleco >>  8) & 0xFF) # Remote address
   frame[6] = (teleco & 0xFF)         # Remote address

   print "Frame  :    ",
   for octet in frame:
      print "0x%0.2X" % octet,
   print ""

   for i in range(0, 7):
      checksum = checksum ^ frame[i] ^ (frame[i] >> 4)

   checksum &= 0b1111; # We keep the last 4 bits only

   frame[1] |= checksum;

   print "With cks  : ",
   for octet in frame:
      print "0x%0.2X" % octet,
   print ""

   for i in range(1, 7):
      frame[i] ^= frame[i-1];

   print "Obfuscated :",
   for octet in frame:
      print "0x%0.2X" % octet,
   print ""

   wf=[]
   wf.append(pigpio.pulse(1<<TXGPIO, 0, 9415))
   wf.append(pigpio.pulse(0, 1<<TXGPIO, 89565))
   for i in range(2):
      wf.append(pigpio.pulse(1<<TXGPIO, 0, 2560))
      wf.append(pigpio.pulse(0, 1<<TXGPIO, 2560))
   wf.append(pigpio.pulse(1<<TXGPIO, 0, 4550))
   wf.append(pigpio.pulse(0, 1<<TXGPIO,  640))

   for i in range (0, 56):
      if ((frame[i/8] >> (7 - (i%8))) & 1):
         wf.append(pigpio.pulse(0, 1<<TXGPIO, 640))
         wf.append(pigpio.pulse(1<<TXGPIO, 0, 640))
      else:
         wf.append(pigpio.pulse(1<<TXGPIO, 0, 640))
         wf.append(pigpio.pulse(0, 1<<TXGPIO, 640))

   wf.append(pigpio.pulse(0, 1<<TXGPIO, 30415))

   #2 (I repeat the frame)
   for i in range(7):
      wf.append(pigpio.pulse(1<<TXGPIO, 0, 2560))
      wf.append(pigpio.pulse(0, 1<<TXGPIO, 2560))
   wf.append(pigpio.pulse(1<<TXGPIO, 0, 4550))
   wf.append(pigpio.pulse(0, 1<<TXGPIO,  640))

   for i in range (0, 56):
      if ((frame[i/8] >> (7 - (i%8))) & 1):
         wf.append(pigpio.pulse(0, 1<<TXGPIO, 640))
         wf.append(pigpio.pulse(1<<TXGPIO, 0, 640))
      else:
         wf.append(pigpio.pulse(1<<TXGPIO, 0, 640))
         wf.append(pigpio.pulse(0, 1<<TXGPIO, 640))

   wf.append(pigpio.pulse(0, 1<<TXGPIO, 30415))


   pi.wave_add_generic(wf)
   wid = pi.wave_create()
   pi.wave_send_once(wid)
   while pi.wave_tx_busy():
      pass
   pi.wave_delete(wid)

   pi.stop()
Nicolas
  • 25
  • 6

1 Answers1

0

Because you have already ported your script to python you could use django

www.djangoproject.com

And when a button is pressed call your python script within a view.

Let me add a number of caveats in that a lot of this could depend on other factors as there is a bit of work in completing this task.

This is a good site for learning html http://www.w3schools.com/

BenJ
  • 456
  • 2
  • 7