This commit is contained in:
parent
827d514036
commit
a2b04c16ec
|
@ -19,6 +19,10 @@ require __DIR__ . '/../../../../../../../vendor/autoload.php';
|
|||
|
||||
$arangodb = new connection(require __DIR__ . '/../settings/arangodb.php');
|
||||
|
||||
/* ini_set('error_reporting', E_ALL);
|
||||
ini_set('display_errors', 1);
|
||||
ini_set('display_startup_errors', 1); */
|
||||
|
||||
/**
|
||||
* Авторизация
|
||||
*
|
||||
|
@ -172,19 +176,33 @@ function generateMenu(Context $ctx): void
|
|||
'reply_markup' => [
|
||||
'inline_keyboard' => [
|
||||
[
|
||||
['text' => '🔍 Активные заявки', 'callback_data' => 'search']
|
||||
['text' => '🔍 Активные заявки', 'callback_data' => 'day']
|
||||
]
|
||||
],
|
||||
'remove_keyboard' => true
|
||||
]
|
||||
]);
|
||||
])->then(function ($message) use ($ctx) {
|
||||
$ctx->setChatDataItem("menu", $message);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
function requests(int $amount = 5, int $page = 1): Cursor
|
||||
/**
|
||||
* Прочитать заявки из ArangoDB
|
||||
*
|
||||
* @param int $amount Количество
|
||||
* @param ?string $date За какую дату (unixtime)
|
||||
* @param int $page Страница
|
||||
*
|
||||
* @return Cursor
|
||||
*/
|
||||
function requests(int $amount = 5, ?string $date = null, int $page = 1): Cursor
|
||||
{
|
||||
global $arangodb;
|
||||
|
||||
// Инициализация значения даты по умолчанию
|
||||
$date ??= time();
|
||||
|
||||
// Фильтрация номера страницы
|
||||
if ($page < 1) $page = 1;
|
||||
|
||||
|
@ -198,12 +216,14 @@ function requests(int $amount = 5, int $page = 1): Cursor
|
|||
$arangodb->session,
|
||||
[
|
||||
'query' => sprintf(
|
||||
"FOR d IN task FILTER d.date >= %s && d.worker == null && d.confirmed != true && d.published == true && d.completed != true SORT d.created DESC, d._key DESC LIMIT %d, %d RETURN d",
|
||||
/* "FOR d IN task FILTER d.date >= %s && d.date <= %s && d.worker == null && d.confirmed != true && d.published == true && d.completed != true SORT d.created DESC, d._key DESC LIMIT %d, %d RETURN d", */
|
||||
(new DateTime('now'))->setTime(7, 0)->format('U'),
|
||||
/* (new DateTime('tomorrow'))->setTime(7, 0)->format('U'), */
|
||||
// d.date < %s там специально, не менять на <=
|
||||
"FOR d IN task FILTER ((d.date >= %s && d.date < %s && d.start >= '05:00') || (d.date >= %s && d.date < %s && d.start < '05:00')) && d.worker == null && d.market != null && d.confirmed != true && d.published == true && d.completed != true SORT d.created DESC, d._key DESC LIMIT %d, %d RETURN d",
|
||||
$from = (new DateTime("@$date"))->setTime(0, 0)->format('U'),
|
||||
$to = (new DateTime("@$date"))->modify('+1 day')->setTime(0, 0)->format('U'),
|
||||
$to,
|
||||
(new DateTime("@$date"))->modify('+2 day')->setTime(0, 0)->format('U'),
|
||||
$offset,
|
||||
$amount + $offset
|
||||
$amount + $offset - ($page > 0)
|
||||
),
|
||||
"batchSize" => 1000,
|
||||
"sanitize" => true
|
||||
|
@ -219,7 +239,7 @@ function generateEmojis(): string
|
|||
function requests_next(Context $ctx): void
|
||||
{
|
||||
$ctx->getChatDataItem('requests_page')->then(function ($page) use ($ctx) {
|
||||
$ctx->setChatDataItem('requests_page', ($page ?? 1) + 1)->then(function () use ($ctx) {
|
||||
$ctx->setChatDataItem('requests_page', ($page ?? 1) + 1)->then(function () use ($ctx, $page) {
|
||||
search($ctx);
|
||||
});
|
||||
});
|
||||
|
@ -242,7 +262,7 @@ function request_choose(Context $ctx): void
|
|||
// Авторизован
|
||||
|
||||
// Инициализация ключа инстанции task в базе данных
|
||||
preg_match('/^#(\d+)\n/', $ctx->getCallbackQuery()->getMessage()->getText(), $matches);
|
||||
preg_match('/\->\s#(\d+)\n/', $ctx->getCallbackQuery()->getMessage()->getText(), $matches);
|
||||
$_key = $matches[1];
|
||||
|
||||
// Инициализация инстанции task в базе данных (выбранного задания)
|
||||
|
@ -252,7 +272,7 @@ function request_choose(Context $ctx): void
|
|||
// Найден сотрудник
|
||||
|
||||
// Запись идентификатора нового сотрудника
|
||||
$task->worker = $worker->getKey();
|
||||
$task->worker = $worker->id;
|
||||
|
||||
// Снятие с публикации
|
||||
$task->published = false;
|
||||
|
@ -260,8 +280,17 @@ function request_choose(Context $ctx): void
|
|||
if (document::update($arangodb->session, $task)) {
|
||||
// Записано обновление в базу данных
|
||||
|
||||
$ctx->sendMessage("✅ *Заявка принята:* \#$_key", ['reply_markup' => ['remove_keyboard' => true]])->then(function () use ($ctx) {
|
||||
generateMenu($ctx);
|
||||
$ctx->getChatDataItem("request_all")->then(function ($requests = []) use ($ctx, $_key) {
|
||||
// Удаление сообщений связанных с запросом
|
||||
foreach ($requests ?? [] as $_message) $ctx->deleteMessage($_message->getChat()->getId(), $_message->getMessageId());
|
||||
$ctx->setChatDataItem("request_all", []);
|
||||
|
||||
$ctx->sendMessage("✅ *Заявка принята:* \#$_key", ['reply_markup' => ['remove_keyboard' => true]])->then(function () use ($ctx) {
|
||||
generateMenu($ctx);
|
||||
});
|
||||
|
||||
// End of the process
|
||||
$ctx->endConversation();
|
||||
});
|
||||
} else $ctx->sendMessage("❎ *Не удалось принять заявку:* \#$_key", ['reply_markup' => ['remove_keyboard' => true]])->then(function () use ($ctx) {
|
||||
generateMenu($ctx);
|
||||
|
@ -272,6 +301,39 @@ function request_choose(Context $ctx): void
|
|||
}
|
||||
}
|
||||
|
||||
function day(Context $ctx): void
|
||||
{
|
||||
if (authorization($ctx->getMessage()?->getFrom()?->getId() ?? $ctx->getCallbackQuery()->getFrom()->getId()) instanceof _document) {
|
||||
// Авторизован
|
||||
|
||||
// Инициализация буфера клавиатуры
|
||||
$keyboard = [];
|
||||
|
||||
// Генерация кнопок с выбором даты
|
||||
for ($i = 1, $r = 0; $i < 15; ++$i) $keyboard[$i > 4 * ($r + 1) ? ++$r : $r][] = ['text' => ($date = (new DateTime)->modify("+$i day"))->format('d.m.Y'), 'callback_data' => $date->format('U')];
|
||||
|
||||
$ctx->setChatDataItem('requests_page', 1)->then(function () use ($ctx, $keyboard) {
|
||||
// Отправка меню
|
||||
$ctx->sendMessage('📅 Выберите дату', [
|
||||
'reply_markup' => [
|
||||
'inline_keyboard' => $keyboard
|
||||
]
|
||||
])->then(function ($message) use ($ctx) {
|
||||
$ctx->getChatDataItem("menu")->then(function ($message) use ($ctx) {
|
||||
// Удаление главного меню
|
||||
if ($message) $ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
$ctx->setChatDataItem("menu", null);
|
||||
});
|
||||
|
||||
// Запись сообщения в кеш (на случай необходимости его удаления при смене страницы)
|
||||
$ctx->setChatDataItem("request_day", $message);
|
||||
});
|
||||
});
|
||||
|
||||
$ctx->nextStep("search");
|
||||
}
|
||||
}
|
||||
|
||||
function search(Context $ctx): void
|
||||
{
|
||||
global $arangodb;
|
||||
|
@ -288,94 +350,132 @@ function search(Context $ctx): void
|
|||
$ctx->setChatDataItem('requests_page', 1);
|
||||
}
|
||||
|
||||
// Поиск заявок из базы данных
|
||||
$tasks = requests(6, $page);
|
||||
$generate = function ($date) use ($ctx, $page, $arangodb) {
|
||||
// Поиск заявок в ArangoDB
|
||||
$tasks = requests(4, (string) $date, $page);
|
||||
|
||||
// Подсчёт количества прочитанных заявок из базы данных
|
||||
$count = $tasks->getCount();
|
||||
// Подсчёт количества прочитанных заявок из базы данных
|
||||
$count = $tasks->getCount();
|
||||
|
||||
// Проверка существования избытка
|
||||
$excess = $count % 6 === 0;
|
||||
// Проверка существования избытка
|
||||
$excess = $count > 3;
|
||||
|
||||
// Обрезка заявок до размера страницы
|
||||
$tasks = array_slice($tasks->getAll(), 0, 5);
|
||||
// Обрезка заявок до размера страницы (3 заявки на 1 странице)
|
||||
$tasks = array_slice($tasks->getAll(), 0, 3);
|
||||
|
||||
if ($count === 0) $ctx->sendMessage('📦 *Заявок нет*');
|
||||
else {
|
||||
// Найдены заявки
|
||||
|
||||
foreach ($tasks as $i => $task) {
|
||||
// Перебор найденных заявок
|
||||
|
||||
if (($market = collection::search(
|
||||
$arangodb->session,
|
||||
sprintf(
|
||||
"FOR d IN market FILTER d._key == '%s' RETURN d",
|
||||
$task->market
|
||||
)
|
||||
)) instanceof _document) {
|
||||
// Найден магазин
|
||||
|
||||
$ctx->getChatDataItem("request_$i")->then(function ($message) use ($ctx) {
|
||||
// Удаление предыдущего сообщения на этой позиции
|
||||
$ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
if ($count === 0) {
|
||||
$ctx->sendMessage('📦 *Заявок нет*')->then(function ($message) use ($ctx) {
|
||||
$ctx->getChatDataItem("request_all")->then(function ($requests = []) use ($ctx, $message) {
|
||||
// Удаление сообщений связанных с запросом
|
||||
foreach ($requests ?? [] as $_message) $ctx->deleteMessage($_message->getChat()->getId(), $_message->getMessageId());
|
||||
$ctx->setChatDataItem("request_all", $requests = [$message]);
|
||||
});
|
||||
});
|
||||
} else {
|
||||
// Найдены заявки
|
||||
|
||||
// Генерация эмодзи
|
||||
/* $emoji = generateEmojis(); */
|
||||
$ctx->getChatDataItem("request_day")->then(function ($message) use ($ctx, $arangodb, $tasks, $page, $excess) {
|
||||
// Удаление предыдущего меню с выбором даты
|
||||
if ($message) $ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
$ctx->setChatDataItem("request_day", null)->then(function () use ($ctx, $arangodb, $tasks, $page, $excess) {
|
||||
$ctx->getChatDataItem("request_all")->then(function ($requests = []) use ($ctx, $arangodb, $tasks, $excess, $page) {
|
||||
// Удаление сообщений связанных с запросом
|
||||
foreach ($requests ?? [] as $_message) $ctx->deleteMessage($_message->getChat()->getId(), $_message->getMessageId());
|
||||
$ctx->setChatDataItem("request_all", [])->then(function () use ($ctx, $arangodb, $tasks, $excess, $page) {
|
||||
foreach ($tasks as $i => $task) {
|
||||
// Перебор найденных заявок
|
||||
|
||||
// Отправка сообщения
|
||||
$ctx->sendMessage(
|
||||
preg_replace(
|
||||
'/([._\-()!#])/',
|
||||
'\\\$1',
|
||||
"*#{$task->getKey()}*\n" . (new DateTime('@' . $task->date))->format('d.m.Y') . " (" . $task->start . " - " . $task->end . ")\n\n*Город:* $market->city\n*Адрес:* $market->address\n*Работа:* $task->work" . (mb_strlen($task->description) > 0 ? "\n\n$task->description" : '')
|
||||
),
|
||||
[
|
||||
'reply_markup' => [
|
||||
'inline_keyboard' => [
|
||||
[
|
||||
['text' => '✅ Отправить запрос', 'callback_data' => 'request_choose']
|
||||
]
|
||||
]
|
||||
]
|
||||
]
|
||||
)->then(function ($message) use ($ctx, $tasks, $i, $page, $excess) {
|
||||
// Запись сообщения в кеш (на случай необходимости его удаления при смене страницы)
|
||||
$ctx->setChatDataItem("request_$i", $message)->then(function () use ($ctx, $tasks, $i, $page, $excess) {
|
||||
if (($market = collection::search(
|
||||
$arangodb->session,
|
||||
sprintf(
|
||||
"FOR d IN market FILTER d.id == '%s' RETURN d",
|
||||
$task->market
|
||||
)
|
||||
)) instanceof _document) {
|
||||
// Найден магазин
|
||||
$ctx->getChatDataItem("request_$i")->then(function ($message) use ($ctx, $task, $market, $tasks, $i, $page, $excess) {
|
||||
// Удаление предыдущего сообщения на этой позиции
|
||||
if ($message) $ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
$ctx->setChatDataItem("request_$i", null)->then(function () use ($ctx, $task, $market, $tasks, $i, $page, $excess) {
|
||||
// Генерация эмодзи
|
||||
/* $emoji = generateEmojis(); */
|
||||
|
||||
if ($i === array_key_last($tasks)) {
|
||||
// Удаление предыдущего меню
|
||||
$ctx->getChatDataItem("request_menu")->then(function ($message) use ($ctx) {
|
||||
$ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
});
|
||||
// Отправка сообщения
|
||||
$ctx->sendMessage(
|
||||
preg_replace(
|
||||
'/([._\-()!#])/',
|
||||
'\\\$1',
|
||||
"*#$task->market* -\> *#{$task->getKey()}*\n" . (new DateTime('@' . $task->date))->format('d.m.Y') . " (" . $task->start . " - " . $task->end . ")\n\n*Город:* $market->city\n*Адрес:* $market->address\n*Работа:* $task->work" . (mb_strlen($task->description) > 0 ? "\n\n$task->description" : '')
|
||||
),
|
||||
[
|
||||
'reply_markup' => [
|
||||
'inline_keyboard' => [
|
||||
[
|
||||
['text' => '✅ Отправить запрос', 'callback_data' => 'request_choose']
|
||||
]
|
||||
]
|
||||
]
|
||||
]
|
||||
)->then(function ($message) use ($ctx, $tasks, $i, $page, $excess) {
|
||||
// Запись сообщения в кеш (на случай необходимости его удаления при смене страницы)
|
||||
$ctx->setChatDataItem("request_$i", $message)->then(function () use ($ctx, $message, $tasks, $i, $page, $excess) {
|
||||
$ctx->getChatDataItem("request_all")->then(function ($requests = []) use ($ctx, $message, $tasks, $i, $page, $excess) {
|
||||
$ctx->setChatDataItem("request_all", $requests = ($requests ?? []) + [count($requests) => $message])->then(function () use ($ctx, $tasks, $i, $page, $excess) {
|
||||
if ($i === array_key_last($tasks)) {
|
||||
// End of the process
|
||||
$ctx->endConversation();
|
||||
|
||||
// Инициализация буфера для меню поиска
|
||||
$keyboard = [];
|
||||
// Удаление предыдущего меню
|
||||
$ctx->getChatDataItem("request_menu")->then(function ($message) use ($ctx, $page, $excess) {
|
||||
if ($message) $ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
$ctx->setChatDataItem("request_menu", null)->then(function () use ($ctx, $page, $excess) {
|
||||
// Инициализация буфера для меню поиска
|
||||
$keyboard = [];
|
||||
|
||||
// Генерация кнопки: "Предыдущая страница"
|
||||
if ($page > 1) $keyboard[] = ['text' => 'Назад ⬅️', 'callback_data' => 'requests_previous'];
|
||||
// Генерация кнопки: "Предыдущая страница"
|
||||
if ($page > 1) $keyboard[] = ['text' => 'Назад', 'callback_data' => 'requests_previous'];
|
||||
|
||||
// Генерация кнопки: "Следующая страница"
|
||||
if ($excess) $keyboard[] = ['text' => '➡️ Вперёд', 'callback_data' => 'requests_next'];
|
||||
// Генерация кнопки: "Отображённая страница"
|
||||
$keyboard[] = ['text' => $page, 'callback_data' => 'requests_current'];
|
||||
|
||||
// Отправка меню
|
||||
$ctx->sendMessage('🔍 Выберите заявку', [
|
||||
'reply_markup' => [
|
||||
'inline_keyboard' => [
|
||||
$keyboard
|
||||
]
|
||||
]
|
||||
])->then(function ($message) use ($ctx) {
|
||||
// Запись сообщения в кеш (на случай необходимости его удаления при смене страницы)
|
||||
$ctx->setChatDataItem("request_menu", $message);
|
||||
});
|
||||
}
|
||||
// Генерация кнопки: "Следующая страница"
|
||||
if ($excess) $keyboard[] = ['text' => 'Вперёд', 'callback_data' => 'requests_next'];
|
||||
|
||||
// Отправка меню
|
||||
$ctx->sendMessage('🔍 Выберите заявку', [
|
||||
'reply_markup' => [
|
||||
'inline_keyboard' => [
|
||||
$keyboard
|
||||
]
|
||||
]
|
||||
])->then(function ($message) use ($ctx) {
|
||||
// Запись сообщения в кеш (на случай необходимости его удаления при смене страницы)
|
||||
$ctx->setChatDataItem("request_menu", $message);
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// Инициализация даты и генерация
|
||||
$ctx->getChatDataItem('requests_date')->then(function ($old) use ($ctx, $generate) {
|
||||
$new = $ctx->getCallbackQuery()->getData();
|
||||
if ($new === (string) (int) $new && $new <= PHP_INT_MAX && $new >= ~PHP_INT_MAX) $ctx->setChatDataItem('requests_date', $new)->then(fn () => $generate($new));
|
||||
else $generate($old);
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -416,13 +516,31 @@ $bot->onUpdate(function (Context $ctx) use (&$stop): void {
|
|||
|
||||
$bot->onCommand('start', function (Context $ctx) use ($stop): void {
|
||||
if ($stop) return;
|
||||
$ctx->getChatDataItem("request_all")->then(function ($requests = []) use ($ctx) {
|
||||
// Удаление сообщений связанных с запросом
|
||||
foreach ($requests ?? [] as $_message) $ctx->deleteMessage($_message->getChat()->getId(), $_message->getMessageId());
|
||||
$ctx->setChatDataItem("request_all", []);
|
||||
});
|
||||
|
||||
$ctx->getChatDataItem("menu")->then(function ($message) use ($ctx) {
|
||||
// Удаление главного меню
|
||||
if ($message) $ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
$ctx->setChatDataItem("menu", null);
|
||||
});
|
||||
|
||||
$ctx->getChatDataItem("request_day")->then(function ($message) use ($ctx) {
|
||||
// Удаление меню выбора даты
|
||||
if ($message) $ctx->deleteMessage($message->getChat()->getId(), $message->getMessageId());
|
||||
$ctx->setChatDataItem("request_day", null);
|
||||
});
|
||||
|
||||
generateMenu($ctx);
|
||||
});
|
||||
|
||||
$bot->onCommand('search', fn ($ctx) => search($ctx));
|
||||
$bot->onCbQueryData(['search'], fn ($ctx) => search($ctx));
|
||||
$bot->onCbQueryData(['requests_next'], fn ($ctx) => requests_next($ctx));
|
||||
$bot->onCbQueryData(['requests_previous'], fn ($ctx) => requests_previous($ctx));
|
||||
$bot->onCbQueryData(['request_choose'], fn ($ctx) => request_choose($ctx));
|
||||
$bot->onCommand('day', fn ($ctx) => day($ctx));
|
||||
$bot->onCbQueryData(['day'], fn ($ctx) => day($ctx));
|
||||
|
||||
$bot->run();
|
||||
|
|
Reference in New Issue