├── README.md ├── aREST.lua └── examples └── basic.lua /README.md: -------------------------------------------------------------------------------- 1 | # aREST-ESP8266 2 | 3 | **This project is now deprecated, as I am focusing all my efforts on the Arduino-compatible ESP8266 library. You can find the Arduino-compatible version of the library at [https://github.com/marcoschwartz/aREST](https://github.com/marcoschwartz/aREST)** 4 | 5 | aREST API for the ESP8266 WiFi chip using the NodeMCU firmware 6 | 7 | Version 0.1 8 | 9 | ## Overview 10 | 11 | A simple module that implements a REST API for the ESP8266 chip. 12 | 13 | If you want to know more about aREST, go over to [http://arest.io/](http://arest.io/). 14 | 15 | ## Contents 16 | 17 | - aREST.lua: the library file. 18 | - examples: several examples using the aREST module 19 | 20 | ## Supported Hardware 21 | 22 | The library is in theory working with all the modules based on the ESP8266 chip. It was tested with the ElectroDragon ESP8266 module & the Olimex ESP8266 development board. 23 | 24 | ## Requirements 25 | 26 | Using this library requires an ESP8266 board with the NodeMCU firmware running on it, and connected to your local WiFi network. You can learn more about the NodeMCU firmware on the NodeMCU GitHub repository ([https://github.com/nodemcu/nodemcu-firmware](https://github.com/nodemcu/nodemcu-firmware)). 27 | 28 | You can also find a complete guide on how to setup an ESP8266 board with the NodeMCU firmware on: 29 | 30 | [https://www.openhomeautomation.net/getting-started-esp8266/](https://www.openhomeautomation.net/getting-started-esp8266/) 31 | 32 | ## Setup 33 | 34 | To install the module, simply place the aREST.lua file at the root of your ESP8266 board. To do so you can use tools like ESPlorer ([https://github.com/4refr0nt/ESPlorer](https://github.com/4refr0nt/ESPlorer)) or LuaTool ([https://github.com/4refr0nt/luatool](https://github.com/4refr0nt/luatool)). 35 | 36 | ## GPIO Pins 37 | 38 | This module follows the GPIO pins mapping as defined in the official [NodeMCU firmware documentation](https://github.com/nodemcu/nodemcu-firmware/wiki/nodemcu_api_en#new_gpio_map). 39 | 40 | ## Quick Test 41 | 42 | 1. Connect a LED & resistor to pin number 1 of your ESP8266 board 43 | 2. Start your ESP8266 module and get the IP address of the module. Let's assume here it is 192.168.1.103 44 | 3. Put the basic.lua example at the root of your ESP8266 chip 45 | 4. Execute the file via the dofile("basic.lua") command 46 | 5. Go to a web browser and type `192.168.1.103/mode/1/o` to set the pin as an output 47 | 6. Now type `192.168.1.103/digital/1/1` and the LED should turn on 48 | 49 | ## API documentation 50 | 51 | The API currently supports five type of commands: digital, analog, and mode. 52 | 53 | ### Digital 54 | 55 | Digital is to write or read on digital pins of the ESP8266. For example: 56 | * `/digital/1/0` sets pin number 1 to a low state 57 | * `/digital/1/1` sets pin number 1 to a high state 58 | * `/digital/1` reads value from pin number 1 in JSON format (note that for compatibility reasons, `/digital/1/r` produces the same result) 59 | 60 | ### Analog 61 | 62 | Analog is to write or read analog values on the ESP8266. Note that you can only read analog values from analog pin 0. For example: 63 | * `/analog/1/123` sets pin number 1 to 123 using PWM 64 | * `/analog/0` returns analog value from pin number 0 in JSON format (note that for compatibility reasons, `/analog/0/r` produces the same result) 65 | 66 | ### Mode 67 | 68 | Mode is to change the mode on a pin. For example: 69 | * `/mode/1/o` sets pin number 1 as a digital output 70 | * `/mode/1/i` sets pin number 1 as a digital input 71 | * `/mode/1/p` sets pin number 1 as a PWM output 72 | 73 | ### Get data about the board 74 | 75 | You can also access a description of all the variables that were declared on the board with a single command. This is useful to automatically build graphical interfaces based on the variables exposed to the API. This can be done via the following calls: 76 | * `/` or `/id` 77 | * The names & types of the variables will then be stored in the variables field of the returned JSON object 78 | -------------------------------------------------------------------------------- /aREST.lua: -------------------------------------------------------------------------------- 1 | --[[ 2 | 3 | aREST Library for the ESP8266 chip using the NodeMCU firmware 4 | See the README file for more details. 5 | 6 | Written in 2015 by Marco Schwartz under a GPL license. 7 | 8 | Version 0.1 9 | 10 | Changelog: 11 | 12 | Version 0.1: First working version of the library 13 | 14 | --]] 15 | 16 | -- Module declaration 17 | local aREST = {} 18 | 19 | -- Attributes 20 | local _name 21 | local _id 22 | 23 | function aREST.set_id(id) 24 | _id = id 25 | end 26 | 27 | function aREST.set_name(name) 28 | _name = name 29 | end 30 | 31 | function aREST.handle(conn, request) 32 | 33 | -- Variables 34 | local pin 35 | local command 36 | local value 37 | local answer = {} 38 | local mode 39 | local variables = {} 40 | 41 | -- ID and name 42 | answer['id'] = _id 43 | answer["name"] = _name 44 | 45 | -- Variables 46 | variables["temperature"] = 30 47 | 48 | -- Find start 49 | local e = string.find(request, "/") 50 | local request_handle = string.sub(request, e + 1) 51 | 52 | -- Cut end 53 | e = string.find(request_handle, "HTTP") 54 | request_handle = string.sub(request_handle, 0, (e-2)) 55 | 56 | -- Find mode 57 | e = string.find(request_handle, "/") 58 | if e == nil then 59 | mode = request_handle 60 | else 61 | mode = string.sub(request_handle, 0, (e-1)) 62 | 63 | -- Find pin & command 64 | request_handle = string.sub(request_handle, (e+1)) 65 | e = string.find(request_handle, "/") 66 | 67 | if e == nil then 68 | pin = request_handle 69 | pin = tonumber(pin) 70 | else 71 | pin = string.sub(request_handle, 0, (e-1)) 72 | pin = tonumber(pin) 73 | request_handle = string.sub(request_handle, (e+1)) 74 | command = request_handle 75 | end 76 | end 77 | 78 | -- Debug output 79 | print('Mode: ', mode) 80 | print('Pin: ', pin) 81 | print('Command: ', command) 82 | 83 | -- Apply command 84 | if pin == nil then 85 | for key,value in pairs(variables) do 86 | if key == mode then answer[key] = value end 87 | end 88 | end 89 | 90 | if mode == "mode" then 91 | if command == "o" then 92 | gpio.mode(pin, gpio.OUTPUT) 93 | answer['message'] = "Pin D" .. pin .. " set to output" 94 | elseif command == "i" then 95 | gpio.mode(pin, gpio.INPUT) 96 | answer['message'] = "Pin D" .. pin .. " set to input" 97 | elseif command == "p" then 98 | pwm.setup(pin, 100, 0) 99 | pwm.start(pin) 100 | answer['message'] = "Pin D" .. pin .. " set to PWM" 101 | end 102 | end 103 | 104 | if mode == "digital" then 105 | 106 | if command == "0" then 107 | gpio.write(pin, gpio.LOW) 108 | answer['message'] = "Pin D" .. pin .. " set to 0" 109 | elseif command == "1" then 110 | gpio.write(pin, gpio.HIGH) 111 | answer['message'] = "Pin D" .. pin .. " set to 1" 112 | elseif command == "r" then 113 | value = gpio.read(pin) 114 | answer['return_value'] = value 115 | elseif command == nil then 116 | value = gpio.read(pin) 117 | answer['return_value'] = value 118 | end 119 | end 120 | 121 | if mode == "analog" then 122 | if command == nil then 123 | value = adc.read(pin) 124 | answer['return_value'] = value 125 | else 126 | pwm.setduty(pin, command) 127 | answer['message'] = "Pin D" .. pin .. " set to " .. command 128 | end 129 | end 130 | 131 | conn:send("HTTP/1.1 200 OK\r\nContent-Type: application/json\r\nConnection: close\r\n\r\n" .. table_to_json(answer) .. "\r\n") 132 | 133 | end 134 | 135 | function table_to_json(json_table) 136 | 137 | local json = "" 138 | json = json .. "{" 139 | 140 | for key,value in pairs(json_table) do 141 | json = json .. "\"" .. key .. "\": \"" .. value .. "\", " 142 | end 143 | 144 | json = string.sub(json, 0, -3) 145 | json = json .. "}" 146 | 147 | return json 148 | 149 | end 150 | 151 | return aREST -------------------------------------------------------------------------------- /examples/basic.lua: -------------------------------------------------------------------------------- 1 | -- Include aREST module 2 | local rest = require "aREST" 3 | 4 | -- Set module ID & name 5 | rest.set_id("1") 6 | rest.set_name("esp8266") 7 | 8 | -- Create server 9 | srv=net.createServer(net.TCP) 10 | print("Server started") 11 | 12 | -- Start server 13 | srv:listen(80,function(conn) 14 | conn:on("receive",function(conn,request) 15 | 16 | -- Handle requests 17 | rest.handle(conn, request) 18 | 19 | end) 20 | 21 | conn:on("sent",function(conn) conn:close() end) 22 | end) --------------------------------------------------------------------------------