Введение

На сегодняшнем уроке мы собираемся создать простое, но сложное автоматизированное приложение Flutter с использованием Telegram Bot Api и Web View. Давайте углубимся в темы, которые мы собираемся обсудить сегодня.

Выше приведено руководство по использованию приложения.

ССЫЛКА НА ПРИЛОЖЕНИЕ: https://drive.google.com/drive/folders/1ze50PtMKyaL6Fyjuh5PPeE3vwL89tsYT?usp=sharing

Содержание урока

  • Главный экран
  • Защищенное хранилище Flutter
  • Объяснение пользовательского интерфейса
  • Веб-представление
  • Интеграция бота Telegram
  • Логика автоматизации
  • ССЫЛКА НА РЕПО GITHUB

Домашний экран

Давайте начнем с разработки нашего домашнего пользовательского интерфейса. Я просто добавил три элемента TextFormField Inside Column Widget, чтобы получить необходимую информацию от пользователя. Он состоит из трех необходимых сведений: токен Telegram Bot API, идентификатор или идентификатор канала и желаемая дата для уведомления. Позвольте мне показать вам код, так вы лучше его поймете.

Из приведенного выше кода видно, что я добавил TextFormFields внутрь виджета «Столбец», чуть ниже кнопки с приподнятыми краями и других виджетов. Это простой дизайн, который, я думаю, мне не нужно объяснять. Итак, давайте перейдем к строке 47. Здесь я использовал CheckBoxListTile для функции «Запомнить информацию», где я назначил логическое значение _saveDetails по умолчанию. Я установил его как true, который может быть изменен пользователем в соответствии с его предпочтениями, поэтому назначенный метод SetState с newValue который будет назначен пользователем нашему логическому _saveDetails.

В строке 57 я добавил ElevatedButton для выполнения процесса. В строках с 61 по 76 я добавил логику для выполнения следующего процесса. В строке 62 я добавил условие для проверки и убедитесь, что ни одно из полей TextFormField не является пустым или нулевым. В строках с 65 по 69 я присвоил введенное пользователем значение глобальным переменным. Я назначил три глобальные переменные, чтобы использовать их в любом месте проекта. Ниже приведен код, который я уже назначил для глобальных переменных в файле main.dart.

Тремя глобальными переменными являются userDate, userToken и userId, которые будут использоваться в ProcessPage.

В строке 70 я добавил метод под названием _onRemember, который используется для сохранения вводимой пользователем информации в безопасное хранилище Flutter. Таким образом, если пользователь закроет и снова откроет приложение, ему не потребуется снова вводить всю информацию. Ниже приведен код для более ясного понимания.

В приведенном выше CodeSnap строки с 24 по 25 используются для выполнения операций записи в локальное хранилище устройства. Кроме того, я назначил там условие, что если только логическое значение _saveDetails истинно, данные будут сохранены, иначе нет. _saveDetails — это то же логическое значение, которое мы использовали в CheckboxListTile.

Прямо над методом _onRemember() вы можете увидеть метод Future с именем _readSavedData(). Он используется для чтения данных, когда пользователь закрывает и снова открывает приложение. Для этого я добавил его в функцию init. Прямо над функцией dispose. Если пользователь использовал функцию запоминания информации, этот метод просто проверит ранее сохраненную информацию и назначит ее текстовым полям формы. Таким образом, пользователю не нужно будет снова вводить каждую информацию.

После варианта использования функции «Запомнить информацию» в строке 71 я использовал AlertDialog, чтобы убедиться, что пользователь ввел все в данный момент. Ниже приведен код содержимого диалогового окна.

Ну, я думаю, мне не нужно объяснять весь дизайн пользовательского интерфейса, я буду придерживаться функций и логики. Я знаю, что вы, ребята, можете сами разобраться с пользовательским интерфейсом.

Итак, в строках с 19 по 25 я только что добавил навигацию на следующую страницу и Navigator.pop, чтобы закрыть диалоговое окно. Я использовал пакет GetX для навигации, управления состоянием и других утилит.

Кроме того, в строке 62 я добавил вводимые пользователем данные с помощью интерполяции строк, чтобы они могли проверить, являются ли введенные ими данные точными или неточными. Итак, это все о диалоговом окне. Я добавил пару других AlertDialogBox для указания пользователю, как вводить данные. Вы можете найти код в моем репозитории Github.

Страница процесса

Давайте перейдем к следующей странице, где осуществляется вся автоматизация и интеграция с API телеграмм-бота.

В ProcessPage я сначала реализовал WebView с помощью этого пакета webview_flutter. Ну, я использовал WEBVIEW, потому что веб-сайт, с которого я собираюсь извлечь данные, защищен HCaptcha. Итак, я применил очень простую логику. . т.е. Просто войдите в систему с действительной учетной записью и продолжайте обновлять страницу каждые 20 секунд и получайте новые и обновленные данные, необходимые пользователю. и отправка данных нашему TelegramBot, который затем опубликует их на канале или в группе в соответствии с назначением пользователя. Мы будем использовать http POST REQUEST для отправки данных TelegramBot. Итак, давайте углубимся и посмотрим код.

В строках с 1 по 7 я только что настроил WebView, JavaUnrestricted означает, что мы можем выполнять операции с JavaScript. Начальный URL-адрес — это URL-адрес нашего целевого веб-сайта. onWebViewCreated — это функция, которая вызывается после создания веб-представления, WebViewController используется для управления веб-представлением и имеет различные методы, которые мы можем вызывать для своего экземпляра для выполнения различных действий в веб-представлении. onWebViewStarted вызывается, когда страница начинает загружаться.

onWebviewStarted is invoked when a page starts while onProgress is invoked when a page is loading. similarly, onPageFinished is invoked when the website is fully loaded.Вы заметите, что я добавил функцию setState на каждый шаг, в основном она используется для LinearProgressIndicator, чтобы показать прогресс при загрузке веб-сайта. onPageFinished я добавил Future, который просто оценивает javascript сайта и помогает нам извлечь необходимую информацию. Я использовал querySelector для извлечения данных с сайта. После получения данных я сопоставил данные с переменной Date. После получения данных в нем есть несколько ненужных частей, чтобы удалить ненужные части из данных. Я использовал функции расширения Regex и Velocity_x Package, чтобы получить именно те данные, которые хочет пользователь.

Наконец, после получения необходимых данных пришло время отправить данные в назначенный пользователем API TelegramBot.

if (finalDate.isNotEmpty) {
if (onlyDate.toString().contains(userDate)) {
final feedback = await http.post(Uri.parse(
"https://api.telegram.org/bot${userToken}/sendMessage?chat_id=${userID}&text=𝐔𝐩𝐝𝐚𝐭𝐞: $onlyDate, ${DateTime.now().year}\n\n<---𝐕𝐢𝐬𝐚 𝐃𝐚𝐭𝐞𝐬 𝐔𝐩𝐝𝐚𝐭𝐞--->\n\n$finalDate\n\n<--------------𝑬𝑵𝑫-------------->"))
.timeout(10.seconds, onTimeout: () {
return http.Response("", 500);
});
if (feedback.statusCode == 500) {
debugPrint("Timed Out"); }}}
else if (finalDate.isEmpty) {
final feedback = await http
.post(Uri.parse(
"https://api.telegram.org/bot${userToken}/sendMessage?chat_id=${userID}&text=<-------𝙎𝙚𝙧𝙫𝙚𝙧 𝙄𝙨𝙨𝙪𝙚------->\n\n𝑹𝒆𝒂𝒔𝒐𝒏: 𝑬𝒊𝒕𝒉𝒆𝒓 𝑫𝒖𝒎𝒎𝒚 𝒂𝒄𝒄𝒐𝒖𝒏𝒕 𝒅𝒆𝒂𝒅 𝒐𝒓 𝑺𝒆𝒓𝒗𝒆𝒓 𝑼𝒑𝒅𝒂𝒕𝒊𝒏𝒈 | 𝑷𝒍𝒆𝒂𝒔𝒆 𝒘𝒂𝒊𝒕......\n\n<--------------𝙴𝙽𝙳-------------->"))
.timeout(const Duration(seconds: 10), onTimeout: () {
return http.Response("", 500);
});
else if (finalDate.isEmpty) {
final feedback = await http
.post(Uri.parse(
"https://api.telegram.org/bot${userToken}/sendMessage?chat_id=${userID}&text=<-------𝙎𝙚𝙧𝙫𝙚𝙧 𝙄𝙨𝙨𝙪𝙚------->\n\n𝑹𝒆𝒂𝒔𝒐𝒏: 𝑬𝒊𝒕𝒉𝒆𝒓 𝑫𝒖𝒎𝒎𝒚 𝒂𝒄𝒄𝒐𝒖𝒏𝒕 𝒅𝒆𝒂𝒅 𝒐𝒓 𝑺𝒆𝒓𝒗𝒆𝒓 𝑼𝒑𝒅𝒂𝒕𝒊𝒏𝒈 | 𝑷𝒍𝒆𝒂𝒔𝒆 𝒘𝒂𝒊𝒕......\n\n<--------------𝙴𝙽𝙳-------------->"))
.timeout(const Duration(seconds: 10), onTimeout: () {
return http.Response("", 500);
});
if (feedback.statusCode == 500) {
debugPrint("Timed Out");}}
Future.delayed(const Duration(seconds: 20), () {
_controller?.reload();
});},

Из приведенного выше кода вы можете видеть, что я использовал условие в первую очередь, чтобы проверить, являются ли собранные нами данные пустыми или нет, и если они не пусты, мы снова использовали другое условие, где мы проверяем, содержат ли данные Дата, назначенная пользователем в первую очередь Если она содержится, то процесс продолжается. Таким образом, когда данные также совпадают с данными, назначенными пользователем, мы вызываем HTTP POST REQUEST в Telegram, используя botToken и ChannelID, которые мы запросили. от пользователя в первую очередь. Вы что-то здесь заметили? , я использовал глобальную переменную, то есть userToken и channelID, которой мы присвоили значение на нашей домашней странице с помощью функции setState при нажатии ElevatedButton(Start-Process). Это просто ссылка, чтобы вы знали, как эта функция используется на этой странице. Вы также заметите, что я также добавил время ожидания, чтобы, если веб-сайт загружался слишком долго, он возвращал statusCode 500, для которого мы просто использовали debugPrint, который, однако, бесполезен. Мы также добавили еще одно условие, т.е. когда данные, извлеченные с веб-сайта, пусты, мы вызвали HTTP POST REQUEST и отправили сообщение SERVER ISSUE ИЛИ UPDATING пользовательскому боту.

После интеграции телеграммы вот простой код для автоматизации в конце файла onPageFinished. Вы можете видеть бит кода. Он продолжает обновлять страницу каждые 20 секунд, обновляя пользователей данными, если они доступны, поскольку они назначили дату.

Future.delayed(const Duration(seconds: 20), () {
_controller?.reload();
});

После этого оставшаяся часть пользовательского интерфейса — это просто контейнеры «Следуй за мной» и заметки для пользователей.

ВОТ ЭТО, РЕБЯТА, МЫ УСПЕШНО ЗАПОЛНИЛИ НАШУ ЗАЯВКУ, КОТОРАЯ БУДЕТ ПРЕДОСТАВЛЯТЬ ДОСТУПНЫЕ ДАТЫ ВИЗЫ США, И ПРОДОЛЖАЕМ обновлять ее КАЖДЫЕ 20 СЕКУНД. НАДЕЮСЬ, ВАМ ПОНРАВИЛОСЬ МОЕ ОБЪЯСНЕНИЕ. ЕСЛИ ВАМ ПОНРАВИЛСЯ МОЙ КОНТЕНТ, ПОДЕЛИТЕСЬ ЕГО С ДРУЗЬЯМИ И СЕМЬЯМИ.

Если вы не хотите пропустить ни один из моих блогов, вы можете подписаться на подписку по электронной почте и подписаться на меня в среде. Вот ссылка на репозиторий GitHub: https://github.com/josephyaduvanshi/US-VISA-DATE-NOTIFER

Сделайте форк и следуйте за мной на GITHUB ТОЖЕ… МИР!!!!