2019-09-17

Line Notify 發訊 with PHP


流程:
  1. 使用者必須先將 Line Notify 加入為好友
  2. 使用者瀏覽一個網頁,網頁中告知【點擊這裡】將您的帳號與 Line Notify 的本服務連結
  3. 瀏覽器導向 Line Notify 網站
  4. 使用者點擊後登入 Line 帳號並選擇要連結的聊天室或 1 對 1 聊天室
  5. Line Notify 網站 Call Back 回你的網站並交付 Access Token
  6. 使用該 Access Token 向 User Push Message
首先登入 Line Notify 網站 https://notify-bot.line.me/en/
點選右上角自己的帳號開啟下拉式選單,再點選 Manage registered services


點選 Add service


輸入相關資訊,這裡 Service logo 不重要,Line Notify 傳送訊息時並不會使用這個 Logo
而其中的 Callback URL 最為重要,必須為 https 連結,打錯就收不到 Call Back 了


輸入完畢按同意確認 => Add


系統告知請去信箱收確認信


點擊確認信中的連結驗證


完成驗證開啟服務


在 Manage registered services (service provider) 點擊該 Service


將 Client ID 與 Client Secret (點擊 Display 才能看到) 複製下來備用


以上完成準備工作,我們先跳過 Code 先講解 User 連結服務的流程
首先連到 index.html , 這裡只有一個按鈕可以按


按下連結跳轉到 Line Notify 網站並登入後,可選擇要連結的聊天室



選擇要連結的聊天室後按 Agree and connect


Line 網站會將 User 導回 Callback.php 網址 


User 的 Line Notify 聊天室同時會收到一則訊息表示已經連結成功



Callbackup.php 中會將 Line 網站傳回的資料 echo 出來,類似下面這樣
程式碼中已經包含驗證來源為 Line Notify 並確認 client_id 有相同
這是範例程式,你只需要 access token 就好,其他資訊可自行參考使用

Link ok!

Array ( [grant_type] => authorization_code [code] => M19l7xYmwpvTXLo4BLgbo2 [redirect_uri] => https://www.contoso.com/LineNotify/CallBack.php [client_id] => o1U3JBseW24qsyW6uomrMG [client_secret] => UYakzhkijjL4wNfrZ8Mb36yakear93eB9IvvAwI4iWq )

{"grant_type":"authorization_code","code":"M19l7xYmwpvTXLo4BLgbo2","redirect_uri":"https:\/\/www.contoso.com\/LineNotify\/CallBack.php","client_id":"o1U3JBseW24qsyW6uomrMG","client_secret":"UYakzhkijjL4wNfrZ8Mb36yakear93eB9IvvAwI4iWq"}

{"status":200,"message":"access_token is issued","access_token":"TzVNCQBFnIjcEGe8xvQ2L0tGgO2ZDldPJInbAJ7jH0m"}

access_token: TzVNCQBFnIjcEGe8xvQ2L0tGgO2ZDldPJInbAJ7jH0m

使用剛剛取得的 Access token 透過 Test.php 發送訊息


使用者收到訊息的情況:


需要注意的是 Line Notify 限制不能單獨發送圖片,必須有文字才能發圖
而經過測試,發送圖片的 imageThumbnail 與 imageFullsize 都用同一張圖即可
且都用 Fullsize 不縮圖的話 User 實際上收到訊息的縮圖會更清晰

更詳細的開發文件請參考 LINE Notify API Document



以下為程式碼

index.html
<!DOCTYPE html>
<html lang="tw">
    <head>
        <title></title>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <script>
        function oAuth2() {
            var URL = 'https://notify-bot.line.me/oauth/authorize?';
            URL += 'response_type=code';
            URL += '&client_id=o1U3JBseW24qsyW6uomrMG';
            URL += '&redirect_uri=https://www.contoso.com/LineNotify/CallBack.php';
            URL += '&scope=notify';
            URL += '&state=NO_STATE';
            URL += '&response_mode=form_post';
            window.location.href = URL;
        }
    </script>
    </head>
    <body>
        <button onclick="oAuth2();"> 連結到 LineNotify 按鈕 </button>
    </body>
</html>
Callback.php

<?php
if (isset($_POST['error'])) {
echo "error:" .$_POST['error'];
echo "<br>";
echo "error_description:" .$_POST['error_description'];
echo "<br>";
exit;
};

$Push_Content['grant_type'] = "authorization_code";
$Push_Content['code'] = $_POST['code'];
$Push_Content['redirect_uri'] = "https://www.contoso.com/LineNotify/CallBack.php";
$Push_Content['client_id'] = "o1U3JBseW24qsyW6uomrMG";
$Push_Content['client_secret'] = "UYakzhkijjL4wNfrZ8Mb36yakear93eB9IvvAwI4iWq";
// Auth Line Official Connect Step-1
$HTTP_Request_Header = getallheaders();
$PassCallBackCheck = 0;
if (isset($HTTP_Request_Header['Origin'])) {
if ($HTTP_Request_Header['Origin'] == "https://notify-bot.line.me") {
$PassCallBackCheck++;
};
}; if (isset($HTTP_Request_Header['Referer'])) {
$ExplodeReferer = explode("&",parse_url($HTTP_Request_Header['Referer'],PHP_URL_QUERY));
if (Count($ExplodeReferer) > 2) {
if ($ExplodeReferer[1] == "client_id=".$Push_Content['client_id']) {
$PassCallBackCheck++;
};
};
};
if ($PassCallBackCheck != 2) {
header('HTTP/1.1 403 Forbidden');
exit;
};
// Auth Line Official Connect Step-1

echo 'Link ok!<br><hr>';
print_r($Push_Content);
echo "<hr>";
echo json_encode($Push_Content);
echo "<hr>";
$ch = curl_init("https://notify-bot.line.me/oauth/token");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($Push_Content));
curl_setopt($ch, CURLOPT_HTTPHEADER, array(
'Content-Type: application/x-www-form-urlencoded'
));
$response_json_str = curl_exec($ch);
curl_close($ch);
echo $response_json_str.'<hr>';
        $response = json_decode($response_json_str, true);
        if (!isset($response['status']) || $response['status'] != 200 || !isset($response['access_token'])) {
            echo 'Request failed';
        } else if (preg_match('/[^a-zA-Z0-9]/u', $response['access_token'])) {
            echo 'Got wired access_token: '.$response['access_token']."<br>";
            echo 'http_response_header'.$http_response_header."<br>";
            echo 'response_json'.$response_json_str."<br>";
        } else {
            echo 'access_token: '.$response['access_token'];
        }
?>
Test.php

<?php
$access_token = array();
$access_token[]="TzVNCQBFnIjcEGe8xvQ2L0tGgO2ZDldPJInbAJ7jH0m";
$message="\r\n\rHello World!\r\n\r\n現在時刻: ".date('Y-m-d H:i:s');
$TargetCount = count($access_token);
$Push_Content['message'] = $message;
// $Push_Content['imageThumbnail'] = "https://i.imgur.com/ZxuJGHG.png";
// $Push_Content['imageFullsize'] = "https://i.imgur.com/ZxuJGHG.png";
// $Push_Content['stickerPackageId'] = "3";
// $Push_Content['stickerId'] = "180";
for ($i=0;$i<$TargetCount;$i++) {
$ch = curl_init("https://notify-api.line.me/api/notify");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($Push_Content));
curl_setopt($ch, CURLOPT_HTTPHEADER, array(
'Content-Type: application/x-www-form-urlencoded',
'Authorization: Bearer '.$access_token[$i]
));
$response_json_str = curl_exec($ch);
curl_close($ch);
echo $response_json_str."<br>\r\n";
// {"status":400,"message":"LINE Notify account doesn't join group which you want to send."}
// {"status":401,"message":"Invalid access token"}
// {"status":400,"message":"message: must not be empty"}
$response = json_decode($response_json_str, true);
print_r($response);
echo "<hr>";
if ( (!isset($response['status'])) || (!isset($response['message'])) ) {
echo "Request failed";
exit;
};
if ( ($response['status'] != 200) || ($response['message'] != 'ok') ) {
echo "Request failed";
exit;
};
if (!isset($response['access_token'])) {
$ch = curl_init("https://notify-api.line.me/api/status");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'GET');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($ch, CURLOPT_HTTPHEADER, array(
'Authorization: Bearer '.$access_token[$i]
));
$response_json_str = curl_exec($ch);
curl_close($ch);
echo $response_json_str."<hr>";
} else if (preg_match('/[^a-zA-Z0-9]/u', $response['access_token'])) {
echo 'Got wired access_token: '.$response['access_token']."<br>";
echo 'http_response_header'.$http_response_header."<br>";
echo 'response_json'.$response_json_str."<br>";
} else {
echo 'access_token: '.$response['access_token'];
}
usleep(6000); // microseconds * 1000 = miliseconds
};
?>







沒有留言:

張貼留言