diff --git a/main.php b/main.php index 2a4bd12..c12cea8 100644 --- a/main.php +++ b/main.php @@ -26,13 +26,36 @@ $mc = new Memcached(); $mc->addServer('localhost', MEMCACHED_PORT) or error("Something is wrong connecting to memcached daemon"); -// Accept only messages from a private chat -if(!isset($row->message->text)) { - if (DEBUG) warning("Message from a not acceptable source"); - die(); -} +// Structure of managed telegram messages +/* + * **Generic message** + * $row + * |_ message § Message + * |_ chat § chat + * |_ id (chatID) § integer + * |_ username (if set - user name for private chat, else channel or group name) § string + * |_ ...not relevant things... + * |_ from § User + * |_ id (userID) § integer + * |_ username (if set - user name) § string + * |_ .... + * |_ forward_from § User + * |_ forward_from_chat § Chat + * |_ text § string (message_text) + * |_ photo, location, video + * + * **Callback Query** + * $row + * |_ callback_query + * |_ id § integer + * |_ from § User + * |_ message § Message + * |_ inline_message_id § integer (inlineID) + * |_ ... + */ + // HANDLE A CALLBACK -elseif (isset ($row->callback_query)) { +if (isset ($row->callback_query)) { $chatID = $row->callback_query->message->chat->id; // Check if it was thrown by admitted users @@ -56,281 +79,544 @@ elseif (isset ($row->callback_query)) { if (DEBUG) warning("That's an old callback!"); die(); } -} -// HANDLE A COMMON MESSAGE (text/commands/keyboard) -else { - // throw away photos, documents and stickers (fixit) - if(isset($row->message->sticker) or isset($row->message->document)) { - // sto username si potrebbe quasi quasi estrapolare e mettere in una variabile decente - error("Qualcheduno (".$row->message->from->username.") ha mandato una cosa non supportata"); - } - // Load variables - $chatID = $row->message->chat->id; - - - // Check if it was thrown by admitted users - in_array($row->message->from->username, BOT_ALLOWED_USERS) or not_authorized($chatID); - - -} - -// Finally, check actual state and do things -$status = $mc->get($chatID.MC_STATUS); - if (!$status) { - $mc->set($chatID.MC_STATUS, STATE_IDLE) or die(); // set status or force it to STATE_IDLE - $status = STATE_IDLE; - } -if (DEBUG) info("Starting from status $status"); - -// ricordati di schiantare quando ricevi un messaggio invece di una callback - -switch ($status) { - case STATE_IDLE: - // In this state are not accepted callback requests - if (isset($callback_data)) { - switch ($callback_data){ - case MSG_DELETE: - $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); - $IDdelete = $mc->get($chatID.MC_DELETE_SCHEDULED_ID); - $sql->query("DELETE FROM ".MYSQL_TABLE." WHERE ID=$IDdelete") - or error("Can't make the query, SQL error ".$sql->error); - $sql->close(); - - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=Rimosso correttamente"; - file_get_contents($url); - die(); - break; - case '>': - $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); - $numbers = $sql->query("SELECT COUNT(*) FROM ".MYSQL_TABLE); - $numbers = $numbers->fetch_array()[0]; - info("Number of pages: $numbers"); - $offset = $mc->get($chatID.MC_LIST_NUMBER); - // gestire meglio qui - $offset++; - break; - case '<': - $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); - $numbers = $sql->query("SELECT COUNT(*) FROM ".MYSQL_TABLE); - $numbers = $numbers->fetch_array()[0]; - info("Number of pages: $numbers"); - $offset = $mc->get($chatID.MC_LIST_NUMBER); - // gestire meglio qui - $offset--; - break; - default: - if (DEBUG) warning("Callback request is not accepted in status $status"); - die(); - } - - $query = $sql->query("SELECT DATE_FORMAT(DateTime,'%d/%m/%Y ore %H') as DateTime,Text,Author,ID FROM ".MYSQL_TABLE." - ORDER BY DateTime ASC LIMIT 1 OFFSET $offset") or error("Can't make the query, SQL error ".$sql->error); - - //while($row = $query->fetch_assoc()) { - $row = $query->fetch_assoc(); - $mc->set($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']) - or $mc->replace($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']); - //~ $query = API_URL . API_TOKEN . '/forwardMessage?' . - //~ 'chat_id=' . urlencode($chatID) . - //~ '&from_chat_id=' . urlencode($row['ChatID']) . - //~ '&message_id=' . urlencode($row['MessageID']); - //~ $answer = file_get_contents($query); - //~ $answer = json_decode($answer); - $sql->close(); - - $container = array( - array( - array( - "text" => $row['DateTime'], - "callback_data" => "null" - ))); - - $container[] = array( - $offset > 0? - array( - "text" => "<", - "callback_data" => "<" - ) - : - array( - "text" => " ", - "callback_data" => "null" - ), - array( - "text" => "$EMOJI_THUMBSDOWN Canc", - "callback_data" => MSG_DELETE - ), - $offset < $numbers-1 ? - array( - "text" => ">", - "callback_data" => ">" - ) - : - array( - "text" => " ", - "callback_data" => "null" - ) - ); - - $resp = array( - "inline_keyboard" => $container); - $reply = json_encode($resp); - - $text="$row[Text]\n_$row[Author]_"; // NOME CANALE ".API_CHANNEL_ID."?"; - - $query = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID. - "&text=".urlencode($text). - "&parse_mode=".urlencode("Markdown"). - "&reply_markup=".$reply; - $answer = file_get_contents($query); - $answer = json_decode($answer); - - $mc->set($chatID.MC_LIST_NUMBER, $offset) - or $mc->replace($chatID.MC_LIST_NUMBER, $offset); - - die(); + // Finally, check actual state and do things + $status = $mc->get($chatID.MC_STATUS); + if (!$status) { + $mc->set($chatID.MC_STATUS, STATE_IDLE) or die(); // set status or force it to STATE_IDLE + $status = STATE_IDLE; } - // qui ci metterei un else - // Search for a command - if (($command = getCommand($row->message)) != null) { - info("Command received: $command[command] with options $command[options]"); - - switch ($command['command']) { - case '/help': - $resp = array("remove_keyboard" => true); - $resp = json_encode($resp); - - $query = API_URL . API_TOKEN . '/sendmessage?' . - 'chat_id=' . urlencode($chatID) . - '&text='.urlencode($WELCOME_MESSAGE). - '&reply_markup='.$resp; - file_get_contents($query); - break; - - case '/edit': - //~ $text = "Invio effettuato correttamente"; - //~ $url = API_URL.API_TOKEN."/deleteMessage?chat_id=".($chatID). - //~ "&message_id=2551"; - //~ file_get_contents($url); - break; - - case '/list': - //~ $dateID = date('Y-n-j G:*'); - - //~ $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); - //~ $query = $sql->query("SELECT DateTime,ChatID,MessageID FROM ".MYSQL_TABLE." WHERE DateTime>='$dateID' - //~ ORDER BY DateTime ASC LIMIT 10") or error("Can't make the query, SQL error ".$sql->error); - - //~ $text = "Prossimi 10 messaggi programmati"; - //~ $i = 1; - //~ while($row = $query->fetch_assoc()) { - //~ $text .= "\n".$i." - ". $row['DateTime']; - //~ $i++; - //~ } - //~ $text .= "\nFunzione in miglioramento"; - //~ $query = API_URL . API_TOKEN . '/sendMessage?' . - //~ 'chat_id=' . urlencode($chatID) . - //~ '&text=' . urlencode($text); - //~ $sql->close(); - //~ file_get_contents($query); - - //~ break; - - // yusdgfdsjf - - //~ $dateID = date('Y-n-j G:*'); - - $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); - $numbers = $sql->query("SELECT COUNT(*) FROM ".MYSQL_TABLE); - $numbers = $numbers->fetch_array()[0]; - if ($numbers == 0) { - $query = API_URL.API_TOKEN."/sendmessage?chat_id=".($chatID). - "&text=Nessun messaggio programmato"; - $answer = file_get_contents($query); + if (DEBUG) info("Starting from status $status"); + + + // Callback state machine + switch ($status) { + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * entering STATE_IDLE - callback * + * you can: list and delete messages given by /list * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + case STATE_IDLE: + switch ($callback_data){ + case MSG_DELETE: + $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); + $IDdelete = $mc->get($chatID.MC_DELETE_SCHEDULED_ID); + $sql->query("DELETE FROM ".MYSQL_TABLE." WHERE ID=$IDdelete") + or error("Can't make the query, SQL error ".$sql->error); + $sql->close(); + + editMessageText($chatID, $inlineID, "Rimosso correttamente"); + + break; + case '>': + $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); + $numbers = $sql->query("SELECT COUNT(*) FROM ".MYSQL_TABLE); + $numbers = $numbers->fetch_array()[0]; + info("Number of pages: $numbers"); + $offset = $mc->get($chatID.MC_LIST_NUMBER); + // gestire meglio qui + $offset++; + break; + case '<': + $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); + $numbers = $sql->query("SELECT COUNT(*) FROM ".MYSQL_TABLE); + $numbers = $numbers->fetch_array()[0]; + info("Number of pages: $numbers"); + $offset = $mc->get($chatID.MC_LIST_NUMBER); + // gestire meglio qui + $offset--; + break; + default: + if (DEBUG) warning("Callback request is not accepted in status $status"); die(); } $query = $sql->query("SELECT DATE_FORMAT(DateTime,'%d/%m/%Y ore %H') as DateTime,Text,Author,ID FROM ".MYSQL_TABLE." - ORDER BY DateTime ASC LIMIT 1") or error("Can't make the query, SQL error ".$sql->error); + ORDER BY DateTime ASC LIMIT 1 OFFSET $offset") or error("Can't make the query, SQL error ".$sql->error); + + //while($row = $query->fetch_assoc()) { + $row = $query->fetch_assoc(); + $mc->set($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']) + or $mc->replace($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']); + //~ $query = API_URL . API_TOKEN . '/forwardMessage?' . + //~ 'chat_id=' . urlencode($chatID) . + //~ '&from_chat_id=' . urlencode($row['ChatID']) . + //~ '&message_id=' . urlencode($row['MessageID']); + //~ $answer = file_get_contents($query); + //~ $answer = json_decode($answer); + $sql->close(); + + $container = array( + array( + array( + "text" => $row['DateTime'], + "callback_data" => "null" + ))); + + $container[] = array( + $offset > 0? + array( + "text" => "<", + "callback_data" => "<" + ) + : + array( + "text" => " ", + "callback_data" => "null" + ), + array( + "text" => "$EMOJI_THUMBSDOWN Canc", + "callback_data" => MSG_DELETE + ), + $offset < $numbers-1 ? + array( + "text" => ">", + "callback_data" => ">" + ) + : + array( + "text" => " ", + "callback_data" => "null" + ) + ); + + $resp = array( + "inline_keyboard" => $container); + $reply = json_encode($resp); + + $text="$row[Text]\n_$row[Author]_"; // NOME CANALE ".API_CHANNEL_ID."?"; + + //~ $query = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID. + //~ "&text=".urlencode($text). + //~ "&parse_mode=".urlencode("Markdown"). + //~ "&reply_markup=".$reply; + //~ $answer = file_get_contents($query); + $answer = editMessageText($chatID, $inlineID, $text, "Markdown", false, $reply); + $answer = json_decode($answer); - //while($row = $query->fetch_assoc()) { - $row = $query->fetch_assoc(); - $mc->set($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']) - or $mc->replace($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']);; - //~ $query = API_URL . API_TOKEN . '/forwardMessage?' . - //~ 'chat_id=' . urlencode($chatID) . - //~ '&from_chat_id=' . urlencode($row['ChatID']) . - //~ '&message_id=' . urlencode($row['MessageID']); - //~ $answer = file_get_contents($query); - //~ $answer = json_decode($answer); - $sql->close(); + $mc->set($chatID.MC_LIST_NUMBER, $offset) + or $mc->replace($chatID.MC_LIST_NUMBER, $offset); + + die(); + break; + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * END STATE_IDLE + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * entering STATE_MSG_ANSWER - callback + * you can: (after you sent a message) choose if forward to + * channel or schedule it + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + + case STATE_MSG_ANSWER: // only accessible by callback + + /////// spostare di là + if (!(isset($callback_data))) { + //$mc->replace($chatID.MC_STATUS, STATE_IDLE); + wrong_action($chatID); + die(); + } + + switch ($callback_data) { + case MSG_YES: + // forward previously sent message + // set status? + $mc->replace($chatID.MC_STATUS, STATE_IDLE) + or error("Something is wrong with memcached"); + $msg = $mc->get($chatID.MC_FORWARD_MSG) + or error("Can't forward message\n"); - //$mc->set($chatID.MC_FW_EDIT, $answer->result->message_id) - // or $mc->replace($chatID.MC_FW_EDIT, $answer->result->message_id); - $container = array( - array( - array( - "text" => $row['DateTime'], - "callback_data" => "null" - ))); + + //~ $query = API_URL . API_TOKEN . '/sendmessage?' . + //~ 'chat_id=' . urlencode(API_CHANNEL_ID) . + //~ '&text='.urlencode($msg->message->text."\n_".$msg->message->chat->username."_"). + //~ "&parse_mode=".urlencode("Markdown"); //bah, un isset un ce lo vedrei male + //~ $result = file_get_contents($query); + if (isset($msg->message->text)) { + $result = sendMessage(API_CHANNEL_ID, + $msg->message->text."\n_".$msg->message->chat->username."_", + "Markdown"); + if(DEBUG) botlog("[LOG] $result\n"); + } + elseif (isset($msg->message->photo)) { + sendPhoto(API_CHANNEL_ID,$msg->message->photo[0]->file_id, + isset($msg->message->caption) ? $msg->message->caption : null); + } - $container[] = array( - array( - "text" => " ", - "callback_data" => "null" - ), - array( - "text" => "$EMOJI_THUMBSDOWN Canc", - "callback_data" => MSG_DELETE - ), - $numbers > 1 ? - array( - "text" => ">", - "callback_data" => ">" - ) - : - array( - "text" => " ", - "callback_data" => "null" - ) + // Remove kbd + $text = "Invio effettuato correttamente"; + editMessageText($chatID, $inlineID, $text); + //~ $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID . + //~ "&text=".urlencode($text); + //~ file_get_contents($url); + break; + + case MSG_NO: + $status = $mc->replace($chatID.MC_STATUS, STATE_IDLE) + or error("Something is wrong with memcached"); + + // destroy saved message? + $text = "Invio annullato correttamente"; + editMessageText($chatID, $inlineID, $text); + //~ $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID . + //~ "&text=".urlencode($text); + //~ file_get_contents($url); + break; + + case MSG_SCHEDULE: + // == from here can be put in a function == + $status = $mc->replace($chatID.MC_STATUS, STATE_WAIT_DATE) or die(); + $currentTab = array( + 'month' => date('n'), + 'year' => date('Y'), + 'day' => null ); - $resp = array( - "inline_keyboard" => $container); - $reply = json_encode($resp); - - $text="$row[Text]\n_$row[Author]_"; // NOME CANALE ".API_CHANNEL_ID."?"; - - $query = API_URL.API_TOKEN."/sendmessage?chat_id=".($chatID). - "&text=".urlencode($text). - "&parse_mode=".urlencode("Markdown"). - "&reply_markup=".$reply; - $answer = file_get_contents($query); - $answer = json_decode($answer); + $container = getCalendarTab($currentTab['month'], $currentTab['year']); - $mc->set($chatID.MC_INLINE_ID, $answer->result->message_id) - or $mc->replace($chatID.MC_INLINE_ID, $answer->result->message_id); - - $mc->set($chatID.MC_LIST_NUMBER, 0) - or $mc->replace($chatID.MC_LIST_NUMBER, 0); - break; - - default: - warning("$command[command] is not a valid command"); + $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) or die (); + + $container = array( + "inline_keyboard" => $container); + + $text="Quando vuoi inviare il messaggio?"; + $reply = json_encode($container); + + //~ $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID . + //~ "&text=".urlencode($text). + //~ "&reply_markup=".$reply; + editMessageText($chatID, $inlineID, $text, "Markdown", false, $reply); + + //~ file_get_contents($url); + + $mc->set($chatID.MC_INLINE_ID, $inlineID) or $mc->replace($chatID.MC_INLINE_ID, $inlineID) + or error("Something is wrong with memcached"); + // == end == + break; } - } - else { // not a command (pure text) - // you probably want to forward a message? - $mc->set($chatID.MC_FORWARD_MSG, $row) - or $mc->replace($chatID.MC_FORWARD_MSG, $row) + break; + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * END STATE_MSG_ANSWER + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * entering STATE_WAIT_DATE - callback + * you can: choose the date of scheduled message(s) + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + case STATE_WAIT_DATE: + $currentTab = $mc->get($chatID.MC_DATE_MSG) or error("Something is wrong with memcached"); - // SetUp inline messages (OK, NO, SCHEDULE) - $container[] = array( + // two cases: change page or confirm date + if ($callback_data == '>') { + // add 1 to month + if ($currentTab['month'] < 12) + $currentTab['month'] +=1; + else { + $currentTab['month'] = 1; + $currentTab['year'] +=1; + } + $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) + or error("Something is wrong with memcached"); + + $text = "Il calendario del ".$currentTab['month']."-".$currentTab['year']; + + // get new inline container + } + elseif ($callback_data == '<') { + if ($currentTab['month'] > 1) + $currentTab['month'] -=1; + else { + $currentTab['month'] = 12; + $currentTab['year'] -=1; + } + $text = "Il calendario del ".$currentTab['month']."-".$currentTab['year']; + + $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) + or error("Something is wrong with memcached"); + } + elseif ($callback_data == 'null') { + // not a valid button (like week days buttons) + die(); + } + elseif ($callback_data == MSG_ABORT) { + $text = "Invio annullato correttamente"; + $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + "&message_id=".$inlineID . + "&text=".urlencode($text); + file_get_contents($url); + $mc->replace($chatID.MC_STATUS, STATE_IDLE) or die(); + die(); + } + else { + // read current day, verify it and then change state + if (!$callback_data = intval($callback_data)) + error("Not a numerical day, how you did it?!?"); + $currentTab['day'] = $callback_data; + $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) or die ("Failed to save data at Memcached server"); + + // Display time inline keyboard + $container = array(); + $riga = array(); + + $firstHour = date('Ynj') == $currentTab['year'].$currentTab['month'].$currentTab['day']? + date('G')+1 : 8; + + for ($i = 8; $i <= 21; $i++) { + if ($i < $firstHour) { + $riga[] = array( + "text" => " ", + "callback_data" => "null" + ); + } + else { + $riga[] = array( + "text" => "$i".":00", + "callback_data" => "$i" + ); + } + + if ($i == 14) { + $container[] = $riga; + $riga = array(); + } + } + $container[] = $riga; + + $container[] = array(array( + "text" => "$EMOJI_X Annulla", + "callback_data" => MSG_ABORT + )); + + $container = array( + "inline_keyboard" => $container); + + $text="A che ora vuoi inviare il messaggio?"; + $reply = json_encode($container); + + //~ $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID . + //~ "&text=".urlencode($text)."&reply_markup=".$reply; + //~ file_get_contents($url); + + editMessageText($chatID, $inlineID, $text, "Markdown", false, $reply); + + $mc->replace($chatID.MC_STATUS, STATE_WAIT_TIME) or die(); + break; + } + + // If answer is < or > remain in current state and update calendar + $container = getCalendarTab($currentTab['month'], $currentTab['year']); + + $resp = array( + "inline_keyboard" => $container); + + $reply = json_encode($resp); + + //~ $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID . + //~ "&text=".urlencode($text)."&reply_markup=".$reply; + //~ file_get_contents($url); + editMessageText($chatID, $inlineID, $text, "Markdown", false, $reply); + + $mc->set($chatID.MC_INLINE_ID, $inlineID) or $mc->replace($chatID.MC_INLINE_ID, $inlineID); + + break; + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * END STATE_WAIT_DATE + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * entering STATE_WAIT_TIME - callback + * you can: choose the time of scheduled message(s) + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + case STATE_WAIT_TIME: + $mc->replace($chatID.MC_STATUS, STATE_IDLE); + if ($callback_data == MSG_ABORT) { + $text = "Invio annullato correttamente"; + $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + "&message_id=".$inlineID . + "&text=".urlencode($text); + file_get_contents($url); + $mc->replace($chatID.MC_STATUS, STATE_IDLE) or die(); + die(); + } + elseif (!$time = intval($callback_data)) { + if (DEBUG) botlog("[EE] Not a numeric time\n"); + die(); + } + + $currentTab = $mc->get($chatID.MC_DATE_MSG); + $msg = $mc->get($chatID.MC_FORWARD_MSG); + + // add to database (mysql) + $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); + // Build up mysql query + $value = "("; + $value .= $msg->message->message_id; + $value .= ","; + $value .= $msg->message->chat->id; + $value .= ","; + $value .= "'".$currentTab['year'].'-'; + $value .= $currentTab['month'].'-'; + $value .= $currentTab['day'].' '; + $value .= $callback_data.":00:00'"; + $value .= ","; + $value .= "'".$sql->escape_string($msg->message->text)."'"; + $value .= ","; + $value .= "'".$sql->escape_string($msg->message->from->username)."'"; // andrebbe fatto un isset, vabbé + $value .= ");"; + + info("Saving post in ".MYSQL_TABLE.", scheduled date: ".$value); + + + $query = $sql->query("INSERT INTO ".MYSQL_TABLE." (MessageID,ChatID,DateTime,Text,Author) VALUE ".$value) + or error("Can't make the query, SQL error ".$sql->error); + $sql->close(); + + $text = "Programmazione avvenuta con successo"; + + //~ $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). + //~ "&message_id=".$inlineID . + //~ "&text=".urlencode($text); + //~ file_get_contents($url); + editMessageText($chatID, $inlineID, $text); + + break; + } + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * END STATE_WAIT_TIME + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ +} + + +// HANDLE A COMMON MESSAGE (text/commands/photos...) +elseif (isset($row->message)) { + // Load variables + $chatID = $row->message->chat->id; + // Check if it was thrown by admitted users + in_array($row->message->from->username, BOT_ALLOWED_USERS) or not_authorized($chatID); + + //////// + ////$status = getStatus($chatID); + //////////////// + + // Finally, check actual state and do things + $status = $mc->get($chatID.MC_STATUS); + if (!$status) { + $mc->set($chatID.MC_STATUS, STATE_IDLE) or die(); // set status or force it to STATE_IDLE + $status = STATE_IDLE; + } + if (DEBUG) info("Starting from status $status"); + + switch($status) { + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * entering STATE_IDLE - message * + * you can: give a command, send messages to forward * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + case STATE_IDLE: + if (($command = getCommand($row->message)) != null) { + info("Command received: $command[command] with options $command[options]"); + + switch ($command['command']) { + case '/help': + $resp = array("remove_keyboard" => true); + $resp = json_encode($resp); + + $query = API_URL . API_TOKEN . '/sendmessage?' . + 'chat_id=' . urlencode($chatID) . + '&text='.urlencode($WELCOME_MESSAGE). + '&reply_markup='.$resp; + file_get_contents($query); + break; + + case '/edit': + // not yet implemented + break; + + case '/list': + + $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); + $numbers = $sql->query("SELECT COUNT(*) FROM ".MYSQL_TABLE); + $numbers = $numbers->fetch_array()[0]; + if ($numbers == 0) { + $query = API_URL.API_TOKEN."/sendmessage?chat_id=".($chatID). + "&text=Nessun messaggio programmato"; + $answer = file_get_contents($query); + die(); + } + + $query = $sql->query("SELECT DATE_FORMAT(DateTime,'%d/%m/%Y ore %H') as DateTime,Text,Author,ID FROM ".MYSQL_TABLE." + ORDER BY DateTime ASC LIMIT 1") or error("Can't make the query, SQL error ".$sql->error); + + //while($row = $query->fetch_assoc()) { + $row = $query->fetch_assoc(); + $mc->set($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']) + or $mc->replace($chatID.MC_DELETE_SCHEDULED_ID, $row['ID']);; + + $sql->close(); + + $container = array( + array( + array( + "text" => $row['DateTime'], + "callback_data" => "null" + ))); + + $container[] = array( + array( + "text" => " ", + "callback_data" => "null" + ), + array( + "text" => "$EMOJI_THUMBSDOWN Canc", + "callback_data" => MSG_DELETE + ), + $numbers > 1 ? + array( + "text" => ">", + "callback_data" => ">" + ) + : + array( + "text" => " ", + "callback_data" => "null" + ) + ); + + $resp = array( + "inline_keyboard" => $container); + $reply = json_encode($resp); + + $text="$row[Text]\n_$row[Author]_"; // NOME CANALE ".API_CHANNEL_ID."?"; + + $query = API_URL.API_TOKEN."/sendmessage?chat_id=".($chatID). + "&text=".urlencode($text). + "&parse_mode=".urlencode("Markdown"). + "&reply_markup=".$reply; + $answer = file_get_contents($query); + $answer = json_decode($answer); + + $mc->set($chatID.MC_INLINE_ID, $answer->result->message_id) + or $mc->replace($chatID.MC_INLINE_ID, $answer->result->message_id); + + $mc->set($chatID.MC_LIST_NUMBER, 0) + or $mc->replace($chatID.MC_LIST_NUMBER, 0); + break; + + default: + warning("$command[command] is not a valid command"); + } + } + else { // not a command (text?) + // you probably want to forward a message? + + // Check what kind of message is this + $container[] = array( array( "text" => "SI ".$EMOJI_THUMBSUP, "callback_data" => MSG_YES @@ -338,291 +624,72 @@ switch ($status) { array( "text" => "NO ".$EMOJI_THUMBSDOWN, "callback_data" => MSG_NO - ), - array( - "text" => "Programma ".$EMOJI_CLOCK, - "callback_data" => MSG_SCHEDULE - )); - $resp = array( - "inline_keyboard" => $container); - $reply = json_encode($resp); - - $text="Vuoi condividere sul canale?"; // NOME CANALE ".API_CHANNEL_ID."?"; - - $query = API_URL.API_TOKEN."/sendmessage?chat_id=".($row->message->chat->id). - "&text=".urlencode($text). - "&reply_markup=".$reply; - $answer = file_get_contents($query); - //if (DEBUG) botlog("\nINLINE ANSWER\n\n".$answer); - $answer = json_decode($answer); - - $inlineID = $answer->result->message_id; - if (DEBUG) info("Callback message id: $inlineID"); - - $mc->replace($chatID.MC_STATUS, STATE_MSG_ANSWER); - $mc->set($chatID.MC_INLINE_ID, $inlineID) or $mc->replace($chatID.MC_INLINE_ID, $inlineID); - } - break; - - - case STATE_MSG_ANSWER: // only accessible by callback - if (!(isset($callback_data))) { - //$mc->replace($chatID.MC_STATUS, STATE_IDLE); - wrong_action($chatID); - die(); - } - - switch ($callback_data) { - case MSG_YES: - // forward previously sent message - $mc->replace($chatID.MC_STATUS, STATE_IDLE) - or error("Something is wrong with memcached"); - $msg = $mc->get($chatID.MC_FORWARD_MSG) - or error("Can't forward message\n"); - - //~ $query = API_URL . API_TOKEN . '/forwardMessage?' . - //~ 'chat_id=' . urlencode(API_CHANNEL_ID) . - //~ '&from_chat_id=' . urlencode($msg->message->chat->id) . - //~ '&message_id=' . urlencode($msg->message->message_id); - //~ file_get_contents($query); - $query = API_URL . API_TOKEN . '/sendmessage?' . - 'chat_id=' . urlencode(API_CHANNEL_ID) . - '&text='.urlencode($msg->message->text."\n_".$msg->message->chat->username."_"). - "&parse_mode=".urlencode("Markdown"); //bah, un isset un ce lo vedrei male - $result = file_get_contents($query); - if(DEBUG) botlog("[LOG] $result\n"); - - // Remove kbd - $text = "Invio effettuato correttamente"; - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text); - file_get_contents($url); - break; - - case MSG_NO: - $status = $mc->replace($chatID.MC_STATUS, STATE_IDLE) - or error("Something is wrong with memcached"); - - // destroy saved message? - $text = "Invio annullato correttamente"; - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text); - file_get_contents($url); - break; - - case MSG_SCHEDULE: - // == from here can be put in a function == - $status = $mc->replace($chatID.MC_STATUS, STATE_WAIT_DATE) or die(); - $currentTab = array( - 'month' => date('n'), - 'year' => date('Y'), - 'day' => null + ) ); - $container = getCalendarTab($currentTab['month'], $currentTab['year']); - - $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) or die (); - - $container = array( - "inline_keyboard" => $container); - - $text="Quando vuoi inviare il messaggio?"; - $reply = json_encode($container); - - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text). - "&reply_markup=".$reply; - - file_get_contents($url); - - $mc->set($chatID.MC_INLINE_ID, $inlineID) or $mc->replace($chatID.MC_INLINE_ID, $inlineID) - or error("Something is wrong with memcached"); - // == end == - break; - } - break; - - case STATE_WAIT_DATE: - if (!isset($callback_data)) { - wrong_action($chatID); - die(); - } - - $currentTab = $mc->get($chatID.MC_DATE_MSG) - or error("Something is wrong with memcached"); - - // two cases: change page or confirm date - if ($callback_data == '>') { - // add 1 to month - if ($currentTab['month'] < 12) - $currentTab['month'] +=1; - else { - $currentTab['month'] = 1; - $currentTab['year'] +=1; - } - $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) - or error("Something is wrong with memcached"); - - $text = "Il calendario del ".$currentTab['month']."-".$currentTab['year']; - - // get new inline container - } - elseif ($callback_data == '<') { - if ($currentTab['month'] > 1) - $currentTab['month'] -=1; - else { - $currentTab['month'] = 12; - $currentTab['year'] -=1; - } - $text = "Il calendario del ".$currentTab['month']."-".$currentTab['year']; - - $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) - or error("Something is wrong with memcached"); - } - elseif ($callback_data == 'null') { - // not a valid button (like week days buttons) - die(); - } - elseif ($callback_data == MSG_ABORT) { - $text = "Invio annullato correttamente"; - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text); - file_get_contents($url); - $mc->replace($chatID.MC_STATUS, STATE_IDLE) or die(); - die(); - } - else { - // read current day, verify it and then change state - if (!$callback_data = intval($callback_data)) - error("Not a numerical day, how you did it?!?"); - $currentTab['day'] = $callback_data; - $mc->set($chatID.MC_DATE_MSG, $currentTab) or $mc->replace($chatID.MC_DATE_MSG, $currentTab) or die ("Failed to save data at Memcached server"); - - // Display time inline keyboard - $container = array(); - $riga = array(); - - $firstHour = date('Ynj') == $currentTab['year'].$currentTab['month'].$currentTab['day']? - date('G')+1 : 8; - - for ($i = 8; $i <= 21; $i++) { - if ($i < $firstHour) { - $riga[] = array( - "text" => " ", - "callback_data" => "null" - ); + // A photo + if (isset($row->message->photo)) { + // at the moment photo are forwardable but no schedulable } - else { - $riga[] = array( - "text" => "$i".":00", - "callback_data" => "$i" + // A location or a video + elseif (isset($row->message->location) + or isset($row->message->video)) { + sendMessage($chatID, "Presto saprò inviare questo tipo di post"); + warning("Not yet supported content"); + die(); + } + // A common text message + elseif (isset($row->message->text)) { + $container[0][] = + array( + "text" => "Programma ".$EMOJI_CLOCK, + "callback_data" => MSG_SCHEDULE ); } - - if ($i == 14) { - $container[] = $riga; - $riga = array(); + // else... this is not supported + else { + sendMessage($chatID, "Questa roba non va bene"); + error("Not supported content"); + die(); } - } - $container[] = $riga; - - $container[] = array(array( - "text" => "$EMOJI_X Annulla", - "callback_data" => MSG_ABORT - )); - - $container = array( - "inline_keyboard" => $container); - $text="A che ora vuoi inviare il messaggio?"; - $reply = json_encode($container); - - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text)."&reply_markup=".$reply; - file_get_contents($url); - - $mc->replace($chatID.MC_STATUS, STATE_WAIT_TIME) or die(); + $mc->set($chatID.MC_FORWARD_MSG, $row) + or $mc->replace($chatID.MC_FORWARD_MSG, $row) + or error("Something is wrong with memcached"); + + // SetUp inline messages (OK, NO, SCHEDULE) + + $resp = array( + "inline_keyboard" => $container); + $reply = json_encode($resp); + + $text="Vuoi condividere sul canale?"; // NOME CANALE ".API_CHANNEL_ID."?"; + + $query = API_URL.API_TOKEN."/sendmessage?chat_id=".($row->message->chat->id). + "&text=".urlencode($text). + "&reply_markup=".$reply; + $answer = file_get_contents($query); + //if (DEBUG) botlog("\nINLINE ANSWER\n\n".$answer); + $answer = json_decode($answer); + + $inlineID = $answer->result->message_id; + if (DEBUG) info("Callback message id: $inlineID"); + + $mc->replace($chatID.MC_STATUS, STATE_MSG_ANSWER); + $mc->set($chatID.MC_INLINE_ID, $inlineID) or $mc->replace($chatID.MC_INLINE_ID, $inlineID); + } break; - } - - // If answer is < or > remain in current state and update calendar - $container = getCalendarTab($currentTab['month'], $currentTab['year']); - - $resp = array( - "inline_keyboard" => $container); - - $reply = json_encode($resp); - - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text)."&reply_markup=".$reply; - file_get_contents($url); - - $mc->set($chatID.MC_INLINE_ID, $inlineID) or $mc->replace($chatID.MC_INLINE_ID, $inlineID); - - break; - - case STATE_WAIT_TIME: - $mc->replace($chatID.MC_STATUS, STATE_IDLE); - if (!isset($callback_data)) { - die(); - } - - if ($callback_data == MSG_ABORT) { - $text = "Invio annullato correttamente"; - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text); - file_get_contents($url); - $mc->replace($chatID.MC_STATUS, STATE_IDLE) or die(); - die(); - } - elseif (!$time = intval($callback_data)) { - if (DEBUG) botlog("[EE] Not a numeric time\n"); - die(); - } - - $currentTab = $mc->get($chatID.MC_DATE_MSG); - $msg = $mc->get($chatID.MC_FORWARD_MSG); - - // add to database (mysql) - $sql = new mysqli('localhost', MYSQL_USER, MYSQL_PASSWORD, MYSQL_DB); - // Build up mysql query - $value = "("; - $value .= $msg->message->message_id; - $value .= ","; - $value .= $msg->message->chat->id; - $value .= ","; - $value .= "'".$currentTab['year'].'-'; - $value .= $currentTab['month'].'-'; - $value .= $currentTab['day'].' '; - $value .= $callback_data.":00:00'"; - $value .= ","; - $value .= "'".$sql->escape_string($msg->message->text)."'"; - $value .= ","; - $value .= "'".$sql->escape_string($msg->message->from->username)."'"; // andrebbe fatto un isset, vabbé - $value .= ");"; - - info("Saving post in ".MYSQL_TABLE.", scheduled date: ".$value); - + /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * END STATE_IDLE + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ - $query = $sql->query("INSERT INTO ".MYSQL_TABLE." (MessageID,ChatID,DateTime,Text,Author) VALUE ".$value) - or error("Can't make the query, SQL error ".$sql->error); - $sql->close(); - - $text = "Programmazione avvenuta con successo"; - - $url = API_URL.API_TOKEN."/editMessageText?chat_id=".($chatID). - "&message_id=".$inlineID . - "&text=".urlencode($text); - file_get_contents($url); - - break; + default: + wrong_action($chatID); + } + +} +// a not supported message (i.e. from a channel) +else { + error("This is not a supported request. Please check JSON dump"); } - ?> diff --git a/schedule.php b/schedule.php index ce45f8c..88024fb 100644 --- a/schedule.php +++ b/schedule.php @@ -4,7 +4,7 @@ */ require_once('config.php'); -require_once('shared.php'); +require_once('functions.php'); if (DEBUG) botlog("\n\n\n".'[II] Scheduler starting at ' . date('Y-m-d H:i:s') . ' ====================' . "\n\n"); diff --git a/shared.php b/shared.php index 37402cf..1f15b15 100644 --- a/shared.php +++ b/shared.php @@ -90,7 +90,7 @@ $disable_web_page_preview = false, $reply_markup = null) { - $query = API_URL . API_TOKEN . "/forwardMessage?" . + $query = API_URL . API_TOKEN . "/editMessageText?" . "chat_id=".urlencode($chat_id) . "&message_id=" . urlencode($message_id). "&text=" . urlencode($text); @@ -115,6 +115,23 @@ return $answer; } + function sendPhoto ($chat_id, $photo, + $caption = null, + $reply_markup = null, + $disable_notification = false, + $reply_to_message_id = null ) { + + $query = API_URL . API_TOKEN . "/sendPhoto?" . + "chat_id=".urlencode($chat_id) . + "&photo=" . urlencode($photo); + + $query .= "&disable_notification=$disable_notification"; + if ($reply_to_message_id != null) $query .= "&reply_to_message_id=$disable_web_page_preview"; + if ($reply_markup != null) $query .= "&reply_markup=$reply_markup"; + if ($caption != null) $query .= "&caption=$caption"; + + $answer = file_get_contents($query); + } // Makes the calendar inline keyboard function getCalendarTab ($month, $year) {