Http method and body for REST endpoint

Hi

I would like to make a custom REST endpoint to send and receive json with HTTP commands over BridgeLibrary

my request

GET /api/led/13 HTTP/1.1
Host: 192.168.1.150
Content-Type: application/json

returns

{  "pin": 13, "light": "on" }

after adding a plain socket endpoint to index.lua

local api_socket_endpoint = make_entry({ "api"}, call("api_plain_socket"), nil)
  api_socket_endpoint.sysauth = rest_api_sysauth
  api_socket_endpoint.sysauth_authenticator = webpanel.sysauth_authenticator

and updating /etc/httpd.conf

A:/api:/cgi-bin/luci/api%s

and changing the api_plain_socket to add method

  sock:write(method)
  sock:write(" ")
  sock:write(params)
  sock:writeall("\r\n")

sketch

void process(YunClient client) {
	// read the command
	String httpCommand = client.readStringUntil(' ');

	String command = client.readStringUntil('/');

	Console.print("Command:");
	Console.print(httpCommand);
	Console.print(" api:");
	Console.println(command);

	// is "digital" command?
	if (command == "digital") {
		digitalCommand(client);
	}

	// is "analog" command?
	if (command == "analog") {
		analogCommand(client);
	}

	// is "mode" command?
	if (command == "mode") {
		modeCommand(client);
	}

	// is "api" command?
	if (command == "led") {
		ledCommand(httpCommand, client);
	}
}

JsonObject& prepareLedResponse(int pin, JsonBuffer& jsonBuffer) {
	JsonObject& root = jsonBuffer.createObject();

	root["pin"] = pin;
	root["light"] = digitalRead(pin) ? "on" : "off";

	return root;
}

void ledCommand(String httpCommand, YunClient client) {
	int pin, value;
	// Read led pin number
	pin = client.parseInt();

	Console.print("Pin:");
	Console.println(pin);

	StaticJsonBuffer<500> jsonBuffer;
	if (httpCommand == "GET")
	{
		JsonObject& json = prepareLedResponse(pin, jsonBuffer);
		writeResponse(client, json);
	}

	if (httpCommand == "PUT" || httpCommand == "POST")
	{
		String json = client.readString();
		Console.print("json:");
		Console.println(json);
	}

}

The problem is when using http method PUT

PUT /api/led/13 HTTP/1.1
Host: 192.168.1.150
Content-Type: application/json
Content-Length: 15
Cache-Control: no-cache

{"light": "on"}

i receive "Bad request" response

After some testing I found that simple endpoint (/api; /arduino) works only with GET and POST command.
Is there something missing in http request header ?
What config or lua file has to be changed to enable PUT and DELETE ?

I also did not manage to send http body to sketch using methods luci.http.content() or luci.http.source()
How to send http body (json) from index.lua to sketch over nixio socket ?

I am using Dragino Yun Shield on Arduino MEGA2560 with Dragino-v2 common-2.0.3

Best Regards and thanks
Rihard

Why not do all that web stuff in Python on the Linux side ?

...R

Thanks for replay

I did handle the request with cgi python to preserve route as http://arduino/api/ and not as http://arduino:1234/api,
and came to the similar "wall" that something handled my request prior of my python code.
I could post code and config after work. My python/linux skills are very :confused:

If I handle it with in some other http server on another port, how to transfer data to sketch ?

Best Regards
Rihard

You can use the Python Bottle web framework on a Yun.

...R

Here is something that should help

Beginner's Introduction to Yun Web Services
http://forum.arduino.cc/index.php?topic=315554.0