Simple IoT Board用のIFTTTのMaker Channelに繋げるためのサンプルです。

Dependencies:   SimpleIoTBoardLib mbed

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers ifttt.cpp Source File

ifttt.cpp

00001 /* mbed Microcontroller Library
00002  * Copyright (c) 2006-2013 ARM Limited
00003  *
00004  * Licensed under the Apache License, Version 2.0 (the "License");
00005  * you may not use this file except in compliance with the License.
00006  * You may obtain a copy of the License at
00007  *
00008  *     http://www.apache.org/licenses/LICENSE-2.0
00009  *
00010  * Unless required by applicable law or agreed to in writing, software
00011  * distributed under the License is distributed on an "AS IS" BASIS,
00012  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00013  * See the License for the specific language governing permissions and
00014  * limitations under the License.
00015  */
00016 
00017 #include "mbed.h"
00018 #include "ifttt.h"
00019 //#include <string>
00020 #include "SoftSerialSendOnry.h"
00021 
00022 extern SoftSerialSendOnry pc;
00023 
00024 #if 0
00025 #define DBG(x, ...)  pc.printf("[IFTTT : DBG]"x" \t[%s,%d]\r\n", ##__VA_ARGS__,__FILE__,__LINE__);
00026 #define WARN(x, ...) pc.printf("[IFTTT : WARN]"x" \t[%s,%d]\r\n", ##__VA_ARGS__,__FILE__,__LINE__);
00027 #define ERR(x, ...)  pc.printf("[IFTTT : ERR]"x" \t[%s,%d]\r\n", ##__VA_ARGS__,__FILE__,__LINE__);
00028 #else
00029 #define DBG(x, ...) //wait_us(10);
00030 #define WARN(x, ...) //wait_us(10);
00031 #define ERR(x, ...)
00032 #endif
00033 
00034 #if 0
00035 #define INFO(x, ...) pc.printf("[IFTTT : INFO]"x" \r\n",##__VA_ARGS__);
00036 #else
00037 #define INFO(x, ...)
00038 #endif
00039 
00040 //
00041 // Initialize object with Event, Key, and valid socket.
00042 // TODO: accept hostname parameter / implement DNS lookup
00043 //
00044 IFTTT::IFTTT(const char * event, const char * key, TCPSocketConnection * s)
00045 {
00046     // Error Check
00047     if(sizeof(event) > IFTTT_MAX_SIZE_EVENTNAME) {
00048         ERR("Given event > IFTTT_MAX_SIZE_EVENTNAME, increase the max event string size in ifttt.h");
00049     }
00050     if(sizeof(key) > IFTTT_MAX_SIZE_SECRETKEY) {
00051         ERR("Given key > IFTTT_MAX_SIZE_SECRETKEY, increase the max secret key string size in ifttt.h");
00052     }
00053     // Copy event name and secret key into object instance
00054     strcpy(this->eventName,event);
00055     strcpy(this->secretKey,key);
00056 
00057     // Set up Socket
00058     if(NULL == s) {
00059         WARN("Given Socket Pointer is NULL, will try opening a socket.");
00060     }
00061     this->socket = s;
00062 
00063     // Set up Host / Port
00064     this->port = IFTTT_PORT;
00065     this->host = IFTTT_IP;
00066     
00067     // Initialize ingredient values to empty strings.
00068     v1 = "";
00069     v2 = "";
00070     v3 = "";
00071 }
00072 
00073 //
00074 // Add ingredients to be sent.
00075 //
00076 bool
00077 IFTTT::addIngredients( char * value1,  char * value2,  char * value3)
00078 {
00079     // update internal pointers. If variable not given then pass an empty string
00080     v1 = (NULL == value1)?"":value1;
00081     v2 = (NULL == value2)?"":value2;
00082     v3 = (NULL == value3)?"":value3;
00083     return true;
00084 }
00085 
00086 //
00087 // This function sends data to maker.ifttt.org via GET query commands
00088 // return true on sucess, false on fail
00089 //
00090 bool IFTTT::get()
00091 {
00092     // Connect to maker.ifttt.org
00093     int retry = 0;
00094     for(retry=0; retry<IFTTT_MAX_RETRY; retry++) {
00095         int ret = this->socket->connect(this->host, this->port);
00096         if(ret == 0) {
00097             DBG("Successfully Connected socket to host");
00098             break ;
00099         }
00100     }
00101     if(retry == IFTTT_MAX_RETRY) {
00102         this->socket->close();
00103         ERR("Could not connect socket to host\r\n");
00104         return false;
00105     }
00106 
00107     // Prep data to send
00108     // TODO: verify / modify data to be query string compliant (convert spaces to '+', convert non-alpha-numberic characters to the proper encoding... etc)
00109     char str[IFTTT_MAX_SIZE_STRING] = {0};
00110     sprintf(str, "GET /trigger/%s/with/key/%s/?value1=%s&value2=%s&value3=%s HTTP/1.1\r\nHost: maker.ifttt.com\r\n\r\n",eventName,secretKey,v1,v2,v3);
00111     DBG("String to send is:\n\r%s",str);
00112 
00113     // Send Data
00114     DBG("Sending GET data...");
00115     int check = 0;
00116     check = this->socket->send_all(str,sizeof(str));
00117     if(check) {
00118         DBG("Sent Sucessfully %d bytes",check);
00119     } else {
00120         ERR("Sending failed");
00121         return false;
00122     }
00123     DBG("Waiting on reply ... \r\n");
00124     int ret = this->socket->receive(str,50);
00125     str[ret]=0;
00126     DBG("Received String : %s",str);
00127     this->socket->close();
00128 
00129     return true;
00130 }
00131 
00132 //
00133 // This function sends JSON encoded data encoded in a POST packet, 
00134 //
00135 bool IFTTT::post()
00136 {
00137     // Connect to maker.ifttt.org
00138     int retry = 0;
00139     for(retry=0; retry<IFTTT_MAX_RETRY; retry++) {
00140         int ret = this->socket->connect(this->host, this->port);
00141         if(ret == 0) {
00142             DBG("Successfully Connected socket to host");
00143             break ;
00144         }
00145     }
00146     if(retry == IFTTT_MAX_RETRY) {
00147         this->socket->close();
00148         ERR("Could not connect socket to host\r\n");
00149         return false;
00150     }
00151 
00152     // Prep data to send, the Assembled POST packet should look like this
00153     //
00154     //
00155     //POST /trigger/<eventName>/with/key/<secretKey> HTTP/1.1
00156     //Host: maker.ifttt.com
00157     //Content-Length: <length of POST data>
00158     //Content-Type: application/json
00159     //
00160     //{"value1":"<v1>","value2":"<v2>","value3":"<v3>"}
00161     //
00162     //
00163     char str[IFTTT_MAX_SIZE_STRING] = {0};
00164     char header[100] = {0};
00165     sprintf(header, "POST /trigger/%s/with/key/%s HTTP/1.1\r\n",eventName,secretKey);
00166     const char * host = "Host: maker.ifttt.com\r\n";
00167     char contentLen[50] = {0};
00168     const char * contentType = "Content-Type: application/json\r\n\r\n";
00169     char valueData [150] = {0};
00170     sprintf(valueData,"{\"value1\":\"%s\",\"value2\":\"%s\",\"value3\":\"%s\"}\r\n",v1,v2,v3);
00171     sprintf(contentLen,"Content-Length: %d\r\n",strlen(valueData));
00172     sprintf(str,"%s%s%s%s%s",header,host,contentLen,contentType,valueData);
00173 
00174     DBG("String to send is:\n\r%s",str);
00175 
00176     // Send Data
00177     DBG("Sending POST data...");
00178     int check = 0;
00179     check = this->socket->send_all(str,strlen(str));
00180     if(check) {
00181         DBG("Sent Sucessfully %d bytes",check);
00182     } else {
00183         ERR("Sending failed");
00184         return false;
00185     }
00186     DBG("Waiting on reply ... \r\n");
00187     int ret = this->socket->receive(str,IFTTT_MAX_SIZE_STRING);
00188     str[ret]=0;
00189     DBG("Received String : %s",str);
00190     this->socket->close();
00191 
00192     return true;
00193 }
00194 
00195 //
00196 // Send trigger and any values associated to maker.ifttt.com
00197 // currently  unsecured (sends over HTTP, not https)
00198 //
00199 bool
00200 IFTTT::trigger(int triggerType)
00201 {
00202     int ret = 0;
00203     switch(triggerType) {
00204         case IFTTT_GET:
00205             DBG("Sending Data as GET request");
00206             ret = get();
00207             break;
00208         case IFTTT_POST:
00209             DBG("Sending Data as POST request");
00210             ret = post();
00211             break;
00212 
00213         default:
00214             WARN("Invalid type, defaulting to sending data as POST request");
00215             ret = post();
00216             break;
00217     }
00218     DBG("Sending Data return code : %d",ret);
00219     if(ret){
00220     INFO("Successfully triggered event: '%s' with v1='%s', v2='%s', v3='%s' !",eventName,v1,v2,v3);
00221     }
00222     return ret;
00223 }