Šablóna pre jednoduchý telegramový robot pre školákov v ročníkoch 7-9 pomocou Powershell

Pri rozhovoroch s kamarátkou som sa zrazu dozvedel, že deti v 8. – 10. ročníku na ich škole vôbec neučia programovať. Word, Excel a všetko ostatné. Žiadne logo, dokonca ani Pascal, dokonca ani VBA pre Excel.

Bol som veľmi prekvapený, otvoril som internet a začal som čítať -
Jednou z úloh špecializovanej školy je podporovať výchovu novej generácie, ktorá svojou úrovňou rozvoja a životného štýlu spĺňa podmienky informačnej spoločnosti.
Tento kurz umožní študentom upevniť si v praxi vedomosti o základných konštrukciách programovacieho jazyka Pascal. (z programu niektorého gymnázia na rok 2017)

Nakoniec som sa rozhodol stráviť pár hodín a načrtnúť príklad „ako vytvoriť jednoduchého robota pre školákov“.

Nižšie je uvedený spôsob, ako napísať ďalšieho jednoduchého robota v Powershell a zabezpečiť, aby fungoval bez webhooku, bielych IP adries, dedikovaných serverov, nasadených virtuálnych strojov v cloude atď. – na bežnom domácom PC s bežným Windowsom.

TLDR: Ďalší nudný článok s gramatickými a faktickými chybami, nič na čítanie, žiadny humor, žiadne obrázky.

V článku nie je nič nové, skoro všetko napísané už bolo na Habré, napríklad v článkoch Pokyny: Ako vytvoriť roboty v telegrame и Telegramový bot pre správcu systému.
Okrem toho je článok zámerne nadbytočný, aby zakaždým neodkazoval na náučnú literatúru. V texte nie sú žiadne odkazy na Gang 4, PowerShell Deep Dives alebo povedzme 5 pilierov dobre architektonického rámca AWS.

Namiesto predslovu môžete preskočiť

Pokojne preskočteV roku 2006 spoločnosť Microsoft vydala PowerShell 1.0 pre vtedajšie systémy Windows XP, Vista a Server 2003. V niektorých ohľadoch nahradil také veci, ako sú skripty cmdbat, skripty vb, Windows Script Host a JScript.

PowerShell možno aj teraz považovať za ďalší krok po možnostiach Logo, namiesto pravdepodobne stále používaného Delphi (alebo niečoho staršieho), napriek prítomnosti slučiek, tried, funkcií, volaní MS GUI, Integrácia Git a tak ďalej.

Powershell sa používa pomerne zriedka, môžete sa s ním stretnúť len vo forme PowerShell Core, VMware vSphere PowerCLI, Azure PowerShell, MS Exchange, Desired State Configuration, Webový prístup PowerShell a asi tucet zriedkavejších programov a funkcií. Snáď dostane druhý dych vydaním WSL2, ale nie je to presne tak.

Powershell má tiež tri veľké výhody:

  1. Je to pomerne jednoduché, existuje o tom veľa literatúry a príkladov a aj v ruštine napríklad článok o Foreach - z knihy PowerShell do hĺbky - o rozdiele () a {}
  2. Ide s redaktorom ISE, ktorý je súčasťou systému Windows. Dokonca je tam aj nejaký debugger.
  3. Dá sa z neho ľahko zavolať komponenty na vytvorenie grafického rozhrania.

0. Príprava.

Budeme potrebovať:

  • Windows PC (mám Windows 10)
  • Aspoň nejaký druh prístupu na internet (napríklad cez NAT)
  • Pre tých, ktorí majú obmedzený prístup k telegramu - nainštalovaná a nakonfigurovaná freegate v prehliadači, v niektorých zložitých prípadoch spolu so Symple DNS Crypt
  • Mať v telefóne funkčného telegramového klienta
  • Pochopenie úplných základov – čo je to premenná, pole, slučka.

Otvorené a prečítané články - Pokyny: Ako vytvoriť roboty v telegrame и Telegramový bot pre správcu systému

1. Vytvorme ďalšieho testovacieho robota.

Keďže to už všetci vedia a už sa to stalo, môžete to aj preskočiťAko je uvedené v článku vyššie - Po prvé, robot pre Telegram - stále je to aplikácia spustená na vašej strane a odosielajúca požiadavky na rozhranie API telegramového bota. Okrem toho je rozhranie API jasné - robot pristupuje na konkrétnu adresu URL s parametrami a telegram odpovedá objektom JSON.

Súvisiace problémy: ak nejakým neznámym spôsobom vezmete nejaký kód z objektu JSON a nejakým spôsobom ho pošlete na vykonanie (nie zámerne), kód sa spustí za vás.

Proces vytvárania je popísaný v dvoch článkoch vyššie, ale opakujem: v telegrame otvoríme kontakty, vyhľadáme @botfather, povieme mu /newbot, vytvoríme bota Botfortest12344321, nazveme ho Mynext1234bot a dostaneme správu s jedinečným kľúčom formulár 1234544311:AbcDefNNNNNNNNNNNNNN

Postarajte sa o kľúč a nedávajte ho!

Potom môžete robota nakonfigurovať, napríklad zakázať jeho pridávanie do skupín, ale v prvých krokoch to nie je potrebné.

Požiadajme BotFathera o „/mybot“ a upravme nastavenia, ak sa nám niečo nepáči.

Otvorme znova kontakty, nájdime tam @Botfortest12344321 (je povinné začať vyhľadávanie pomocou @), klikneme na „štart“ a napíšeme robotovi „/Sláva robotom“. Znak / je povinný, úvodzovky nie sú potrebné.
Robot samozrejme na nič neodpovie.

Skontrolujte, či bol robot vytvorený a otvorte ho.

api.telegram.org/bot1234544311:AbcDefNNNNNNNNNNNNNN/getMe
kde 1234544311:AbcDefNNNNNNNNNNNNNN je predtým prijatý kľúč,
a získajte riadok ako
{"ok":true,"result":{""}}

Máme prvú tajnú frázu (token). Teraz musíme zistiť druhé tajné číslo - ID chatu s robotom. Každý chat, skupina a pod. je individuálny a má svoje číslo (niekedy s mínusom - pre otvorené skupiny). Aby sme toto číslo zistili, musíme si v prehliadači vyžiadať (v skutočnosti to v prehliadači vôbec nie je potrebné, ale pre lepšie pochopenie ním môžete začať) adresu (kde 1234544311:NNNNNNNNNN je váš token

https://api.telegram.org/bot1234544311:NNNNNNNNN/getUpdates

a dostanete odpoveď ako

{"ok":true,"result":[{"update_id":...,... rozprávanie":{"id":123456789

Potrebujeme chat_id.

Skontrolujeme, či môžeme písať do chatu manuálne: zavolajte na adresu z prehliadača

https://api.telegram.org/botваштокен/sendMessage?chat_id=123456789&text="Life is directed motion"

Ak dostanete správu od robota vo svojom rozhovore, dobre, prejdete do ďalšej fázy.

Takto (cez prehliadač) môžete vždy skontrolovať, či nie sú problémy s generovaním odkazu, alebo či niečo nie je niekde skryté a nefunguje.

Čo potrebujete vedieť pred pokračovaním v čítaní

Telegram má niekoľko typov skupinových rozhovorov (otvorený, uzavretý). Pre tieto chaty sú niektoré funkcie (napríklad id) odlišné, čo niekedy spôsobuje určité problémy.

Predpokladajme, že je koniec roka 2019 a aj hrdina našej doby, známy Man-Orchestra (administrátor, právnik, špecialista na informačnú bezpečnosť, programátor a prakticky MVP) Evgeniy V. rozlišuje premennú $i od poľa, zvládol slučky, pozrite sa, že o pár rokov zvládne aj Chocolatey a potom Paralelné spracovanie s PowerShell и Paralelne pre každý objekt príde to.

1. Premýšľame o tom, čo náš bot urobí

Nemal som žiadne nápady, musel som premýšľať. Už som napísal bot-notebook. Nechcel som urobiť robota, „ktorý niekam niečo pošle“. Na pripojenie k Azure potrebujete kreditnú kartu, ale odkiaľ ju študent získa? Treba poznamenať, že všetko nie je také zlé: hlavné mraky dávajú nejaký druh testovacieho obdobia zadarmo (stále však potrebujete číslo kreditnej karty - a zdá sa, že z toho bude odpočítaný dolár. Nepamätám si, či bol vrátený neskôr.)

Bez AI ML nie je také zaujímavé robiť robota, chudobného básnika, tkáča.

Rozhodol som sa vyrobiť bota, ktorý mi bude (alebo nie mne) pripomínať anglické slová zo slovníka.
Aby ste sa vyhli manipulácii s databázou, slovník sa uloží do textového súboru a aktualizuje sa ručne.
V tomto prípade je úlohou ukázať základy práce a nie vyrobiť aspoň čiastočne hotový výrobok.

2. Prvýkrát skúšať čo a ako

Vytvorme priečinok C:poshtranslate
Najprv sa pozrime, aký druh powershell máme, poďme spustiť ISE cez štart-run
powershell ise
alebo nájdite Powershell ISE v nainštalovaných programoch.
Po spustení sa otvorí obvyklý známy „nejaký editor“; ak neexistuje žiadne textové pole, môžete vždy kliknúť na „Súbor - vytvoriť nový“.

Pozrime sa na verziu powershell - do textového poľa napíšte:

get-host 

a stlačte F5.

Powershell ponúkne uloženie - “Skript, ktorý sa chystáte spustiť, sa uloží.”, súhlasíme a uložíme súbor z powershell s názvom v C: poshtranslate myfirstbotBT100.

Po spustení v spodnom textovom okne dostaneme tabuľku údajov:

Name             : Windows PowerShell ISE Host
Version          : 5.1.(и так далее)

Mám niečo 5.1, to stačí. Ak máte starý Windows 7/8, nevadí - hoci PowerShell bude potrebné aktualizovať na verziu 5 - napr. inštrukcie.

Do príkazového riadku nižšie napíšte Get-Date, stlačte Enter, pozrite sa na čas, prejdite do koreňového priečinka s príkazom
cd
a vymažte obrazovku príkazom cls (nie, nemusíte použiť rm)

Teraz sa pozrime, čo funguje a ako - napíšme ani nie kód, ale dva riadky a pokúsme sa pochopiť, čo robia. Zakomentujme riadok s get-host symbolom # a trochu pridajte.

# Пример шаблона бота 
# get-host
<# это пример многострочного комментария #>
$TimeNow = Get-Date
$TimeNow

(Zaujímavé je, že v rozbaľovacom zozname formátovania kódu na Habré sú dva tucty možností - ale Powershell tam nie je. Je tam Dos. Je tam Perl.)

A spustíme kód stlačením F5 alebo ">" z GUI.

Získame výstup:

Saturday, December 8, 2019 21:00:50 PM (или что-то типа)

Teraz sa pozrime na tieto dva riadky a niekoľko zaujímavých bodov, aby sme sa k tomu v budúcnosti nevracali.

Na rozdiel od Pascalu (a nielen) sa PowerShell sám snaží určiť, aký typ priradiť premennej; viac podrobností o tom je napísané v článku Vzdelávací program o písaní v programovacích jazykoch
Vytvorením premennej $TimeNow a jej priradením hodnoty aktuálneho dátumu a času (Get-Date) sa teda nemusíme príliš zaoberať tým, aký typ údajov tam bude.

Je pravda, že táto nevedomosť môže neskôr bolieť, ale to bude na neskôr. Nižšie v texte bude uvedený príklad.
Pozrime sa, čo máme. Spustite (na príkazovom riadku)

$TimeNow | Get-member

a dostanete stranu nezrozumiteľného textu

Príklad nezrozumiteľného textu číslo 1

PS C:> $TimeNow | Get-member
   TypeName: System.DateTime
Name                 MemberType     Definition                                                                                                                                       
----                 ----------     ----------                                                                                                                                       
Add                  <b>Method         </b>datetime Add(timespan value)  
..
DisplayHint          NoteProperty   DisplayHintType DisplayHint=DateTime                                                                                                             
Date                 <b>Property       </b>datetime Date {get;}                                                                                                                             
Year                 Property       int Year {get;}   
..                                                                                                                               
DateTime             ScriptProperty System.Object DateTime {get=if ((& { Set-StrictMode -Version 1; $this.DisplayHint }) -ieq  "Date")...                                         

Ako vidíte, premenná typu TypeName: System.DateTime bola vytvorená s množstvom metód (v zmysle toho, čo môžeme robiť s týmto objektom premennej) a vlastností.

Zavolajme $TimeNow.DayOfYear — dostaneme číslo dňa v roku.
Zavolajme $TimeNow.DayOfYear | Get-Member - dostaneme TypeName: System.Int32 a skupina metód.
Zavolajme $TimeNow.ToUniversalTime() - a získajte čas v UTC

Debugger

Niekedy sa stáva, že je potrebné vykonať program až po určitý riadok a vidieť stav programu v danom momente. Na tento účel má ISE funkciu Debug – toggle break point
Niekde do stredu vložte bod prerušenia, spustite tieto dva riadky a uvidíte, ako prestávka vyzerá.

3. Pochopenie interakcie s telegramovým robotom

Samozrejme, ešte viac literatúry bolo napísané o interakcii s robotom, so všetkými getpush a tak ďalej, ale otázka teórie sa môže zvážiť voliteľne.

V našom prípade je potrebné:

  • Naučte sa posielať niečo v korešpondencii
  • Naučte sa niečo získať z korešpondencie

3.1 Naučiť sa niečo posielať v korešpondencii a prijímať z nej

Malý kód - časť 3

Write-output "This is part 3"
$MyToken = "1234544311:AbcDefNNNNNNNNNNNNN"
$MyChatID = "123456789"
$MyProxy = "http://1.2.3.4:5678" 

$TimeNow = Get-Date
$TimeNow.ToUniversalTime()
$ScriptDir = Split-Path $script:MyInvocation.MyCommand.Path
$BotVersion = "BT102"

$MyText01 = "Life is directed motion - " + $TimeNow

$URL4SEND = "https://api.telegram.org/bot$MyToken/sendMessage?chat_id=$MyChatID&text=$MyText01"

Invoke-WebRequest -Uri $URL4SEND

a v Ruskej federácii v tomto bode dostaneme chybu Nedá sa pripojiť k vzdialenému serveru.

Alebo ho nedostaneme - závisí to od telekomunikačného operátora a od toho, či je server proxy nakonfigurovaný a funkčný
Ostáva už len pridať proxy. Upozorňujeme, že používanie nešifrovaného a vo všeobecnosti podvodného proxy je mimoriadne nebezpečné pre vaše zdravie.

Úloha nájsť fungujúci proxy nie je veľmi náročná - väčšina publikovaných http proxy funguje. Myslím, že ten piaty sa mi osvedčil.

Syntax pomocou proxy:

Invoke-WebRequest -Uri $URL4SEND -Proxy $MyProxy

Ak dostanete správu v chate s robotom, potom je všetko v poriadku, môžete pokračovať. Ak nie, pokračujte v ladení.

Môžete vidieť, na čo sa premení váš reťazec $URL4SEND, a skúste si to vyžiadať v prehliadači takto:

$URL4SEND2 = '"'+$URL4SEND+'"'
start chrome $URL4SEND2 

3.2. Naučili sme sa, ako napísať „niečo“ v chate, teraz si to skúsme prečítať

Pridajme ďalšie 4 riadky a uvidíme, čo je vnútri cez | stať sa členom

$URLGET = "https://api.telegram.org/bot$MyToken/getUpdates"
$MyMessageGet = Invoke-WebRequest -Uri $URLGET -Method Get -Proxy $MyProxy
Write-Host "Get-Member"
$MyMessageGet | Get-Member

To najzaujímavejšie je nám poskytnuté

Content           Property   string Content {get;}  
ParsedHtml        Property   mshtml.IHTMLDocument2 ParsedHtml {get;}                                    
RawContent        Property   string RawContent {get;set;}

Pozrime sa, čo v nich je:

Write-Host "ParsedHtml"
$MyMessageGet.ParsedHtml # тут интересное
Write-Host "RawContent"
$MyMessageGet.RawContent # и тут интересное, но еще к тому же и читаемое. 
Write-Host "Content"
$MyMessageGet.Content

Ak všetko funguje pre vás, dostanete dlhý rad ako:

{"ok":true,"result":[{"update_id":12345678,
"message":{"message_id":3,"from":{"id"

Našťastie v predtým publikovanom článku Telegram bot pre správcu systému tento riadok (áno, podľa $MyMessageGet.RawContent | get-member je System.String), bol už rozobraný.

4. Spracujte, čo dostanete (my už vieme, ako niečo poslať)

Ako už bolo napísané tu, najpotrebnejšie veci spočívajú v obsahu. Poďme sa na to pozrieť bližšie.

Najprv napíšeme pár ďalších fráz do robota z webového rozhrania alebo z telefónu

/message1
/message2
/message3

a pozrite sa cez prehliadač na adresu, ktorá bola vytvorená v premennej $URLGET.

Uvidíme niečo ako:

{"ok":true,"result":[{"update_id":NNNNNNN,
"message":{"message_id":10, .. "text":"/message1"
"message":{"message_id":11, .. "text":"/message2 
"message":{"message_id":12, .. "text":"/message3 

Čo to je? Nejaký zložitý objekt z polí objektov obsahujúcich koncový identifikátor správy, identifikátor chatu, identifikátor odosielania a množstvo ďalších informácií.

Nemusíme však zisťovať, „čo je to za objekt“ – časť práce už bola vykonaná za nás. Pozrime sa, čo je vo vnútri:

Čítanie prijatých správ alebo časť 4

Write-Host "This is part 4" <# конечно эта строка нам не нужна в итоговом тексте, но по ней удобно искать. #> 

$Content4Pars01 = ConvertFrom-Json $MyMessageGet.Content
$Content4Pars01 | Get-Member
$Content4Pars01.result
$Content4Pars01.result[0]
$Content4Pars01.result[0] | Get-Member
$Content4Pars01.result[0].update_id
$Content4Pars01.result[0].message
$Content4Pars01.result[0].message.text
$Content4Pars01.result[1].message.text
$Content4Pars01.result[2].message.text

5. Čo s tým máme teraz robiť?

Výsledný súbor si uložme pod názvom myfirstbotBT105 alebo pod názvom myfirstbotBTXNUMX, zmeňte názov a zakomentujte všetok už napísaný kód cez

<#start comment 105 end comment 105#>

Teraz sa musíme rozhodnúť, kde slovník získať (dobre, kde - na disku v súbore) a ako bude vyzerať.

Priamo v texte skriptu sa samozrejme dá napísať obrovský slovník, ale to je úplne vedľa.
Poďme sa teda pozrieť, s čím môže powershell normálne fungovať.
Vo všeobecnosti je mu jedno, s ktorým súborom má pracovať, na nás nezáleží.
Máme na výber: txt (môžete, ale prečo), csv, xml.
Môžeme sledovať všetkých? Pozrime sa na všetkých.
Vytvorme triedu MyVocabClassExample1 a premennú $MyVocabExample1
Podotýkam, že trieda je napísaná bez $

nejaký kód #5

write-host "This is part 5"
class MyVocabClassExample1 {
    [string]$Original  # слово
    [string]$Transcript
    [string]$Translate
    [string]$Example
    [int]$VocWordID # очень интересный момент. Использование int с его ограничениями может порой приводить к диким последствиям, для примера - недавний случай с SSD HPE. Изначально я не стал добавлять этот элемент, потом все же дописал и закомментировал.
    }

$MyVocabExample1 = [MyVocabClassExample1]::new()
$MyVocabExample1.Original = "Apple"
$MyVocabExample1.Transcript = "[ ˈapəl ]"
$MyVocabExample1.Translate = "Яблоко"
$MyVocabExample1.Example = "An apple is a sweet, edible fruit produced by an apple tree (Malus domestica)"
# $MyVocabExample1.$VocWordID = 1

$MyVocabExample2 = [MyVocabClassExample1]::new()
$MyVocabExample2.Original = "Pear"
$MyVocabExample2.Transcript = "[ pe(ə)r ]"
$MyVocabExample2.Translate = "Груша"
$MyVocabExample2.Example = "The pear (/ˈpɛər/) tree and shrub are a species of genus Pyrus"
# $MyVocabExample1.$VocWordID = 2

Skúsme to zapísať do súborov pomocou vzorka.

Nejaký kód #5.1

Write-Host $ScriptDir # надеюсь $ScriptDir вы не закомментировали 
$MyFilenameExample01 = $ScriptDir + "Example01.txt"
$MyFilenameExample02 = $ScriptDir + "Example02.txt"
Write-Host $MyFilenameExample01
Out-File  -FilePath $MyFilenameExample01 -InputObject $MyVocabExample1

Out-File  -FilePath $MyFilenameExample01 -InputObject -Append $MyVocabExample2
notepad $MyFilenameExample01

- a dostaneme chybu v riadku Out-File -FilePath $MyFilenameExample01 -InputObject -Append $MyVocabExample2.

Nechce dodať, ach, aká hanba.

$MyVocabExample3AsArray = @($MyVocabExample1,$MyVocabExample2)
Out-File  -FilePath $MyFilenameExample02 -InputObject $MyVocabExample3AsArray
notepad $MyFilenameExample02

Poďme sa pozrieť čo sa stalo. Skvelé zobrazenie textu – ale ako ho exportovať späť? Mal by som zaviesť nejaké oddeľovače textu, napríklad čiarky?

A nakoniec dostanete súbor „hodnoty oddelené čiarkou (CSV) A PRESTAŇTE ČAKAJTE.
#

$MyFilenameExample03 = $ScriptDir + "Example03.csv"
$MyFilenameExample04 = $ScriptDir + "Example04.csv"
Export-Csv  -Path $MyFilenameExample03 -InputObject $MyVocabExample1 
Export-Csv  -Path $MyFilenameExample03 -InputObject $MyVocabExample2 -Append 
Export-Csv  -Path $MyFilenameExample04 -InputObject $MyVocabExample3AsArray 

Ako je ľahko vidieť, MS sa svojou logikou nijako zvlášť nerozlišuje; pre podobný postup sa v jednom prípade používa -FilePath, v inom -Path.

Navyše v treťom súbore zmizol ruský jazyk, v štvrtom súbore sa ukázalo...no, niečo sa stalo. #TYPE System.Object[] 00
# “Count”, “Length”, “LongLength”,”Rank”, “SyncRoot”,”IsReadOnly”,”IsFixedSize”,”Issynchroned”
#
Trochu si to prepíšeme:

Export-Csv  -Path $MyFilenameExample03 -InputObject $MyVocabExample1 -Encoding Unicode
Export-Csv  -Path $MyFilenameExample03 -InputObject $MyVocabExample2 -Append -Encoding Unicode
notepad $MyFilenameExample03
notepad $MyFilenameExample04

Zdá sa, že to pomohlo, ale stále sa mi nepáči ten formát.

Nepáči sa mi hlavne, že nemôžem vkladať riadky z objektu priamo do súboru.
Mimochodom, odkedy sme začali zapisovať do súborov, môžeme začať viesť spúšťací denník? Čas máme ako premennú, môžeme nastaviť názov súboru.

Pravda, zatiaľ nie je čo písať, ale môžete popremýšľať, ako najlepšie rotovať polená.
Zatiaľ skúsme xml.

Nejaký xml

$MyFilenameExample05 = $ScriptDir + "Example05.xml"
$MyFilenameExample06 = $ScriptDir + "Example06.xml"
Export-Clixml  -Path $MyFilenameExample05 -InputObject $MyVocabExample1 
Export-Clixml  -Path $MyFilenameExample05 -InputObject $MyVocabExample2 -Append -Encoding Unicode
Export-Clixml  -Path $MyFilenameExample06 -InputObject $MyVocabExample3AsArray
notepad $MyFilenameExample05
notepad $MyFilenameExample06

Export do xml má mnoho výhod – čitateľnosť, export celého objektu a nie je potrebné vykonávať uppend.

Skúsme to čítať xml súbor.

Trochu čítania z xml

$MyFilenameExample06 = $ScriptDir + "Example06.xml"
$MyVocabExample4AsArray = Import-Clixml -Path $MyFilenameExample06
# $MyVocabExample4AsArray 
# $MyVocabExample4AsArray[0]
# и немного о совершенно неочевидных нюансах. Powershell время от времени ведет себя не так, как вроде бы как бы стоило бы ожидать бы.
# например у меня эти два вывода отличаются
# Write-Output $MyVocabExample4AsArray 
# write-host $MyVocabExample4AsArray 

Vráťme sa k úlohe. Napísali sme testovací súbor, prečítajte si ho, formát úložiska je jasný, v prípade potreby môžete napísať samostatný editor malých súborov na pridávanie a mazanie riadkov.

Pripomínam, že úlohou bolo vyrobiť malého cvičného robota.

Pracovný formát: Pošlem robotovi príkaz „example“, robot mi pošle náhodne vybrané slovo a prepis a po 10 sekundách mi pošle preklad a komentár. Vieme čítať príkazy, chceli by sme sa tiež naučiť automaticky vyberať a kontrolovať proxy a resetovať počítadlá správ do zabudnutia.

Odkomentujme všetko, čo bolo predtým zakomentované ako nepotrebné, zakomentujme teraz nepotrebné príklady pomocou txt a csv a uložme súbor ako verziu B106

Ó áno. Opäť niečo pošlime robotovi.

6. Odoslanie z funkcií a ďalšie

Pred spracovaním príjmu je potrebné vytvoriť funkciu na odoslanie „aspoň niečoho“ okrem testovacej správy.

Samozrejme, v tomto príklade budeme mať iba jedno odoslanie a iba jedno spracovanie, ale čo ak potrebujeme urobiť to isté niekoľkokrát?

Je jednoduchšie napísať funkciu. Máme teda premennú typu objekt $MyVocabExample4AsArray, načítanú zo súboru vo forme poľa až dvoch prvkov.
Poďme čítať.

Zároveň sa budeme zaoberať hodinami; budeme ich potrebovať neskôr (v tomto príklade ich v skutočnosti nebudeme potrebovať :)

Nejaký kód #6.1

Write-Output "This is Part 6"
$Timezone = (Get-TimeZone)
IF($Timezone.SupportsDaylightSavingTime -eq $True){
    $TimeAdjust =  ($Timezone.BaseUtcOffset.TotalSeconds + 3600) } # приведенное время
    ELSE{$TimeAdjust = ($Timezone.BaseUtcOffset.TotalSeconds) 
    }
    
function MyFirstFunction($SomeExampleForFunction1){
$TimeNow = Get-Date
$TimeNow.ToUniversalTime()
# $MyText02 = $TimeNow + " " + $SomeExampleForFunction1 # и вот тут мы получим ошибку
$MyText02 = $SomeExampleForFunction1 + " " + $TimeNow # а тут не получим, кто догадается почему - тот молодец.

$URL4SendFromFunction = "https://api.telegram.org/bot$MyToken/sendMessage?chat_id=$MyChatID&text=$MyText02"
Invoke-WebRequest -Uri $URL4SendFromFunction -Proxy $MyProxy
}

Ako môžete ľahko vidieť, funkcia volá $MyToken a $MyChatID, ktoré boli predtým pevne zakódované.

Nie je to potrebné a ak je $MyToken jeden pre každého robota, potom sa $MyChatID zmení v závislosti od chatu.

Keďže je to však príklad, budeme ho zatiaľ ignorovať.

Keďže $MyVocabExample4AsArray nie je pole, hoci je veľmi podobné jednému, potom nemôžeš to len tak zobrať požiadať o jeho dĺžku.

Opäť budeme musieť urobiť niečo, čo sa nedá - padák nie podľa kódu - vezmite a počítajte

Nejaký kód #6.2

$MaxRandomExample = 0 
foreach ($Obj in $MyVocabExample4AsArray) {
$MaxRandomExample ++
}
Write-Output $MaxRandomExample
$RandomExample = Get-Random -Minimum 0 -Maximum ($MaxRandomExample)
$TextForExample1 = $MyVocabExample4AsArray[$RandomExample].Original
# MyFirstFunction($TextForExample1)
# или в одну строку
# MyFirstFunction($MyVocabExample4AsArray[Get-Random -Minimum 0 -Maximum ($MaxRandomExample -1)].Example)
# Угадайте сами, какой пример легче читается посторонними людьми.

náhodný zaujímavá vlastnosť. Povedzme, že chceme prijať 0 alebo 1 (v poli máme len dva prvky). Pri nastavení hraníc 0..1 dostaneme „1“?
nie - nedostaneme to, máme špeciálny príklad Príklad 2: Získajte náhodné celé číslo medzi 0 a 99 Get-Random -Maximum 100
Preto pre 0..1 musíme nastaviť veľkosť 0..2 s maximálnym počtom prvkov = 1.

7. Spracovanie prichádzajúcich správ a maximálna dĺžka frontu

Kde sme sa zastavili skôr? máme prijatú premennú $MyMessageGet
a z neho získané $Content4Pars01, z ktorých nás zaujímajú prvky poľa Content4Pars01.result

$Content4Pars01.result[0].update_id
$Content4Pars01.result[0].message
$Content4Pars01.result[0].message.text

Pošlime robotovi /správa10, /správa11, /správa12, /slovo a znova /slovo a /ahoj.
Pozrime sa, čo máme:

$Content4Pars01.result[0].message.text
$Content4Pars01.result[2].message.text

Poďme si prejsť všetko prijaté a poslať odpoveď, ak bola správa /word
prípad konstruktu, ktorý niektorí popisujú ako if-elseif, sa nazýva v powershell cez prepínač. Zároveň nižšie uvedený kód používa kľúč -wildcard, čo je úplne zbytočné a dokonca škodlivé.

Nejaký kód #7.1

Write-Output "This is part 7"
Foreach ($Result in $Content4Pars01.result) # Да, можно сделать быстрее 
 { 
    switch -wildcard ($Result.message.text) 
            {
            "/word" {MyFirstFunction($TextForExample1)}
            }
}

Spustite skript niekoľkokrát. Za každý pokus o vykonanie dostaneme to isté slovo dvakrát, najmä ak sme sa pomýlili pri implementácii náhodného.

Ale prestaň. Neposlali sme znova /word, tak prečo sa správa znova spracováva?

Front na odosielanie správ robotovi má konečnú dĺžku (100 alebo 200 správ, myslím) a musí sa vyčistiť manuálne.

Toto je samozrejme popísané v dokumentácii, ale musíte si ju prečítať!

V tomto prípade potrebujeme parameter ?chat_id a &timeout, &limit, &parse_mode=HTML a &disable_web_page_preview=true ešte nie sú potrebné.

Dokumentácia pre telegram api je tu
Je tam bielo a anglicky:
Identifikátor prvej aktualizácie, ktorá sa má vrátiť. Musí byť o jeden väčší ako najvyšší medzi identifikátormi predtým prijatých aktualizácií. V predvolenom nastavení sa aktualizácie začínajú najskoršou
nepotvrdený aktualizácie sa vrátia. Aktualizácia sa považuje za potvrdenú hneď, ako sa zavolá getUpdates s ofset vyššia než jeho update_id. Záporný posun možno zadať na získanie aktualizácií počnúc aktualizáciou -offset od konca frontu aktualizácií. Všetky predchádzajúce aktualizácie budú zabudnuté.

Poďme sa pozrieť na:

$Content4Pars01.result[0].update_id
$Content4Pars01.result[1].update_id 
$Content4Pars01.result | select -last 1
($Content4Pars01.result | select -last 1).update_id

Áno, resetujeme to a trochu prepíšeme funkciu. Máme dve možnosti – odovzdať celú správu funkcii a celú ju spracovať vo funkcii, alebo dať iba ID správy a resetovať ju. Napríklad druhý vyzerá jednoduchšie.

Predtým vyzeral náš reťazec dopytu „všetky správy“.

$URLGET = "https://api.telegram.org/bot$MyToken/getUpdates"

a bude to vyzerať

$LastMessageId = ($Content4Pars01.result | select -last 1).update_id
$URLGET1 = "https://api.telegram.org/bot$mytoken/getUpdates?offset=$LastMessageId&limit=100" 
$MyMessageGet = Invoke-WebRequest -Uri $URLGET1 -Method Get -Proxy $MyProxy 

Nikto vám nezakazuje najprv všetky správy prijímať, spracovať a až po úspešnom spracovaní požiadavku nepotvrdenú -> potvrdenú.

Prečo má zmysel volať potvrdenie po dokončení všetkých procesov? Zlyhanie je možné uprostred vykonávania a ak napríklad u bezplatného chatbota nie je vynechanie jednej správy ničím výnimočným, potom ak spracovávate niečí plat alebo transakciu kartou, výsledok môže byť horší.

Ešte pár riadkov kódu

$LastMessageId = ($Content4Pars01.result | select -last 1).update_id  #ошибку в этом месте предполагается исправить самостоятельно. 
$URLGET1 = "https://api.telegram.org/bot$mytoken/getUpdates?offset=$LastMessageId&limit=100" 
Invoke-WebRequest -Uri $URLGET1 -Method Get -Proxy $MyProxy

8. Namiesto záveru

Základné funkcie - čítanie správ, resetovanie frontu, čítanie zo súboru a zápis do súboru sú vykonané a zobrazené.

Zostávajú už len štyri veci:

  • odoslanie správnej odpovede na požiadavku v chate
  • odoslanie odpovede na AKÝKOĽVEK chat, do ktorého bol robot pridaný
  • vykonávanie kódu v slučke
  • spustenie robota z plánovača systému Windows.

Všetky tieto úlohy sú jednoduché a dajú sa ľahko vykonať prečítaním dokumentácie o parametroch ako napr
Set-ExecutionPolicy Unrestricted a -ExecutionPolicy Bypass
cyklus formulára

$TimeToSleep = 3 # опрос каждые 3 секунды
$TimeToWork = 10 # минут
$HowManyTimes = $TimeToWork*60/$TimeToSleep # счетчик для цикла
$MainCounter = 0
for ($MainCounter=0; $MainCounter -le $HowManyTimes) {
sleep $TimeToSleep
$MainCounter ++

Ďakujem každému, kto číta.

Zdroj: hab.com

Pridať komentár