-
Notifications
You must be signed in to change notification settings - Fork 33
/
app.js
276 lines (232 loc) · 9.75 KB
/
app.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
/*
* 作者 : Chang Chun Shawn ( jcshawn.com )
* 程式名稱 : 加一 LINE 紀錄機器人
* 簡述 : 這是一個可以紀錄聊天室或群組傳「+1」訊息使用者的 LINE 機器人,將資料存放在 Google Sheet 中,基於 App Script 語法
* 授權: Apache 2.0
* 聯絡方式: contact@jcshawn.com
* 最新更新 : 2022 / 3 / 30
*/
function doPost(e) {
// LINE Messenging API Token
var CHANNEL_ACCESS_TOKEN = ''; // LINE Bot API Token
// 以 JSON 格式解析 User 端傳來的 e 資料
var msg = JSON.parse(e.postData.contents);
// for debugging
Logger.log(msg);
console.log(msg);
/*
* LINE API JSON 解析資訊
*
* replyToken : 一次性回覆 token
* user_id : 使用者 user id,查詢 username 用
* userMessage : 使用者訊息,用於判斷是否為預約關鍵字
* event_type : 訊息事件類型
*/
const replyToken = msg.events[0].replyToken;
const user_id = msg.events[0].source.userId;
const userMessage = msg.events[0].message.text;
const event_type = msg.events[0].source.type;
/*
* Google Sheet 資料表資訊設定
*
* 將 sheet_url 改成你的 Google sheet 網址
* 將 sheet_name 改成你的工作表名稱
*/
const sheet_url = 'https://docs.google.com/spreadsheets/d/******';
const sheet_name = 'reserve';
const SpreadSheet = SpreadsheetApp.openByUrl(sheet_url);
const reserve_list = SpreadSheet.getSheetByName(sheet_name);
/*
* 預約人數設定
*
* maxium_member : 正式預約人數上限
* waiting_start : 候補人數開始的欄位,無需修改
* waiting_member : 開放候補人數
*/
const maxium_member = 40;
const waiting_start = maxium_member+1;
const waiting_member = 3;
// 必要參數宣告
var current_hour = Utilities.formatDate(new Date(), "Asia/Taipei", "HH"); // 取得執行時的當下時間
var current_list_row = reserve_list.getLastRow(); // 取得工作表最後一欄( 直欄數 )
var reply_message = []; // 空白回覆訊息陣列,後期會加入 JSON
// 查詢傳訊者的 LINE 帳號名稱
function get_user_name() {
// 判斷為群組成員還是單一使用者
switch (event_type) {
case "user":
var nameurl = "https://api.line.me/v2/bot/profile/" + user_id;
break;
case "group":
var groupid = msg.events[0].source.groupId;
var nameurl = "https://api.line.me/v2/bot/group/" + groupid + "/member/" + user_id;
break;
}
try {
// 呼叫 LINE User Info API,以 user ID 取得該帳號的使用者名稱
var response = UrlFetchApp.fetch(nameurl, {
"method": "GET",
"headers": {
"Authorization": "Bearer " + CHANNEL_ACCESS_TOKEN,
"Content-Type": "application/json"
},
});
var namedata = JSON.parse(response);
var reserve_name = namedata.displayName;
}
catch {
reserve_name = "not avaliable";
}
return String(reserve_name)
}
// 回傳訊息給line 並傳送給使用者
function send_to_line() {
var url = 'https://api.line.me/v2/bot/message/reply';
UrlFetchApp.fetch(url, {
'headers': {
'Content-Type': 'application/json; charset=UTF-8',
'Authorization': 'Bearer ' + CHANNEL_ACCESS_TOKEN,
},
'method': 'post',
'payload': JSON.stringify({
'replyToken': replyToken,
'messages': reply_message,
}),
});
}
// 將輸入值 word 轉為 LINE 文字訊息格式之 JSON
function format_text_message(word) {
let text_json = [{
"type": "text",
"text": word
}]
return text_json;
}
var reserve_name = get_user_name();
if (typeof replyToken === 'undefined') {
return;
};
if (userMessage == "+1" | userMessage == "加一" | userMessage == "+1" | userMessage == "十1") {
// 檢查是否在晚上七點之前傳送
if (current_hour >= 0 & current_hour <= 19 | current_hour >= 21) {
if (current_list_row < maxium_member) {
reserve_list.getRange(current_list_row + 1, 1).setValue(reserve_name);
current_list_row = reserve_list.getLastRow();
reply_message = format_text_message(reserve_name + "成功預約 🙆,是第 " + current_list_row + " 位。" + "還有 " + (maxium_member - current_list_row) + " 位名額")
}
// 人數超過最大正式名額時,進入候補
else if (current_list_row >= maxium_member & current_list_row < (waiting_member + maxium_member)) {
reserve_name = "候補:" + reserve_name;
reserve_list.getRange(current_list_row + 1, 1).setValue(reserve_name);
reply_message = format_text_message("超過 40 人。" + reserve_name + " 為候補預約");
}
else {
reply_message = format_text_message("⚠️ 報名額滿!已達 " + maxium_member + "人");
}
}
else {
reply_message = format_text_message("現在不是報名時間喔 ~ ,請在 00:00 - 19:00 預約");
}
send_to_line()
}
else if (userMessage == "+2" | userMessage == "加二" | userMessage == "十2") {
if (current_hour >= 0 & current_hour <= 19) {
if (current_list_row < maxium_member) {
let name_array = [[reserve_name], [reserve_name]];
reserve_list.getRange(current_list_row + 1, 1, 2, 1).setValues(name_array);
current_list_row = current_list_row + 2;
reply_message = format_text_message(reserve_name + "成功預約兩位 🙆" + "還有" + (maxium_member - current_list_row) + "位名額");
}
else if (current_list_row >= maxium_member & current_list_row < maxium_member + 2) { // +2 時不給候補
let waiting_list_name = "候補:" + reserve_name;
let waiting_names_array = [[waiting_list_name], [waiting_list_name]];
reserve_list.getRange(current_list_row + 1, 1, 2, 1).setValues(waiting_names_array);
reply_message = format_text_message(reserve_name + "預約兩位候補");
}
// 名單超過 40 人時不新增,回傳通知訊息
else {
reply_message = format_text_message("⚠️ 報名額滿!已達 40 人");
}
}
// 非報名時間的訊息通知
else {
reply_message = format_text_message("現在不是報名時間喔 ~ ,請在 00:00 - 19:00 預約");
}
send_to_line();
}
else if (userMessage == "-1" | userMessage == "減一") {
let all_members = reserve_list.getRange(1, 1, current_list_row, 1).getValues().flat();
let leaving_member_index = all_members.indexOf(reserve_name);
if (leaving_member_index != -1) {
let checking_range = leaving_member_index + 1;
var waiting_add = reserve_list.getRange(waiting_start, 1).getValue();
reserve_list.getRange(checking_range, 1).clearContent();
current_list_row = reserve_list.getLastRow();
move_all_data();
var state = reserve_name + "已退出預約";
}
else {
var state = "您尚未報名,不用減一"
}
if (waiting_add != "") {
reply_message = [{
"type": "text",
"text": state
}, {
"type": "text",
"text": waiting_add + "候補進入上課名單"
}]
}
else {
reply_message = format_text_message(state);
}
// 將取消報名者下方所有資料向上移動
function move_all_data() {
let all_members = reserve_list.getRange(1, 1, current_list_row, 1).getValues().flat();
let spaced_cell_index = all_members.indexOf("");
let modify_range = current_list_row - spaced_cell_index - 1;
let tmp_data = reserve_list.getRange(spaced_cell_index + 2, 1, modify_range, 1).getValues();
reserve_list.getRange(spaced_cell_index + 1, 1, modify_range, 1).setValues(tmp_data);
reserve_list.getRange(current_list_row, 1).clearContent();
}
send_to_line();
}
else if (userMessage == "test") {
if (current_hour >= 0 & current_hour <= 19) {
reply_message = [{
"type": "text",
"text": "Test"
}]
}
send_to_line();
}
else if (userMessage == "報名人數" | userMessage == "名單") {
var ready_namelist = "【 報名名單 】\n";
var all_members = reserve_list.getRange(1, 1, current_list_row, 1).getValues().flat();
for (var x = 0; x <= all_members.length-1; x++) {
ready_namelist = ready_namelist + "\n" + all_members[x];
}
reply_message = [
{
"type": "text",
"text": "共有 " + current_list_row + " 位同學報名 ✋"
},
{
"type": "text",
"text": ready_namelist
}]
send_to_line();
}
else if (userMessage == "貼圖") {
reply_message = [{
"type": "sticker",
"packageId": "6136",
"stickerId": "10551378"
}]
send_to_line();
}
// 其他非關鍵字的訊息則不回應( 避免干擾群組聊天室 )
else {
console.log("else here,nothing will happen.")
}
}