yeelink在PX2上的運用(遠程控制)

首先介紹yeelink,這嘛,是一個開放的雲服務器平臺,你們均可以去註冊一個本身的帳號,而後就可使用它的服務器就是,只要你的設備可以聯網,不管你人在哪裏,就能從網絡上控制你的設備,而它就提供各類API接口,咱們只要熟悉一點tcp的編程咱們就能夠簡單使用了,另外值得注意的一點是,yeelink也能夠在微信公衆號上查看,修改咱們的設備,十分簡便。php

官網是這個,http://www.yeelink.net/ ,註冊完以後咱們進入用戶中心就能夠看到這樣的界面編程

  

而在帳戶中找到咱們的apikey,這個值在編程時會用到,另外在設備管理中,咱們能夠建立本身的設備,選擇在設備裏建立個本身的傳感器,可選擇數值型和開關型等,以下,能夠在傳感器的這個位置,看到設備的ID,和傳感器的ID,這兩個值也是須要的api

  

而後咱們先測試下通訊是否能成功,可使用網絡助手做爲一個服務器端,做爲一個設備向yeelink服務器發送命令服務器

下面兩個命令中一個是發送數值到服務器,一個是從服務器獲取數值,通訊成功的效果以下,若通訊失敗的話,能夠嘗試從新獲取下apikey的值,在帳戶那邊能夠從新獲取。(記得將下面的ID值和apikey值改成本身的)微信

    

而後咱們就能夠寫個tcp通訊程序,而且將設備的開啓加入其中了,樓主這裏就簡單用個GPIO口作個例子,若是想的話,咱們也能夠寫個溫度檢測的程序,而後經過微信實時檢測家裏或某個地方的溫度。網絡

程序以下socket

#include<stdlib.h>tcp

#include<stdio.h>工具

#include<errno.h>測試

#include<netdb.h>

#include<string.h>

#include<sys/types.h>

#include<netinet/in.h>

#include<sys/socket.h>

#include <fcntl.h>

#include<string.h>

#define portnumber 80//yeelink的服務器端口

#define DEVICE_NAME     "/dev/rkpx2_GPIO"//gpio的設備,提供的kernel已包含,裏面定義裏gpio4的1234四個引腳,這裏用到1引腳

int main(int argc,char *argv[])

{         

    int sockfd//tcp進程號

    int fd//gpio的設備號

    int recdata//收到的數據長度

    char *addr//一個字符型指針,用來找數據value的位置,後面的值便是網站上按鍵的值

    int offset//value的長度,以便找到按鍵值

    char *yeelink//yeelink服務器ip地址

    char recv_data[1024]//收到數據的內存

    char flag//按鍵值

    yeelink="42.96.164.52"

    struct sockaddr_in server_addr

    struct sockaddr_in cilent_addr

    char send_data1[300] = "GET /v1.0/device/××××××××/sensor/×××××××/datapoints HTTP/1.1\r\nHost: api.yeelink.net\r\nContent-Length: 11\r\nU-ApiKey:××××××××××××(這裏請用本身的APIKEY代替包括前面的ID)\r\n\r\n{\"value\":0}\r\n" /* 發送用到的數據 */

    struct hostent *host

        fprintf(stderr,"start")

    while(1){//循環起來,每隔5s讀一次按鍵值

            if((host=gethostbyname(yeelink))==NULL)//獲取服務器地址

            {fprintf(stderr,"gethostname Error:%s\a\n",strerror(errno))

                exit(1)

            }

        if((sockfd=socket(AF_INET,SOCK_STREAM,0))==-1)//創建socket

            {

            fprintf(stderr,"socketError:%s\a\n")

                exit(1)}

        bzero(&server_addr ,sizeof(server_addr))//堆棧初始化,所有化爲0

        server_addr.sin_family=AF_INET

        server_addr.sin_port=htons(portnumber)

        server_addr.sin_addr=*((struct in_addr *)host->h_addr)

            if(connect(sockfd,(struct sockaddr*)(&server_addr),sizeof( struct sockaddr))==-1)//申請鏈接

                {

                fprintf(stderr,"connect Error:%s\a\n",strerror(errno))

                exit(1)

            } 

        send(sockfd,send_data1,sizeof(send_data1),0)//將http文件頭髮過去

         recdata = recv(sockfd, recv_data, sizeof(recv_data), 0)//接受服務器返回的數值

        recv_data[recdata]=' '//加上結束符        

        addr = strstr(recv_data,"\"value\"")//在接受到的數據中找到按鍵值的位置,即value,收到數據的樣式以下{「value」:key}

        offset=strlen("\"value\":")//判斷value的長度,

        flag = *(addr + offset) //找到按鍵的值,賦值給flag

        fprintf(stderr,"the value is %c \n")

        close(sockfd)//關閉socket,記住,這裏得提早關閉,否則會發生段錯誤。

        fd=open(DEVICE_NAME,O_RDWR)//打開GPIO設備

            if (fd==-1){

        fprintf(stderr,"open devices %s error\n",DEVICE_NAME)

    }

        if(flag=='1'){//判斷flag的值,而後執行相應的操做

        ioctl(fd,1)

        fprintf(stderr,"the value is %c \n",flag)

        }

        else

        {

        ioctl(fd,0)

        fprintf(stderr,"the value is %c \n",flag)

}      

        fprintf(stderr,"please wait 5s\n")

        sleep(10)//延時10s,讓實驗效果更明顯

        close(fd)

}

        exit(0)

}

由於是用GPIO口的,用的是板上的GPIO4_1樓主也很差加圖片,因此效果就不演示了,可是已驗證可行,樓主用的使用的kernel和程序文件以下,都放壓縮包裏了,有興趣能夠下載過去研究下,壓縮包中的文件一個是kernel,這個是支持VGA顯示的,並且包含了樓主的一個GPIO驅動,在程序中會用到,一個是源碼,咱們能夠在源碼包中編譯出可執行文件,最後一個是可執行文件,能夠用adb工具push進板中,而後執行起來就能夠了,固然,這裏是樓主本身的賬號,ID ,APIKEY都是樓主賬號的,因此大家想用的話,就得修改下,只須要在程序中改這三個值便行,而後就可使用本身賬號的設備 控制,

 yeelink.zip 

測試時的部分圖片以下,按那個開關會改變GPIO端口的值,而改變端口時,debug口也會有提示,這裏也會有提示,你們可使用這個端口電平的改變,控制燈,蜂鳴器之類的。

       

如今說說程序中樓主遇到的幾個錯誤。

1.發送過去的http文件頭,在{"value":**}的前面要有兩個回車,這個別漏了,這是格式要求,漏了就無法正常把值放到服務器了

2.獲取服務器的值的時候,咱們得在服務器中的值處理,由於他發過來的值時沒有結束符的,因此咱們得手動加上結束符。

相關文章
相關標籤/搜索