In this post I’ll break down how to build a flow that uses the HTTP request node to PUT a file (a *.png image file in this case) into the unsecured file area on a groov EPIC – but this will also work with the secured file area and USB storage on EPICs and groov RIOs as well.
The two main sources for this are the groov Manage API Swagger page and the help tab of the HTTP request node:
The Manage API Swagger page tells us the "KEY"
should be "file"
, the FILE_CONTENTS
should be the file binary buffer, and "FILENAME"
is of course the filename. Along with that we need to set msg.headers
to have both "content-type"
and "apiKey"
properties.
The last part is the URL, again referring to the Swagger UI we can see the endpoint is "/api/v1/files/{area}/rpc/create-file/{areaPath}"
where {area}
should be ‘unsecured’, ‘secured’, or ‘usb’, and {areaPath}
is the folder and filename within that area.
For example to just create a file “hello.txt” directly in the unsecured file area of the localhost device, use the following URL:
https://localhost/manage/api/v1/files/unsecured/rpc/create-file/
hello.txt
To create a new folder or add to an existing folder, just include that in the {areaPath}
like this:
https://localhost/manage/api/v1/files/unsecured/rpc/create-file/
folder/hello.txt
All together, it ends up looking something like this, where I’m reading an image file into my flow, then writing it to the unsecured file area:
Using the following JavaScript code in the “set properties” function node:
msg.payload = {
"file": {
"value": msg.payload,
"options": {
"filename": msg.filename
}
}
}
msg.headers = {
"apiKey":"mR4VG3sRSrRJok4ZouNGJN7iNJQpfKER",
"Content-Type":"multipart/form-data"
}
msg.url = "https://localhost/manage/api/v1/files/unsecured/rpc/create-file/folder/image.png";
return msg;
One final note is that to make the HTTPS request you will need to enable the secure (SSL/TLS) connection option in the http request
node, which is covered in this forum post: Authenticating Opto API calls with HTTP request
If you have any questions about this, or end up modifying this or using it in a project, please drop a line in the thread below.
And as always, happy flowing!
Flow import JSON:
[{"id":"d57e4f633753da9d","type":"tab","label":"HTTP PUT Example","disabled":false,"info":""},{"id":"534f4bec03ec7ecc","type":"inject","z":"d57e4f633753da9d","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"","payloadType":"date","x":140,"y":60,"wires":[["e7f55d7be760072e"]]},{"id":"e7f55d7be760072e","type":"file in","z":"d57e4f633753da9d","name":"input.png","filename":"/home/dev/unsecured/input.png","format":"","chunk":false,"sendError":false,"encoding":"base64","allProps":false,"x":280,"y":60,"wires":[["b90a33f234962d78"]]},{"id":"8fde62bcb5a56053","type":"http request","z":"d57e4f633753da9d","name":"","method":"PUT","ret":"obj","paytoqs":"ignore","url":"","tls":"39d8eb96e6ac28c0","persist":false,"proxy":"","authType":"","credentials":{},"x":610,"y":60,"wires":[["7d6dcc5cabc9e65f"]]},{"id":"7d6dcc5cabc9e65f","type":"debug","z":"d57e4f633753da9d","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"true","targetType":"full","statusVal":"","statusType":"auto","x":750,"y":60,"wires":[]},{"id":"b90a33f234962d78","type":"function","z":"d57e4f633753da9d","name":"set properties","func":"msg.payload = {\n \"file\": {\n \"value\": msg.payload,\n \"options\": {\n \"filename\": msg.filename\n }\n }\n}\nmsg.headers = {\n \"apiKey\":\"mR4VG3sRSrRJok4ZouNGJN7iNJQpfKER\",\n \"Content-Type\":\"multipart/form-data\"\n}\nmsg.url = \"https://localhost/manage/api/v1/files/unsecured/rpc/create-file/folder/image.png\";\nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":440,"y":60,"wires":[["8fde62bcb5a56053"]]},{"id":"39d8eb96e6ac28c0","type":"tls-config","name":"","cert":"","key":"","ca":"","certname":"","keyname":"","caname":"","servername":"","verifyservercert":false,"alpnprotocol":""}]