Compare commits

...

260 Commits

Author SHA1 Message Date
Kay Marquardt 8f23bca8a1
Update README.md 2023-04-18 00:27:39 +02:00
Kay Marquardt 420029c7f6
Update README.md 2023-04-18 00:25:50 +02:00
Kay Marquardt 02c73d432e
Update README.md 2023-04-18 00:20:06 +02:00
Kay Marquardt 1c2c07397a
Update 3_advanced.md 2023-04-17 15:36:10 +02:00
Kay Marquardt 8f742ff1fb
Explain data flow in interactive chats (finally) 2023-04-17 15:31:04 +02:00
Kay Marquardt d0c3156e7d
Include 2023-04-17 15:26:36 +02:00
Kay Marquardt d157f61cf2
Update 3_advanced.md 2023-04-17 14:03:29 +02:00
Kay Marquardt af7596f69a
Update 3_advanced.md 2023-04-17 13:54:01 +02:00
Kay Marquardt 0c25a11c5c
Update 3_advanced.md 2023-04-17 13:34:53 +02:00
Kay Marquardt 5653582d68
Update 3_advanced.md 2023-04-17 13:20:03 +02:00
Kay Marquardt b6dc3a0d93
Update 3_advanced.md 2023-04-17 13:06:21 +02:00
Kay Marquardt 4b2331b623
Update 3_advanced.md 2023-04-17 13:00:49 +02:00
Kay Marquardt 38f2cc475b
Update 4_expert.md
must use crontab -e
2023-04-12 08:18:08 +02:00
Kay Marquardt 74294f3fb4
Update bashbot.cron
change bashbot.sh to bashbot.rc
2023-04-10 09:48:50 +02:00
Kay Marquardt 4591b357d1
Merge pull request #193 from topkecleon/develop
Bashbot Version 1.52
2022-06-27 20:19:54 +02:00
Kay Marquardt (Gnadelwartz) bc71f37a2e resolve merge conflicts 2022-06-27 20:18:58 +02:00
Kay Marquardt (Gnadelwartz) 0dae2db8ac Bashbot Version 1.52 2022-06-27 19:55:03 +02:00
Kay Marquardt (Gnadelwartz) 1a83202a07 modules/chatMember: fix missing quotes around user_id 2022-06-27 19:49:55 +02:00
Kay Marquardt (Gnadelwartz) 58e6d0aaf6 modules/sendMessage: send_file: fix double escaped caption 2022-05-12 17:46:40 +02:00
Kay Marquardt (Gnadelwartz) 479f41c80e modules/send_message: send_file: fix double escaped caption 2022-05-12 17:42:18 +02:00
Kay Marquardt (Gnadelwartz) 67d75feace bashbot.rc: fix stop warning for mode 2022-05-03 23:48:49 +02:00
Kay Marquardt (Gnadelwartz) 1ffa890428 bashbot.rc: detect if bot run in both modes 2022-05-02 14:38:43 +02:00
Kay Marquardt 6490f6756f
Merge pull request #189 from z4zz/fix-cmd-args
fix split message arguments
2022-01-19 22:17:37 +01:00
z4zz 90d3d7551d
fix split message arguments
read into array
2022-01-19 14:36:37 +03:00
Kay Marquardt (Gnadelwartz) d06c162f16 Merge branch 'master' into develop 2021-11-06 08:32:33 +01:00
Kay Marquardt 89ac61afe7
Merge pull request #184 from konqiDAM/patch-1
Small documentaion fixes for edit_inline_buttons
2021-11-06 08:28:28 +01:00
konqi 369d7f8d4d
fix url quotes 2021-11-06 08:02:47 +01:00
konqi 93dc4a09d6
fix another edit_inline_buttons 2021-11-05 23:39:59 +01:00
konqi 738c5e5f6d
fix edit_inline_buttons
fix edit_inline_buttons instead of edit_inline_keyboard
2021-11-05 23:38:20 +01:00
Kay Marquardt (Gnadelwartz) aad42a52fb sendMEssage: send_keyboard: send text bigger 4k seperate 2021-09-29 16:56:47 +02:00
Kay Marquardt (Gnadelwartz) a2a3927117 hide url with token from crul argc e.g. ps command 2021-09-20 20:32:51 +02:00
Kay Marquardt (Gnadelwartz) 5205fe3990 mycommnds.sh: fix error403 example 2021-06-18 15:06:26 +02:00
Kay Marquardt (Gnadelwartz) 783bf30190 bin: send_message: implement read from stdin or file 2021-06-04 22:47:43 +02:00
Kay Marquardt a23370645f
Merge pull request #182 Bashbot Version 1.51
Version 1.51
2021-06-03 14:41:07 +02:00
Kay Marquardt (Gnadelwartz) 36d8604cde Bashbot Version 1.51 2021-06-03 14:21:40 +02:00
Kay Marquardt (Gnadelwartz) 6e66a2877c adjust webhook readme and /help message 2021-06-03 14:12:47 +02:00
Kay Marquardt (Gnadelwartz) 52fbb14770 add timeout to interactive example 2021-06-03 13:28:29 +02:00
Kay Marquardt (Gnadelwartz) c63f098fb0 fix: use REALME as SCRIPT if sourced 2021-06-03 13:00:37 +02:00
Kay Marquardt (Gnadelwartz) 69b1871eea fix Terminated message on stophook 2021-06-03 12:03:10 +02:00
Kay Marquardt (Gnadelwartz) 45efa80699 modules: startBot: adjust start message 2021-04-09 17:10:37 +02:00
Kay Marquardt (Gnadelwartz) b097f088c8 modules: processUpdates: fix inform chat if blocked 2021-04-05 02:32:59 +02:00
Kay Marquardt (Gnadelwartz) e4c13ddabe modules: processUpdates: optimize inform user if blocked 2021-04-04 11:45:37 +02:00
Kay Marquardt (Gnadelwartz) f7f55ea45f modules: processUpdates: inform user if he is blocked 2021-04-04 11:27:39 +02:00
Kay Marquardt (Gnadelwartz) 9b6aba0586 mycommands.sh: autoblock example 2021-04-04 11:22:34 +02:00
Kay Marquardt (Gnadelwartz) ecaecfee6f fix dev version 2021-03-24 12:07:49 +01:00
Kay Marquardt (Gnadelwartz) 4c4ba0ba5e bashbot: add error Pocessing to SendJsonRetry 2021-03-24 11:06:30 +01:00
Kay Marquardt (Gnadelwartz) f790d73e66 modules: process_update: ignore unknown update types 2021-03-23 17:25:10 +01:00
Kay Marquardt (Gnadelwartz) 79fc511bdb Merge branch 'develop' of github.com:topkecleon/telegram-bot-bash into develop 2021-03-19 14:02:13 +01:00
Kay Marquardt (Gnadelwartz) 3501318d84 bashbot.rc: fix missing open { in pipe name 2021-03-19 14:01:30 +01:00
Kay Marquardt 443958aa5f
Merge pull request #179 from topkecleon/master
Merge pull request #177 from topkecleon/develop
2021-03-18 15:01:27 +01:00
Kay Marquardt (Gnadelwartz) 12157b380d bashbot.rc: fix hook status, harmonize messages for hook and poll 2021-03-18 14:58:18 +01:00
Kay Marquardt (Gnadelwartz) cbd74a7f72 bashbot.rc: fix default bashbot path 2021-03-18 14:12:48 +01:00
Kay Marquardt (Gnadelwartz) dedcc00b8c bashbot.rc: more/better run mode warnings 2021-03-18 14:09:42 +01:00
Kay Marquardt (Gnadelwartz) 721e433b47 bashbot.rc: make log for hook configurable 2021-03-18 12:44:17 +01:00
Kay Marquardt (Gnadelwartz) cbde841bae bashbot.rc: factor out status, warn if wrong status 2021-03-18 12:35:14 +01:00
Kay Marquardt (Gnadelwartz) f1ea49426b fix modules: jsshDB: fix removal of unwanted characters from untrusted input 2021-03-18 11:50:44 +01:00
Kay Marquardt (Gnadelwartz) e60ada0bfe revert modules: jsshDB: fix removal of unwanted characters from untrusted input 2021-03-18 11:30:53 +01:00
Kay Marquardt (Gnadelwartz) 85f7c074f4 bin: process_batch: output logmsg first on kill 2021-03-18 10:48:43 +01:00
Kay Marquardt (Gnadelwartz) 43cab461f8 modules: sendMessage: send_dice add bowling 2021-03-17 20:02:17 +01:00
Kay Marquardt (Gnadelwartz) 99950e6518 modules: jsshDB: fix removal of unwanted characters from untrusted input 2021-03-17 19:46:31 +01:00
Kay Marquardt 94aefbe4d5
Merge pull request #177 from topkecleon/develop
Prepare 1.45 release with final webhook and get-file support
2021-03-11 12:16:57 +01:00
Kay Marquardt (Gnadelwartz) 369124bada Bashbot Version 1.5 2021-03-10 08:39:17 +01:00
Kay Marquardt (Gnadelwartz) 8adca9beea final adjustments for v1.5 2021-03-08 08:06:35 +01:00
Kay Marquardt (Gnadelwartz) 41e6883817 dev: make-standalone: improvments, extra files, make-dist: exclude test 2021-03-07 09:09:48 +01:00
Kay Marquardt (Gnadelwartz) ae525c47e0 dev: make-standalone: fix standalone outside dev 2021-03-06 11:45:28 +01:00
Kay Marquardt (Gnadelwartz) 47a032d582 dev: make-standalone: include in distribution 2021-03-05 20:12:30 +01:00
Kay Marquardt (Gnadelwartz) 761aa46b66 dev: standalone: fix addons 2021-03-05 19:48:08 +01:00
Kay Marquardt (Gnadelwartz) a5b230646b bin: process_batch: output messages with date prefix 2021-03-05 12:33:15 +01:00
Kay Marquardt (Gnadelwartz) 24638662d3 bin: process_batch: delay between processing updates 2021-03-05 12:03:04 +01:00
Kay Marquardt (Gnadelwartz) b1af0f07e7 dev: version.sh: ask to update ALL files 2021-03-05 12:01:21 +01:00
Kay Marquardt (Gnadelwartz) c4e2981116 example: webhook: improvce doc for full processing 2021-03-05 11:48:06 +01:00
Kay Marquardt (Gnadelwartz) 235f26a0e9 dev: fix can't get remote version 2021-03-04 14:02:45 +01:00
Kay Marquardt (Gnadelwartz) 50777ceff7 startup: factor out bot_cleanup 2021-03-04 13:58:04 +01:00
Kay Marquardt (Gnadelwartz) fdb2b3ac7b bashbot.rc: fix runuser 2021-03-03 18:44:16 +01:00
Kay Marquardt (Gnadelwartz) 0a296eaaa1 bashbot polling mode 2021-03-03 18:37:57 +01:00
Kay Marquardt (Gnadelwartz) eb0c227615 bashbot.rc: fix background start 2021-03-03 18:23:09 +01:00
Kay Marquardt (Gnadelwartz) 7500ca0d12 modules: chatMember: fix user_is_botadmin 2021-03-03 15:57:58 +01:00
Kay Marquardt (Gnadelwartz) ac16103361 mycommands: use BOTADMIN 2021-03-03 15:33:40 +01:00
Kay Marquardt (Gnadelwartz) b78431eacd bin: fix missing include 2021-03-03 14:09:34 +01:00
Kay Marquardt (Gnadelwartz) b454827109 bin: use BOTNAME BOTADMIN 2021-03-03 13:40:51 +01:00
Kay Marquardt (Gnadelwartz) e6838d1436 always set BOTADMIN 2021-03-03 13:27:07 +01:00
Kay Marquardt (Gnadelwartz) 53e936ee65 bashbot.rc: nohup for webhook 2021-03-03 09:05:16 +01:00
Kay Marquardt (Gnadelwartz) ec90ce820d example: mention bashbot.rc 2021-03-03 09:00:41 +01:00
Kay Marquardt (Gnadelwartz) 859ce92379 bashbot.rc: webhook usage 2021-03-03 08:55:49 +01:00
Kay Marquardt (Gnadelwartz) fff79d6daf examples: minimal support for full processing 2021-03-03 08:49:50 +01:00
Kay Marquardt (Gnadelwartz) e098aee321 bashbot.rc: fix name, user, start command 2021-03-02 18:32:09 +01:00
Kay Marquardt (Gnadelwartz) 4854d0d051 bashbot.rc: fix webhook 2021-03-02 18:26:41 +01:00
Kay Marquardt (Gnadelwartz) 7b8e391479 bin: process_batch: fix options bashbot.rc: support webhook 2021-03-02 18:05:14 +01:00
Kay Marquardt (Gnadelwartz) 24158142f9 init: bashbot.rc: bashbotdir 2021-03-01 19:40:53 +01:00
Kay Marquardt (Gnadelwartz) a9ac7eaeda example: webhook: small doc updates 2021-03-01 13:22:49 +01:00
Kay Marquardt (Gnadelwartz) a473e25dfd example: webhook: small doc updates 2021-03-01 12:59:06 +01:00
Kay Marquardt (Gnadelwartz) b6e90af4fa examples: webhook: Full webhook processing 2021-03-01 08:30:11 +01:00
Kay Marquardt (Gnadelwartz) 0859354be8 example: webhook: default and full webhook processing 2021-02-28 17:13:25 +01:00
Kay Marquardt (Gnadelwartz) 5dd24c3958 bin: process-batch: implement startbot for webhook 2021-02-28 16:51:28 +01:00
Kay Marquardt (Gnadelwartz) dda86e3496 bin: process_xxx: replace BOTADMIN with id of bot admin 2021-02-28 14:15:26 +01:00
Kay Marquardt (Gnadelwartz) 941598d01f bin: add process_batch for processing updates from file 2021-02-27 16:57:07 +01:00
Kay Marquardt (Gnadelwartz) 84ff8cec15 webhook: save json as one line 2021-02-27 16:46:04 +01:00
Kay Marquardt (Gnadelwartz) f7842f4f60 bin: bashbot_inc: fix full path, add WEBHOOK path 2021-02-27 13:39:59 +01:00
Kay Marquardt (Gnadelwartz) 34923ddabe MEONLY: fix and simplify 2021-02-26 06:45:50 +01:00
Kay Marquardt (Gnadelwartz) 2131911625 restart == resume 2021-02-25 19:58:00 +01:00
Kay Marquardt (Gnadelwartz) f4d45d814f example: webhook limitations 2021-02-25 19:20:09 +01:00
Kay Marquardt (Gnadelwartz) f4323e48b5 doc: no jobs with webhook 2021-02-24 16:33:03 +01:00
Kay Marquardt (Gnadelwartz) c57e9273fb mycommnds: clearer message in errorProcessing examples 2021-02-22 08:26:20 +01:00
Kay Marquardt (Gnadelwartz) 6b8ad9783a use cleanEscape for more logging 2021-02-21 23:34:34 +01:00
Kay Marquardt (Gnadelwartz) 17efeeb903 doc: rephrase jsshDB intro 2021-02-21 08:16:33 +01:00
Kay Marquardt (Gnadelwartz) ac71000519 doc: small fixes 2021-02-21 07:51:56 +01:00
Kay Marquardt (Gnadelwartz) 1a0642bcce doc: JSSHDB_UNSET value 2021-02-21 07:45:21 +01:00
Kay Marquardt (Gnadelwartz) 192fae8a37 modules: jsshDB: do not save unset marked values 2021-02-20 16:48:56 +01:00
Kay Marquardt (Gnadelwartz) 70724427d9 webhook: stay with simple mode 2021-02-20 08:34:42 +01:00
Kay Marquardt (Gnadelwartz) 8b18f25c88 bin: process_updates: use process_multi for preprocessing 2021-02-18 18:59:27 +01:00
Kay Marquardt (Gnadelwartz) 882efa8f1a doc: fix backticks 2021-02-17 13:00:53 +01:00
Kay Marquardt (Gnadelwartz) fdbfcebc7c doc: backticks, new set_chat_xxx functions 2021-02-17 12:54:00 +01:00
Kay Marquardt (Gnadelwartz) f7897fd41b modules: sendMessage: delete_message: return chat_id also 2021-02-17 12:29:41 +01:00
Kay Marquardt (Gnadelwartz) 473d802aab fix checkUploadFile 2021-02-17 10:20:45 +01:00
Kay Marquardt b1e6e0fc50
Merge pull request #176 from topkecleon/master
Bashbot Version 1.41
2021-02-17 09:45:43 +01:00
Kay Marquardt aee7bae141
Merge branch 'develop' into master 2021-02-17 09:42:35 +01:00
Kay Marquardt (Gnadelwartz) 622a394494 Bashbot Version 1.41 2021-02-17 08:54:24 +01:00
Kay Marquardt (Gnadelwartz) 3f848ac17d fix: escape all $ for weebhook also 2021-02-17 08:49:39 +01:00
Kay Marquardt (Gnadelwartz) 8efbfcaab9 modules: jsonDB: delete backticks in Json2Array input 2021-02-17 08:35:17 +01:00
Kay Marquardt (Gnadelwartz) d6f37afa3a example/webhook: add botname to fifo 2021-02-15 15:17:50 +01:00
Kay Marquardt (Gnadelwartz) 9958b5b5e1 fix dice cheating in example :-) 2021-02-14 10:46:26 +01:00
Kay Marquardt (Gnadelwartz) 77ffbabf22 unescape: keep \uxxx UTF-8 encoding 2021-02-10 21:30:42 +01:00
Kay Marquardt (Gnadelwartz) 82a57a77ed modules: chatMember: set_chatadmin_title 2021-02-10 21:16:03 +01:00
Kay Marquardt (Gnadelwartz) b1f6a0b230 modules: factor out checkUploadFile 2021-02-10 21:11:15 +01:00
Kay Marquardt (Gnadelwartz) 785e769460 modules: chatMember: set_chat_photo 2021-02-10 20:50:04 +01:00
Kay Marquardt (Gnadelwartz) 805a74eb6d test: process_message: fix test files 2021-02-10 19:52:52 +01:00
Kay Marquardt (Gnadelwartz) 6b07242179 test: split process_message test files for better coverage 2021-02-10 19:38:17 +01:00
Kay Marquardt (Gnadelwartz) e67e43dd2e mycommands: react on user sent dice 2021-02-10 10:38:21 +01:00
Kay Marquardt (Gnadelwartz) 2f4ef69971 test: process-message: add and fix tests 2021-02-10 09:05:00 +01:00
Kay Marquardt (Gnadelwartz) 429f271939 modules: processUpdates: /_dice_received 2021-02-09 20:12:22 +01:00
Kay Marquardt (Gnadelwartz) 193ca1e5b9 doc: add MESSAGE[DICE] MESSAGE[CAPTION] 2021-02-09 08:39:50 +01:00
Kay Marquardt (Gnadelwartz) a7d85e352c modules: proseccUpdates: get sent dice 2021-02-09 07:31:12 +01:00
Kay Marquardt (Gnadelwartz) c58fa22b7a modules: move delete_message to sendMessage.sh 2021-02-08 20:01:20 +01:00
Kay Marquardt (Gnadelwartz) d3a1cecf1f add error process to delete_message 2021-02-08 19:56:01 +01:00
Kay Marquardt (Gnadelwartz) f842730645 modules: fix ERROR description in error processing 2021-02-08 19:53:42 +01:00
Kay Marquardt (Gnadelwartz) 117255a958 modules: implement processError in sendMessage.sh 2021-02-08 18:41:54 +01:00
Kay Marquardt (Gnadelwartz) 066274c943 add inital custom error processing 2021-02-08 17:55:43 +01:00
Kay Marquardt (Gnadelwartz) 897458a37f mycommands: update send_dice example 2021-02-08 17:17:44 +01:00
Kay Marquardt (Gnadelwartz) b2fc4052fc mycommands.sh: add send_dice example 2021-02-07 20:44:58 +01:00
Kay Marquardt (Gnadelwartz) 62b6b618d5 doc: add send_dice, sendMessage: optimze send_dice emoji selection 2021-02-07 19:32:36 +01:00
Kay Marquardt (Gnadelwartz) 069570e4ed bin: add send_dice.sh 2021-02-07 18:57:15 +01:00
Kay Marquardt (Gnadelwartz) a9ed559383 modules: send_dice: accept more formats, allow false reply_to 2021-02-07 18:35:19 +01:00
Kay Marquardt (Gnadelwartz) 2f6f3bd4d8 test: fix init test 2021-02-07 18:01:34 +01:00
Kay Marquardt (Gnadelwartz) eee5458232 modules: add send_dice 2021-02-07 18:00:25 +01:00
Kay Marquardt (Gnadelwartz) 52d1ac5618 modules: sendMessage: add copy_message 2021-02-07 17:05:34 +01:00
Kay Marquardt (Gnadelwartz) 429c230627 init: improve change user for regular users 2021-02-07 16:56:35 +01:00
Kay Marquardt (Gnadelwartz) a6ff405cc5 fix: alias not always working, init: improve for unprivileged user, guess touser from config file 2021-02-07 11:02:01 +01:00
Kay Marquardt (Gnadelwartz) 34455c2c4c modules: fix/improve error logging 2021-02-07 10:20:09 +01:00
Kay Marquardt (Gnadelwartz) 9d36f23b14 Version 1.41: fix never working file download 2021-02-06 18:04:11 +01:00
Kay Marquardt (Gnadelwartz) ad1b91f3bc finish get_file rework: remove URLS[*] logging obfuscation 2021-02-06 17:45:52 +01:00
Kay Marquardt (Gnadelwartz) ccac62dd72 download_file: return normalised absolute path 2021-02-06 17:38:37 +01:00
Kay Marquardt (Gnadelwartz) 5294d00ae3 doc: move get_file download_file to own section 2021-02-06 17:19:07 +01:00
Kay Marquardt (Gnadelwartz) b91e96dce1 doc: use FILEURL 2021-02-06 16:52:25 +01:00
Kay Marquardt (Gnadelwartz) 5212df422e fix never working file download 2021-02-06 16:05:18 +01:00
Kay Marquardt (Gnadelwartz) 0702d58ab0 download_file: use mktemp doc: do not download manually 2021-02-06 15:30:31 +01:00
Kay Marquardt (Gnadelwartz) 54673ac396 doc: more/better download_file examples 2021-02-06 14:05:50 +01:00
Kay Marquardt (Gnadelwartz) baa4e14ebc doc: adjust user visible changes to URLS and download_file 2021-02-06 12:08:24 +01:00
Kay Marquardt (Gnadelwartz) bc40a3fcbb change internal get_file / download_file API 2021-02-06 11:04:39 +01:00
Kay Marquardt (Gnadelwartz) 5a689d22de JsonEscape: handle \r \n also 2021-02-05 14:46:11 +01:00
Kay Marquardt (Gnadelwartz) 58fb001d1e clean escaped json before logging 2021-02-05 14:25:21 +01:00
Kay Marquardt d15b4f5070
Merge pull request #173 Version 1.40
Prepare Version 1.40
2021-02-04 18:50:39 +01:00
Kay Marquardt (Gnadelwartz) 6fe19556b7 Bashbot Version 1.40 2021-02-04 18:13:32 +01:00
Kay Marquardt (Gnadelwartz) f9dab50f84 small updates and fixes for 1.40 2021-02-02 20:33:22 +01:00
Kay Marquardt (Gnadelwartz) 1440d56f48 modules: better shorten URLS[*] 2021-02-02 09:18:25 +01:00
Kay Marquardt (Gnadelwartz) 969c7a9fbb webhook: fix some glitches 2021-02-01 19:37:24 +01:00
Kay Marquardt (Gnadelwartz) d876f758ee no debug_checks on source 2021-02-01 18:30:34 +01:00
Kay Marquardt (Gnadelwartz) 9ce139a689 bin: bashbot_env: set ME 2021-02-01 16:30:04 +01:00
Kay Marquardt (Gnadelwartz) 3a29a9dc4a doc: xlink webhook example 2021-02-01 12:58:57 +01:00
Kay Marquardt (Gnadelwartz) 737be16b3f doc: NOT IMPLEMENTED modules: improve webbhok message 2021-02-01 10:30:47 +01:00
Kay Marquardt (Gnadelwartz) 91a143ab15 bin: basshot_env: improve messages 2021-02-01 10:18:42 +01:00
Kay Marquardt (Gnadelwartz) c4d100e0ad source: better exit_source handling 2021-02-01 10:00:08 +01:00
Kay Marquardt (Gnadelwartz) e86c8dc116 source: return from source to avoid killing shell 2021-02-01 09:37:22 +01:00
Kay Marquardt (Gnadelwartz) c1aec9285e start: show already running bot 2021-02-01 09:02:22 +01:00
Kay Marquardt (Gnadelwartz) e4a983b16f modules: processUpdates: show sleep minutes 2021-02-01 08:59:53 +01:00
Kay Marquardt (Gnadelwartz) 4e7b3052de example: webhook: fix missing setup part 2021-01-31 21:30:28 +01:00
Kay Marquardt (Gnadelwartz) 6754273c6e example: webhook: rewrite setup 2021-01-31 21:18:40 +01:00
Kay Marquardt (Gnadelwartz) 5b0b121ba5 examples: webhook: make home and file configurable 2021-01-31 18:08:18 +01:00
Kay Marquardt (Gnadelwartz) a7c98d750c modules: processUpdates: conflict webhook slow start 2021-01-31 13:16:27 +01:00
Kay Marquardt (Gnadelwartz) 0dd5f83d5a modules: processUpdates: detect conflicting webhook 2021-01-31 12:42:41 +01:00
Kay Marquardt (Gnadelwartz) 342a5da97a fix _exec_if_function 2021-01-31 12:40:13 +01:00
Kay Marquardt (Gnadelwartz) 8034a5f055 bin: any_command fix reference location 2021-01-31 12:38:40 +01:00
Kay Marquardt (Gnadelwartz) f377e17e44 doc: small webhook desc fixes 2021-01-31 10:29:38 +01:00
Kay Marquardt (Gnadelwartz) bc3a3b3def doc: improve webhook desc 2021-01-31 10:19:33 +01:00
Kay Marquardt (Gnadelwartz) 4833712246 doc: webhook functions bin: do not show JSON.sh error 2021-01-31 10:00:15 +01:00
Kay Marquardt (Gnadelwartz) 2a3663a463 webhook: final index.php 2021-01-31 08:58:24 +01:00
Kay Marquardt (Gnadelwartz) a289cb8e5b examples: fix webhook description 2021-01-30 21:53:14 +01:00
Kay Marquardt (Gnadelwartz) 9316caa260 example: apache webhook example 2021-01-30 21:36:38 +01:00
Kay Marquardt (Gnadelwartz) c0f1af529e bin: process_update.sh webhook script 2021-01-30 20:18:54 +01:00
Kay Marquardt (Gnadelwartz) 1e49f6c2b1 modules: processUpdates rename process_client 2021-01-30 20:14:20 +01:00
Kay Marquardt (Gnadelwartz) 9cfeab9cdc modules: processUpdate fix webhook handling 2021-01-30 17:40:23 +01:00
Kay Marquardt (Gnadelwartz) 10d275c557 bin: any_command.sh for testing bashbot commands 2021-01-30 14:12:52 +01:00
Kay Marquardt (Gnadelwartz) 08b7b85d03 modules: processUpdates: start experimental webhooks support 2021-01-30 11:38:30 +01:00
Kay Marquardt (Gnadelwartz) c9daa822bb fix start 2021-01-29 20:55:54 +01:00
Kay Marquardt (Gnadelwartz) c693ab5bb9 modules: factor out processUpdates.sh 2021-01-29 20:48:31 +01:00
Kay Marquardt (Gnadelwartz) 7c748247d8 dev: make-dist: do not overwrite bashbot.conf 2021-01-27 21:23:39 +01:00
Kay Marquardt (Gnadelwartz) cfc4d2eed1 doc: chat_member_count 2021-01-27 19:34:08 +01:00
Kay Marquardt (Gnadelwartz) 41e2d09067 add chat_member_count 2021-01-27 19:30:03 +01:00
Kay Marquardt (Gnadelwartz) 279a9e7ca3 doc: add iBUTTON variables 2021-01-27 19:05:12 +01:00
Kay Marquardt (Gnadelwartz) a3eec98491 disbale obsolete download 2021-01-27 18:40:12 +01:00
Kay Marquardt (Gnadelwartz) e83f4d443f init: finalize external init 2021-01-27 16:29:58 +01:00
Kay Marquardt (Gnadelwartz) 0c0dc01f26 init: move to bin/bashbot_init.inc.sh 2021-01-27 16:19:43 +01:00
Kay Marquardt (Gnadelwartz) 3f331dc8e8 init: external init extension 2021-01-27 13:58:55 +01:00
Kay Marquardt (Gnadelwartz) ca9ea1bf31 init: fix msgs 2021-01-27 13:35:31 +01:00
Kay Marquardt (Gnadelwartz) b45efa3726 init: basic config for new conf file 2021-01-27 12:39:04 +01:00
Kay Marquardt (Gnadelwartz) 079eb1c289 fix running commands.sh in subshell 2021-01-27 11:54:48 +01:00
Kay Marquardt (Gnadelwartz) 5a0a5712dd doc: more button examples 2021-01-27 07:54:28 +01:00
Kay Marquardt (Gnadelwartz) 5192212782 doc: more complex buttons, rearrange inline again 2021-01-27 07:36:26 +01:00
Kay Marquardt (Gnadelwartz) 8c85c81f94 commands: fork commands.sh 2021-01-26 21:05:27 +01:00
Kay Marquardt (Gnadelwartz) cbf3945e4f mycommands: better iBUTTONS example 2021-01-26 20:59:10 +01:00
Kay Marquardt (Gnadelwartz) fa0cb75c60 doc: add inline_buttons, move inline_keybord to internal 2021-01-26 20:53:08 +01:00
Kay Marquardt (Gnadelwartz) 75e775606a modules: sendMessage: more comforable inline_buttons functions 2021-01-26 20:49:55 +01:00
Kay Marquardt (Gnadelwartz) e4ee88003e conf: BASHBOT_SLEEP use default, 10s and 2s as example 2021-01-26 19:44:40 +01:00
Kay Marquardt (Gnadelwartz) b096338c33 doc: add answer_callback_query 2021-01-26 14:51:50 +01:00
Kay Marquardt (Gnadelwartz) 2222875e2b modules: sendMessage: add answer_callback_query 2021-01-26 14:38:31 +01:00
Kay Marquardt (Gnadelwartz) b441384d4a iBUTTON: fix comamnds and mycommands processing 2021-01-26 14:34:25 +01:00
Kay Marquardt (Gnadelwartz) 08a05242f9 init: offer copy config only for new installations 2021-01-26 13:02:04 +01:00
Kay Marquardt (Gnadelwartz) bc414eef5a init: offer copy mycommands files 2021-01-26 12:57:27 +01:00
Kay Marquardt (Gnadelwartz) 47cab8021d bin: kickban + promote user 2021-01-25 22:32:14 +01:00
Kay Marquardt (Gnadelwartz) 6b102a728a doc: use USER[ID] CHAT[ID] in usage: 2021-01-25 20:34:50 +01:00
Kay Marquardt (Gnadelwartz) 70a3c194a0 doc: promote_chat_member 2021-01-25 20:17:38 +01:00
Kay Marquardt (Gnadelwartz) 5ceddde4e8 modules: chatMember: promote_chat_member 2021-01-25 19:44:45 +01:00
Kay Marquardt (Gnadelwartz) cc4ac1a816 better callback processing 2021-01-25 16:49:15 +01:00
Kay Marquardt (Gnadelwartz) 9584068ea3 add callback processing to commands and mycommands 2021-01-25 14:52:47 +01:00
Kay Marquardt (Gnadelwartz) c90b5658b3 doc: better xxx_keyboard description 2021-01-24 14:39:36 +01:00
Kay Marquardt (Gnadelwartz) cc7afdb149 doc: fix inline_keyboard frormat descritption 2021-01-24 14:15:01 +01:00
Kay Marquardt (Gnadelwartz) aa2c20b37e doc: add callback buttons 2021-01-24 13:52:44 +01:00
Kay Marquardt (Gnadelwartz) 461e748c92 iBUTTON: infrastructe seems to work 2021-01-24 13:04:20 +01:00
Kay Marquardt (Gnadelwartz) 1fe22a0345 modules: button url not starting with hhttp is sent as data 2021-01-24 12:30:56 +01:00
Kay Marquardt (Gnadelwartz) 9023b21791 test: adjust inline test 2021-01-24 12:03:12 +01:00
Kay Marquardt (Gnadelwartz) d9b3342c3c iBUTTONS: initial code for processing CallbackQuery buttons 2021-01-24 10:28:04 +01:00
Kay Marquardt (Gnadelwartz) f995eeea13 move JsonEscape up before sourcing other files 2021-01-23 14:06:55 +01:00
Kay Marquardt (Gnadelwartz) 78e4551107 fix set CHAT[ID] to new id on chat migration 2021-01-23 13:58:45 +01:00
Kay Marquardt (Gnadelwartz) 41e956d517 remove obsolete JsonGetXxx functions 2021-01-23 09:53:50 +01:00
Kay Marquardt (Gnadelwartz) 121f131bb4 dev: fix missing global flag in README.txt creation 2021-01-23 09:21:28 +01:00
Kay Marquardt (Gnadelwartz) 13052f01da README: mention JSON.awk 2021-01-23 09:12:48 +01:00
Kay Marquardt (Gnadelwartz) 2960e58941 doc: add edit_inline_keyboard 2021-01-22 23:44:15 +01:00
Kay Marquardt (Gnadelwartz) 8bb4b7e5ac bin: fix missing print_help arg 2021-01-22 21:22:16 +01:00
Kay Marquardt (Gnadelwartz) 28328013c7 bin: finally symlink send_edit_message.sh 2021-01-22 08:56:25 +01:00
Kay Marquardt (Gnadelwartz) 3378c1a5d1 dev: fix symlink counts as file :-( 2021-01-22 08:51:28 +01:00
Kay Marquardt (Gnadelwartz) 407194b23f dev: fix symlink bug in version.sh 2021-01-22 08:34:37 +01:00
Kay Marquardt (Gnadelwartz) 4371050206 bin: rename to edit_message.sh 2021-01-22 08:18:17 +01:00
Kay Marquardt (Gnadelwartz) db8f32b732 bin: add edit_buttons.sh 2021-01-22 08:14:19 +01:00
Kay Marquardt (Gnadelwartz) 662c6f48cb modules: add edit_inline_keyboard 2021-01-22 08:11:57 +01:00
Kay Marquardt (Gnadelwartz) e9543991ee add shellcheck for bashbot.conf 2021-01-21 19:51:04 +01:00
Kay Marquardt (Gnadelwartz) 07f026c6a7 bin: less duplicate code 2021-01-21 09:22:14 +01:00
Kay Marquardt (Gnadelwartz) 749eee74a4 dev: adjust make-standalone 2021-01-20 19:50:19 +01:00
Kay Marquardt (Gnadelwartz) 127cc85a2a load modules before commands.sh 2021-01-20 18:20:03 +01:00
Kay Marquardt (Gnadelwartz) 85a178d68a doc: small fix for _button_row 2021-01-20 16:27:59 +01:00
Kay Marquardt (Gnadelwartz) f6e319c6eb doc: advise use of new _button_row helper function 2021-01-20 16:21:46 +01:00
Kay Marquardt (Gnadelwartz) f95b6c2e7d modules: _button_row empty button starts new row 2021-01-19 23:53:58 +01:00
Kay Marquardt (Gnadelwartz) 6c91a327a6 bin: send_buttons.sh use _button_row to create buttons 2021-01-19 23:35:26 +01:00
Kay Marquardt (Gnadelwartz) 8854e03ece modules: JsonEscape button text 2021-01-19 23:22:38 +01:00
Kay Marquardt (Gnadelwartz) e923e2e8fc modules: helper function _button_row 2021-01-19 23:18:26 +01:00
Kay Marquardt (Gnadelwartz) f2dd64c900 modules: send_button remove double JsonEscape 2021-01-19 22:56:58 +01:00
Kay Marquardt (Gnadelwartz) f66e5702b0 bin: send_buttons.sh 2021-01-19 21:58:50 +01:00
Kay Marquardt (Gnadelwartz) 0ee6973143 modules: send_inline_keyboard fix empty text, improve doc 2021-01-19 21:55:39 +01:00
Kay Marquardt (Gnadelwartz) b0f653b705 dev: save date of last commit 2021-01-19 18:09:45 +01:00
Kay Marquardt (Gnadelwartz) 427f670a02 bashbot.sh: fix UPD array access to use "real" strings 2021-01-19 17:47:15 +01:00
Kay Marquardt (Gnadelwartz) 62378f7cf6 replace old JsoenGetXxx functions with direct UPD access 2021-01-19 17:24:53 +01:00
Kay Marquardt (Gnadelwartz) fe1fb75748 make _round_float more LANG independent (C not installed) 2021-01-18 21:09:30 +01:00
103 changed files with 3305 additions and 1405 deletions

View File

@ -6,136 +6,6 @@
<meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=yes" />
<title>Bashbot README</title>
<style>
html {
line-height: 1.5;
font-family: Georgia, serif;
font-size: 20px;
color: #1a1a1a;
background-color: #fdfdfd;
}
body {
margin: 0 auto;
max-width: 36em;
padding-left: 50px;
padding-right: 50px;
padding-top: 50px;
padding-bottom: 50px;
hyphens: auto;
word-wrap: break-word;
text-rendering: optimizeLegibility;
font-kerning: normal;
}
@media (max-width: 600px) {
body {
font-size: 0.9em;
padding: 1em;
}
}
@media print {
body {
background-color: transparent;
color: black;
font-size: 12pt;
}
p, h2, h3 {
orphans: 3;
widows: 3;
}
h2, h3, h4 {
page-break-after: avoid;
}
}
p {
margin: 1em 0;
}
a {
color: #1a1a1a;
}
a:visited {
color: #1a1a1a;
}
img {
max-width: 100%;
}
h1, h2, h3, h4, h5, h6 {
margin-top: 1.4em;
}
h5, h6 {
font-size: 1em;
font-style: italic;
}
h6 {
font-weight: normal;
}
ol, ul {
padding-left: 1.7em;
margin-top: 1em;
}
li > ol, li > ul {
margin-top: 0;
}
blockquote {
margin: 1em 0 1em 1.7em;
padding-left: 1em;
border-left: 2px solid #e6e6e6;
color: #606060;
}
code {
font-family: Menlo, Monaco, 'Lucida Console', Consolas, monospace;
font-size: 85%;
margin: 0;
}
pre {
margin: 1em 0;
overflow: auto;
}
pre code {
padding: 0;
overflow: visible;
}
.sourceCode {
background-color: transparent;
overflow: visible;
}
hr {
background-color: #1a1a1a;
border: none;
height: 1px;
margin: 1em 0;
}
table {
margin: 1em 0;
border-collapse: collapse;
width: 100%;
overflow-x: auto;
display: block;
font-variant-numeric: lining-nums tabular-nums;
}
table caption {
margin-bottom: 0.75em;
}
tbody {
margin-top: 0.5em;
border-top: 1px solid #1a1a1a;
border-bottom: 1px solid #1a1a1a;
}
th {
border-top: 1px solid #1a1a1a;
padding: 0.25em 0.5em 0.25em 0.5em;
}
td {
padding: 0.125em 0.5em 0.25em 0.5em;
}
header {
margin-bottom: 4em;
text-align: center;
}
#TOC li {
list-style: none;
}
#TOC a:not(:hover) {
text-decoration: none;
}
code{white-space: pre-wrap;}
span.smallcaps{font-variant: small-caps;}
span.underline{text-decoration: underline;}
@ -204,7 +74,6 @@
code span.va { color: #19177c; } /* Variable */
code span.vs { color: #4070a0; } /* VerbatimString */
code span.wa { color: #60a0b0; font-weight: bold; font-style: italic; } /* Warning */
.display.math{display: block; text-align: center; margin: 0.5rem auto;}
</style>
<!--[if lt IE 9]>
<script src="//cdnjs.cloudflare.com/ajax/libs/html5shiv/3.7.3/html5shiv-printshiv.min.js"></script>
@ -223,8 +92,8 @@ Written by Drew (@topkecleon) and Kay M (@gnadelwartz).
<p>Released to the public domain wherever applicable. Elsewhere, consider it released under the <a href="http://www.wtfpl.net/txt/copying/">WTFPLv2</a>.</p>
<p>Linted by <a href="https://github.com/koalaman/shellcheck">#ShellCheck</a></p>
<h2>Prerequisites</h2>
<p>Uses <a href="http://github.com/dominictarr/JSON.sh">JSON.sh</a> and the magic of sed.</p>
<p>Bashbot is written in bash. It depends on commands typically available in a Linux/Unix Environment. For more concrete information on the common commands provided by recent versions of <a href="https://en.wikipedia.org/wiki/List_of_GNU_Core_Utilities_commands">coreutils</a>, <a href="https://en.wikipedia.org/wiki/BusyBox#Commands">busybox</a> or <a href="https://landley.net/toybox/help.html">toybox</a>, see <a href="doc/7_develop.md#common-commands">Developer Notes</a>.</p>
<p>Uses <a href="http://github.com/dominictarr/JSON.sh">JSON.sh</a>/<a href="https://github.com/step-/JSON.awk">JSON.awk</a> and the magic of sed.</p>
<p>Bashbot is written in bash. It depends on commands typically available in a Linux/Unix Environment. For more information on commands provided by recent versions of <a href="https://en.wikipedia.org/wiki/List_of_GNU_Core_Utilities_commands">coreutils</a>, <a href="https://en.wikipedia.org/wiki/BusyBox#Commands">busybox</a> or <a href="https://landley.net/toybox/help.html">toybox</a>, see <a href="doc/7_develop.md#common-commands">Developer Notes</a>.</p>
<p><strong>Note for MacOS and BSD Users:</strong> Bashbot will not run without installing additional software as it uses modern bash and (gnu) grep/sed features. See <a href="doc/0_install.md">Install Bashbot</a>.</p>
<p><strong>Note for embedded systems:</strong> You need to install a "real" bash as the vanilla installation of busybox or toybox is not sufficient. See <a href="doc/0_install.md">Install Bashbot</a>.</p>
<p>Bashbot <a href="https://github.com/topkecleon/telegram-bot-bash">Documentation</a> and <a href="https://github.com/topkecleon/telegram-bot-bash/releases">Downloads</a> are available on <a href="https://www.github.com">www.github.com</a>.</p>
@ -284,34 +153,35 @@ Written by Drew (@topkecleon) and Kay M (@gnadelwartz).
<li>Setup your environment</li>
<li>Bashbot test suite</li>
</ul></li>
<li><a href="examples/README.md">Examples Directory</a></li>
<li><a href="examples">Examples Directory</a></li>
<li><a href="examples/webhook">Webhook Example</a></li>
</ul>
<h3>Your very first bashbot in a nutshell</h3>
<p>To install and run bashbot you need access to a Linux/Unix command line with bash, a <a href="https://telegram.org">Telegram client</a> and a mobile phone <a href="https://telegramguide.com/create-a-telegram-account/">with a Telegram account</a>.</p>
<p>First you need to <a href="doc/1_firstbot.md">create a new Telegram Bot token</a> for your bot and write it down.</p>
<p>Now open a Linux/Unix terminal with bash, create a new directory, change to it and install telegram-bot-bash:</p>
<div class="sourceCode" id="cb1"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb1-1"><a href="#cb1-1" aria-hidden="true" tabindex="-1"></a><span class="co"># create bot dir</span></span>
<span id="cb1-2"><a href="#cb1-2" aria-hidden="true" tabindex="-1"></a><span class="fu">mkdir</span> mybot</span>
<span id="cb1-3"><a href="#cb1-3" aria-hidden="true" tabindex="-1"></a><span class="bu">cd</span> mybot</span>
<span id="cb1-4"><a href="#cb1-4" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb1-5"><a href="#cb1-5" aria-hidden="true" tabindex="-1"></a><span class="co"># download latest release with wget or from https://github.com/topkecleon/telegram-bot-bash/releases/latest</span></span>
<span id="cb1-6"><a href="#cb1-6" aria-hidden="true" tabindex="-1"></a><span class="fu">wget</span> <span class="st">&quot;https://github.com/</span><span class="va">$(</span><span class="fu">wget</span> <span class="at">-q</span> <span class="st">&quot;https://github.com/topkecleon/telegram-bot-bash/releases/latest&quot;</span> <span class="at">-O</span> <span class="at">-</span> <span class="kw">|</span> <span class="fu">egrep</span> <span class="st">&#39;/.*/download/.*/.*tar.gz&#39;</span> <span class="at">-o</span><span class="va">)</span><span class="st">&quot;</span></span>
<span id="cb1-7"><a href="#cb1-7" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb1-8"><a href="#cb1-8" aria-hidden="true" tabindex="-1"></a><span class="co"># Extract the tar archive and go into bot dir</span></span>
<span id="cb1-9"><a href="#cb1-9" aria-hidden="true" tabindex="-1"></a><span class="fu">tar</span> <span class="at">-xzf</span> <span class="pp">*</span>.tar.gz</span>
<span id="cb1-10"><a href="#cb1-10" aria-hidden="true" tabindex="-1"></a><span class="bu">cd</span> telegram-bot-bash</span>
<span id="cb1-11"><a href="#cb1-11" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb1-12"><a href="#cb1-12" aria-hidden="true" tabindex="-1"></a><span class="co"># initialize your bot</span></span>
<span id="cb1-13"><a href="#cb1-13" aria-hidden="true" tabindex="-1"></a><span class="co"># Enter your bot token when asked, all other questions can be answered by hitting the \&lt;Return\&gt; key.</span></span>
<span id="cb1-14"><a href="#cb1-14" aria-hidden="true" tabindex="-1"></a><span class="ex">./bashbot.sh</span> init</span>
<span id="cb1-15"><a href="#cb1-15" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb1-16"><a href="#cb1-16" aria-hidden="true" tabindex="-1"></a><span class="co"># Now start your bot</span></span>
<span id="cb1-17"><a href="#cb1-17" aria-hidden="true" tabindex="-1"></a><span class="ex">./bashbot.sh</span> start</span>
<span id="cb1-18"><a href="#cb1-18" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb1-19"><a href="#cb1-19" aria-hidden="true" tabindex="-1"></a><span class="ex">Bottoken</span> is valid ...</span>
<span id="cb1-20"><a href="#cb1-20" aria-hidden="true" tabindex="-1"></a><span class="ex">Bot</span> Name: yourbotname_bot</span>
<span id="cb1-21"><a href="#cb1-21" aria-hidden="true" tabindex="-1"></a><span class="ex">Session</span> Name: yourbotname_bot-startbot</span>
<span id="cb1-22"><a href="#cb1-22" aria-hidden="true" tabindex="-1"></a><span class="ex">Bot</span> started successfully.</span></code></pre></div>
<div class="sourceCode" id="cb1"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb1-1"><a href="#cb1-1"></a><span class="co"># create bot dir</span></span>
<span id="cb1-2"><a href="#cb1-2"></a><span class="fu">mkdir</span> mybot</span>
<span id="cb1-3"><a href="#cb1-3"></a><span class="bu">cd</span> mybot</span>
<span id="cb1-4"><a href="#cb1-4"></a></span>
<span id="cb1-5"><a href="#cb1-5"></a><span class="co"># download latest release with wget or from https://github.com/topkecleon/telegram-bot-bash/releases/latest</span></span>
<span id="cb1-6"><a href="#cb1-6"></a><span class="fu">wget</span> <span class="st">&quot;https://github.com/</span><span class="va">$(</span><span class="fu">wget</span> -q <span class="st">&quot;https://github.com/topkecleon/telegram-bot-bash/releases/latest&quot;</span> -O - <span class="kw">|</span> <span class="fu">egrep</span> <span class="st">&#39;/.*/download/.*/.*tar.gz&#39;</span> -o<span class="va">)</span><span class="st">&quot;</span></span>
<span id="cb1-7"><a href="#cb1-7"></a></span>
<span id="cb1-8"><a href="#cb1-8"></a><span class="co"># Extract the tar archive and go into bot dir</span></span>
<span id="cb1-9"><a href="#cb1-9"></a><span class="fu">tar</span> -xzf *.tar.gz</span>
<span id="cb1-10"><a href="#cb1-10"></a><span class="bu">cd</span> telegram-bot-bash</span>
<span id="cb1-11"><a href="#cb1-11"></a></span>
<span id="cb1-12"><a href="#cb1-12"></a><span class="co"># initialize your bot</span></span>
<span id="cb1-13"><a href="#cb1-13"></a><span class="co"># Enter your bot token when asked, all other questions can be answered by hitting the \&lt;Return\&gt; key.</span></span>
<span id="cb1-14"><a href="#cb1-14"></a><span class="ex">./bashbot.sh</span> init</span>
<span id="cb1-15"><a href="#cb1-15"></a></span>
<span id="cb1-16"><a href="#cb1-16"></a><span class="co"># Now start your bot</span></span>
<span id="cb1-17"><a href="#cb1-17"></a><span class="ex">./bashbot.sh</span> start</span>
<span id="cb1-18"><a href="#cb1-18"></a></span>
<span id="cb1-19"><a href="#cb1-19"></a><span class="ex">Bottoken</span> is valid ...</span>
<span id="cb1-20"><a href="#cb1-20"></a><span class="ex">Bot</span> Name: yourbotname_bot</span>
<span id="cb1-21"><a href="#cb1-21"></a><span class="ex">Session</span> Name: yourbotname_bot-startbot</span>
<span id="cb1-22"><a href="#cb1-22"></a><span class="ex">Bot</span> started successfully.</span></code></pre></div>
<p>Now open the Telegram App on your mobile phone and start a chat with your bot (<em>your bot's username is shown after 'Bot Name:'</em>):</p>
<pre><code>/start
@ -324,7 +194,8 @@ Available commands:
/info
This is bashbot, the Telegram bot written entirely in bash.
It features background tasks and interactive chats, and can serve as an interface for CLI programs.</code></pre>
It features background tasks and interactive chats, and can serve as an interface for CLI programs.
</code></pre>
<p>For more Information on how to install, customize and use your new bot, read the <a href="#Documentation">Documentation</a>.</p>
<h3>Log files</h3>
<p>Bashbot actions are logged to <code>BASHBOT.log</code>. Telegram send/receive errors are logged to <code>ERROR.log</code>. Start bashbot in debug mode to see all messages sent to / received from Telegram, as well as bash command error messages.</p>
@ -334,13 +205,14 @@ It features background tasks and interactive chats, and can serve as an interfac
| |__ ERROR.log # connection errors from / to Telegram API
| |
| |__ DEBUG.log # stdout/stderr of you bot (debug mode enabled)
| |__ MESSAGE.log # full text of all message send/received (debug mode enabled)</code></pre>
| |__ MESSAGE.log # full text of all message send/received (debug mode enabled)
</code></pre>
<hr />
<h2>Security Considerations</h2>
<p>Running a Telegram Bot means it is connected to the public and you never know what's send to your Bot.</p>
<p>Bash scripts in general are not designed to be bulletproof, so consider this Bot as a proof of concept. Bash programmers often struggle with 'quoting hell' and globbing, see <a href="https://unix.stackexchange.com/questions/171346/security-implications-of-forgetting-to-quote-a-variable-in-bash-posix-shells">Implications of wrong quoting</a>.</p>
<p>Whenever you are processing input from untrusted sources (messages, files, network) you must be as careful as possible (e.g. set IFS appropriately, disable globbing with <code>set -f</code> and quote everything). In addition remove unused scripts and examples from your Bot (e.g. everything in <code>example/</code>) and disable/remove all unused bot commands.</p>
<p>It's important to escape or remove <code>$</code> in input from user, files or network (<em>as bashbot does</em>). One of the powerful features of Unix shells is variable and command substitution using <code>${}</code> and<code>$()</code> can lead to remote code execution (RCE) or remote information disclosure (RID) bugs if unescaped <code>$</code> is included in untrusted input (e.g. <code>$$</code> or <code>$(rm -rf /*)</code>).</p>
<p>It's important to escape or remove <code>$</code> and ` in input from user, files or network (<em>as bashbot does</em>). One of the powerful features of Unix shells is variable and command substitution using <code>${var}</code>, <code>$(cmd)</code> and `cmd` can lead to remote code execution (RCE) or remote information disclosure (RID) bugs if unescaped <code>$</code> or ` is included in untrusted input (e.g. <code>$$</code> or <code>$(rm -rf /*)</code>).</p>
<p>A powerful tool to improve your scripts is <code>shellcheck</code>. You can <a href="https://www.shellcheck.net/">use it online</a> or <a href="https://github.com/koalaman/shellcheck#installing">install shellcheck locally</a>. Shellcheck is used extensively in bashbot development to ensure a high code quality (e.g. it's not allowed to push changes without passing all shellcheck tests). In addition bashbot has a <a href="doc/7_develop.md">test suite</a> to check if important functionality is working as expected.</p>
<h3>Use printf whenever possible</h3>
<p>If you're writing a script that accepts external input (e.g. from the user as arguments or the file system), you shouldn't use echo to display it. <a href="https://unix.stackexchange.com/a/6581">Use printf whenever possible</a>.</p>
@ -349,8 +221,9 @@ It features background tasks and interactive chats, and can serve as an interfac
<p><strong>Never run your Bot as root, this is the most dangerous you can do!</strong> Usually the user 'nobody' has almost no rights on Linux/Unix systems. See <a href="doc/4_expert.md">Expert use</a> on how to run your Bot as an other user.</p>
<h3>Secure your Bot installation</h3>
<p><strong>Your Bot configuration must not be readable by other users.</strong> Everyone who can read your Bots token is able to act as your Bot and has access to all chats the Bot is in!</p>
<p>Everyone with read access to your Bot files can extract your Bots data. Especially your Bot config in<code>config.jssh</code> must be protected against other users. No one except you should have write access to the Bot files. The Bot should be restricted to have write access to<code>count.jssh</code> and <code>data-bot-bash</code> only, all other files must be write protected.</p>
<p>To set access rights for your bashbot installation to a reasonable default run<code>sudo ./bashbot.sh init</code> after every update or change to your installation directory.</p>
<p>Everyone with read access to your Bot files can extract your Bots data. Especially your Bot config in <code>config.jssh</code> must be protected against other users. No one except you should have write access to the Bot files. The Bot should be restricted to have write access to <code>count.jssh</code>, <code>data-bot-bash/</code> and <code>logs/</code> only, all other files must be write protected.</p>
<p>To set access rights for your bashbot installation to a reasonable default run <code>sudo ./bashbot.sh init</code> after every update or change to your installation directory.</p>
<p><em>Note</em>: Keep old log files in a safe place or even better delete them, they are GDPR relevant and <a href="https://github.com/topkecleon/telegram-bot-bash/issues/174">may contain information</a> you don't want to be public.</p>
<h2>FAQ</h2>
<h3>Is this Bot insecure?</h3>
<p>Bashbot is not more (in)secure than a Bot written in another language. We have done our best to make it as secure as possible. But YOU are responsible for the bot commands you wrote and you should know about the risks ...</p>
@ -364,32 +237,32 @@ It features background tasks and interactive chats, and can serve as an interfac
<li>no database, not event driven, not object oriented ...</li>
</ul>
<h3>Can I have the single bashbot.sh file back?</h3>
<p>At the beginning bashbot was simply the file<code>bashbot.sh</code> that you could copy everywhere and run the bot. Now we have 'commands.sh', 'mycommands.sh', 'modules/*.sh' and much more.</p>
<p>Hey no problem, if you are finished with your cool bot, run<code>dev/make-standalone.sh</code> to create a stripped down version of your bot containing only 'bashbot.sh' and 'commands.sh'! For more information see <a href="doc/7_develop.md">Create a stripped down version of your Bot</a>.</p>
<p>At the beginning bashbot was simply the file <code>bashbot.sh</code> that you could copy everywhere and run the bot. Now we have 'commands.sh', 'mycommands.sh', 'modules/*.sh' and much more.</p>
<p>Hey no problem, if you are finished with your cool bot, run <code>dev/make-standalone.sh</code> to create a stripped down version of your bot containing only 'bashbot.sh' and 'commands.sh'! For more information see <a href="doc/7_develop.md">Create a stripped down version of your Bot</a>.</p>
<h3>Can I send messages from CLI and scripts?</h3>
<p>Of course you can send messages from command line and scripts! Simply install bashbot as <a href="#Your-really-first-bashbot-in-a-nutshell">described here</a>, send the message '/start' to set yourself as botadmin and then stop the bot with <code>./bashbot.sh stop</code>.</p>
<p>Bashbot provides some ready to use scripts for sending messages from command line in <code>bin/</code> dir, e.g. <code>send_message.sh</code>.</p>
<div class="sourceCode" id="cb4"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb4-1"><a href="#cb4-1" aria-hidden="true" tabindex="-1"></a><span class="ex">bin/send_message.sh</span> BOTADMIN <span class="st">&quot;This is my first message send from CLI&quot;</span></span>
<span id="cb4-2"><a href="#cb4-2" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb4-3"><a href="#cb4-3" aria-hidden="true" tabindex="-1"></a><span class="ex">bin/send_message.sh</span> <span class="at">--help</span></span></code></pre></div>
<div class="sourceCode" id="cb4"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb4-1"><a href="#cb4-1"></a><span class="ex">bin/send_message.sh</span> BOTADMIN <span class="st">&quot;This is my first message send from CLI&quot;</span></span>
<span id="cb4-2"><a href="#cb4-2"></a></span>
<span id="cb4-3"><a href="#cb4-3"></a><span class="ex">bin/send_message.sh</span> --help</span></code></pre></div>
<p>You can also source bashbot for use in your scripts, for more information see <a href="doc/4_expert.md">Expert Use</a>.</p>
<h3>Blocked by telegram?</h3>
<p>This may happen if too many or wrong requests are sent to api.telegram.org, e.g. using a invalid token or invalid API calls. If the block stay for longer time you can ask telegram service to unblock your IP-Address.</p>
<p>You can check with curl or wget if you are blocked by Telegram:</p>
<div class="sourceCode" id="cb5"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb5-1"><a href="#cb5-1" aria-hidden="true" tabindex="-1"></a><span class="ex">curl</span> <span class="at">-m</span> 10 https://api.telegram.org/bot</span>
<span id="cb5-2"><a href="#cb5-2" aria-hidden="true" tabindex="-1"></a><span class="co">#curl: (28) Connection timed out after 10001 milliseconds</span></span>
<span id="cb5-3"><a href="#cb5-3" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb5-4"><a href="#cb5-4" aria-hidden="true" tabindex="-1"></a><span class="fu">wget</span> <span class="at">-t</span> 1 <span class="at">-T</span> 10 https://api.telegram.org/bot</span>
<span id="cb5-5"><a href="#cb5-5" aria-hidden="true" tabindex="-1"></a><span class="co">#Connecting to api.telegram.org (api.telegram.org)|46.38.243.234|:443... failed: Connection timed out.</span></span>
<span id="cb5-6"><a href="#cb5-6" aria-hidden="true" tabindex="-1"></a></span>
<span id="cb5-7"><a href="#cb5-7" aria-hidden="true" tabindex="-1"></a><span class="ex">nc</span> <span class="at">-w</span> 2 api.telegram.org 443 <span class="kw">||</span> <span class="bu">echo</span> <span class="st">&quot;your IP seems blocked by telegram&quot;</span></span>
<span id="cb5-8"><a href="#cb5-8" aria-hidden="true" tabindex="-1"></a><span class="co">#your IP seems blocked by telegram</span></span></code></pre></div>
<div class="sourceCode" id="cb5"><pre class="sourceCode bash"><code class="sourceCode bash"><span id="cb5-1"><a href="#cb5-1"></a><span class="ex">curl</span> -m 10 https://api.telegram.org/bot</span>
<span id="cb5-2"><a href="#cb5-2"></a><span class="co">#curl: (28) Connection timed out after 10001 milliseconds</span></span>
<span id="cb5-3"><a href="#cb5-3"></a></span>
<span id="cb5-4"><a href="#cb5-4"></a><span class="fu">wget</span> -t 1 -T 10 https://api.telegram.org/bot</span>
<span id="cb5-5"><a href="#cb5-5"></a><span class="co">#Connecting to api.telegram.org (api.telegram.org)|46.38.243.234|:443... failed: Connection timed out.</span></span>
<span id="cb5-6"><a href="#cb5-6"></a></span>
<span id="cb5-7"><a href="#cb5-7"></a><span class="ex">nc</span> -w 2 api.telegram.org 443 <span class="kw">||</span> <span class="bu">echo</span> <span class="st">&quot;your IP seems blocked by telegram&quot;</span></span>
<span id="cb5-8"><a href="#cb5-8"></a><span class="co">#your IP seems blocked by telegram</span></span></code></pre></div>
<p>Bashbot offers the option to recover from broken connections (blocked). Therefore you can provide a function named <code>bashbotBlockRecover()</code> in <code>mycommands.sh</code>, the function is called every time when a broken connection is detected.</p>
<p>Possible actions are: Check if network is working, change IP-Address or simply wait some time. See <code>mycommnds.sh.dist</code> for an example.</p>
<hr />
<p>@Gnadelwartz</p>
<h2>That's it all guys!</h2>
<p>If you feel that there's something missing or if you found a bug, feel free to submit a pull request!</p>
<h4>$$VERSION$$ v1.30-0-g3266427</h4>
<h4>$$VERSION$$ v1.52-0-g1a83202</h4>
</body>
</html>

View File

@ -10,11 +10,19 @@ Elsewhere, consider it released under the [WTFPLv2](http://www.wtfpl.net/txt/cop
Linted by [#ShellCheck](https://github.com/koalaman/shellcheck)
---
**Bashbot** is created by old-fashioned shell hackers to show that it's possible to write a bot in Bash.
It is designed for **simple** use cases and easily integrates with Linux tasks.
For bots that serve a lot of users or a heavy workload, I strongly recommend using a dedicated bot framework.
---
## Prerequisites
Uses [JSON.sh](http://github.com/dominictarr/JSON.sh) and the magic of sed.
Uses [JSON.sh](http://github.com/dominictarr/JSON.sh)/[JSON.awk](https://github.com/step-/JSON.awk) and the magic of sed.
Bashbot is written in bash. It depends on commands typically available in a Linux/Unix Environment.
For more concrete information on the common commands provided by recent versions of [coreutils](https://en.wikipedia.org/wiki/List_of_GNU_Core_Utilities_commands), [busybox](https://en.wikipedia.org/wiki/BusyBox#Commands) or [toybox](https://landley.net/toybox/help.html), see [Developer Notes](doc/7_develop.md#common-commands).
For more information on commands provided by recent versions of [coreutils](https://en.wikipedia.org/wiki/List_of_GNU_Core_Utilities_commands), [busybox](https://en.wikipedia.org/wiki/BusyBox#Commands) or [toybox](https://landley.net/toybox/help.html), see [Developer Notes](doc/7_develop.md#common-commands).
**Note for MacOS and BSD Users:** Bashbot will not run without installing additional software as it uses modern bash and (gnu) grep/sed features. See [Install Bashbot](doc/0_install.md).
@ -63,7 +71,8 @@ Bashbot [Documentation](https://github.com/topkecleon/telegram-bot-bash) and [Do
* Modules, addons, events
* Setup your environment
* Bashbot test suite
* [Examples Directory](examples/README.md)
* [Examples Directory](examples)
* [Webhook Example](examples/webhook)
### Your very first bashbot in a nutshell
@ -145,8 +154,9 @@ Whenever you are processing input from untrusted sources (messages, files, netwo
(e.g. set IFS appropriately, disable globbing with `set -f` and quote everything). In addition remove unused scripts and examples
from your Bot (e.g. everything in `example/`) and disable/remove all unused bot commands.
It's important to escape or remove `$` in input from user, files or network (_as bashbot does_).
One of the powerful features of Unix shells is variable and command substitution using `${}` and`$()` can lead to remote code execution (RCE) or remote information disclosure (RID) bugs if unescaped `$` is included in untrusted input (e.g. `$$` or `$(rm -rf /*)`).
It's important to escape or remove `$` and \` in input from user, files or network (_as bashbot does_).
One of the powerful features of Unix shells is variable and command substitution using `${var}`, `$(cmd)` and \`cmd\` can lead to remote
code execution (RCE) or remote information disclosure (RID) bugs if unescaped `$` or \` is included in untrusted input (e.g. `$$` or `$(rm -rf /*)`).
A powerful tool to improve your scripts is `shellcheck`. You can [use it online](https://www.shellcheck.net/) or
[install shellcheck locally](https://github.com/koalaman/shellcheck#installing). Shellcheck is used extensively in bashbot development
@ -168,9 +178,11 @@ For the same reason every file your Bot can read is in danger of being disclosed
### Secure your Bot installation
**Your Bot configuration must not be readable by other users.** Everyone who can read your Bots token is able to act as your Bot and has access to all chats the Bot is in!
Everyone with read access to your Bot files can extract your Bots data. Especially your Bot config in`config.jssh` must be protected against other users. No one except you should have write access to the Bot files. The Bot should be restricted to have write access to`count.jssh` and `data-bot-bash` only, all other files must be write protected.
Everyone with read access to your Bot files can extract your Bots data. Especially your Bot config in `config.jssh` must be protected against other users. No one except you should have write access to the Bot files. The Bot should be restricted to have write access to `count.jssh`, `data-bot-bash/` and `logs/` only, all other files must be write protected.
To set access rights for your bashbot installation to a reasonable default run`sudo ./bashbot.sh init` after every update or change to your installation directory.
To set access rights for your bashbot installation to a reasonable default run `sudo ./bashbot.sh init` after every update or change to your installation directory.
*Note*: Keep old log files in a safe place or even better delete them, they are GDPR relevant and [may contain information](https://github.com/topkecleon/telegram-bot-bash/issues/174) you don't want to be public.
## FAQ
@ -188,9 +200,9 @@ Well, that's a damn good question... maybe because I'm a Unix admin from the sto
- no database, not event driven, not object oriented ...
### Can I have the single bashbot.sh file back?
At the beginning bashbot was simply the file`bashbot.sh` that you could copy everywhere and run the bot. Now we have 'commands.sh', 'mycommands.sh', 'modules/*.sh' and much more.
At the beginning bashbot was simply the file `bashbot.sh` that you could copy everywhere and run the bot. Now we have 'commands.sh', 'mycommands.sh', 'modules/*.sh' and much more.
Hey no problem, if you are finished with your cool bot, run`dev/make-standalone.sh` to create a stripped down version of your bot containing only
Hey no problem, if you are finished with your cool bot, run `dev/make-standalone.sh` to create a stripped down version of your bot containing only
'bashbot.sh' and 'commands.sh'! For more information see [Create a stripped down version of your Bot](doc/7_develop.md).
### Can I send messages from CLI and scripts?
@ -238,4 +250,4 @@ See `mycommnds.sh.dist` for an example.
If you feel that there's something missing or if you found a bug, feel free to submit a pull request!
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -39,18 +39,21 @@ Linted by #ShellCheck
Prerequisites
Uses JSON.sh [http://github.com/dominictarr/JSON.sh] and the magic of sed.
Uses JSON.sh [http://github.com/dominictarr/JSON.sh]/JSON.awk [https://github.com/step-/
JSON.awk] and the magic of sed.
Bashbot is written in bash. It depends on commands typically available in a Linux/Unix
Environment. For more concrete information on the common commands provided by recent
versions of coreutils [https://en.wikipedia.org/wiki/List_of_GNU_Core_Utilities_commands],
busybox or toybox, see Developer_Notes.
Environment. For more information on commands provided by recent versions of coreutils
[https://en.wikipedia.org/wiki/List_of_GNU_Core_Utilities_commands], busybox [https://
en.wikipedia.org/wiki/BusyBox#Commands] or toybox [https://landley.net/toybox/help.html],
see Developer Notes [doc/7_develop.md#common-commands].
Note for MacOS and BSD Users: Bashbot will not run without installing additional software
as it uses modern bash and (gnu) grep/sed features. See Install Bashbot [doc/
0_install.md].
Note for embedded systems: You need to install a "real" bash as the vanilla installation
of busybox or toybox is not sufficient. See Install Bashbot [doc/0_install.md].
Bashbot Documentation [https://github.com/topkecleon/telegram-bot-bash] and Downloads are
available on www.github.com.
Bashbot Documentation [https://github.com/topkecleon/telegram-bot-bash] and Downloads
[https://github.com/topkecleon/telegram-bot-bash/releases] are available on www.github.com
[https://www.github.com].
Documentation
@ -109,13 +112,15 @@ Documentation
o Setup your environment
o Bashbot test suite
* Examples Directory [examples/README.md]
* Examples Directory [examples]
* Webhook Example [examples/webhook]
Your very first bashbot in a nutshell
To install and run bashbot you need access to a Linux/Unix command line with bash, a
Telegram client [https://telegram.org] and a mobile phone with_a_Telegram_account.
Telegram client [https://telegram.org] and a mobile phone with a Telegram account [https:/
/telegramguide.com/create-a-telegram-account/].
First you need to create a new Telegram Bot token [doc/1_firstbot.md] for your bot and
write it down.
Now open a Linux/Unix terminal with bash, create a new directory, change to it and install
@ -195,15 +200,17 @@ Whenever you are processing input from untrusted sources (messages, files, netwo
must be as careful as possible (e.g. set IFS appropriately, disable globbing with set -
f and quote everything). In addition remove unused scripts and examples from your Bot
(e.g. everything in example/) and disable/remove all unused bot commands.
It's important to escape or remove $ in input from user, files or network (as bashbot
does). One of the powerful features of Unix shells is variable and command substitution
using ${} and$() can lead to remote code execution (RCE) or remote information disclosure
(RID) bugs if unescaped $ is included in untrusted input (e.g. $$ or $(rm -rf /*)).
It's important to escape or remove $ and ` in input from user, files or network (as
bashbot does). One of the powerful features of Unix shells is variable and command
substitution using ${var}, $(cmd) and `cmd` can lead to remote code execution (RCE) or
remote information disclosure (RID) bugs if unescaped $ or ` is included in untrusted
input (e.g. $$ or $(rm -rf /*)).
A powerful tool to improve your scripts is shellcheck. You can use it online [https://
www.shellcheck.net/] or install_shellcheck_locally. Shellcheck is used extensively in
bashbot development to ensure a high code quality (e.g. it's not allowed to push changes
without passing all shellcheck tests). In addition bashbot has a test_suite to check if
important functionality is working as expected.
www.shellcheck.net/] or install shellcheck locally [https://github.com/koalaman/
shellcheck#installing]. Shellcheck is used extensively in bashbot development to ensure a
high code quality (e.g. it's not allowed to push changes without passing all shellcheck
tests). In addition bashbot has a test suite [doc/7_develop.md] to check if important
functionality is working as expected.
Use printf whenever possible
@ -226,11 +233,14 @@ Secure your Bot installation
Your Bot configuration must not be readable by other users. Everyone who can read your
Bots token is able to act as your Bot and has access to all chats the Bot is in!
Everyone with read access to your Bot files can extract your Bots data. Especially your
Bot config inconfig.jssh must be protected against other users. No one except you should
have write access to the Bot files. The Bot should be restricted to have write access
tocount.jssh and data-bot-bash only, all other files must be write protected.
To set access rights for your bashbot installation to a reasonable default runsudo ./
Bot config in config.jssh must be protected against other users. No one except you should
have write access to the Bot files. The Bot should be restricted to have write access to
count.jssh, data-bot-bash/ and logs/ only, all other files must be write protected.
To set access rights for your bashbot installation to a reasonable default run sudo ./
bashbot.sh init after every update or change to your installation directory.
Note: Keep old log files in a safe place or even better delete them, they are GDPR
relevant and may contain information [https://github.com/topkecleon/telegram-bot-bash/
issues/174] you don't want to be public.
FAQ
@ -258,9 +268,9 @@ Nevertheless there are more reasons from my side:
Can I have the single bashbot.sh file back?
At the beginning bashbot was simply the filebashbot.sh that you could copy everywhere and
At the beginning bashbot was simply the file bashbot.sh that you could copy everywhere and
run the bot. Now we have 'commands.sh', 'mycommands.sh', 'modules/*.sh' and much more.
Hey no problem, if you are finished with your cool bot, rundev/make-standalone.sh to
Hey no problem, if you are finished with your cool bot, run dev/make-standalone.sh to
create a stripped down version of your bot containing only 'bashbot.sh' and 'commands.sh'!
For more information see Create a stripped down version of your Bot [doc/7_develop.md].
@ -309,5 +319,5 @@ That's it all guys!
If you feel that there's something missing or if you found a bug, feel free to submit a
pull request!
$$VERSION$$ v1.30-0-g3266427
$$VERSION$$ v1.52-0-g1a83202

View File

@ -4,7 +4,7 @@
# this addon counts how many files, e.g. stickers, are sent to
# a chat and takes actions if threshold is reached
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# used events:
#

View File

@ -4,7 +4,7 @@
# Addons can register to bashbot events at startup
# by providing their name and a callback per event
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#
# If an event occurs each registered event function is called.
#

View File

@ -1,13 +1,14 @@
#!/bin/sh
#!/bin/bash
# description: Start or stop telegram-bash-bot
#
# example service script to run bashbot in background as specified user
#
# tested on: ubuntu, opensuse, debian
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# shellcheck disable=SC2009
# shellcheck disable=SC2181
# shellcheck disable=SC2250
#
### BEGIN INIT INFO
@ -31,53 +32,112 @@ runas="nobody"
# uncomment one of the example lines to fit your system
# runcmd="su ${runas} -s /bin/bash -c " # runasuser with *su*
# runcmd="runuser ${runas} -s /bin/bash -c " # runasuser with *runuser*
# runcmd="/usr/sbin/runuser ${runas} -s /bin/bash -c " # runasuser with *runuser*
# edit the values of the following lines to fit your config:
# your bot installation dir
bashbot="cd /usr/local/telegram-bot-bash; /usr/local/telegram-bot-bash/bashbot.sh"
# your bot name as given to botfather, e.g. mysomething_bot
name=""
[ -z "${name}" ] && name="unknown"
# your bot installation dir
bashbotdir="/usr/local/telegram-bot-bash"
databotdir="${bashbotdir}/data-bot-bash"
FIFO="${databotdir}/webhook-fifo-${name}"
# programs to run
bashbot="cd ${bashbotdir}; ${bashbotdir}/bashbot.sh"
webhook="cd ${bashbotdir}; nohup ${bashbotdir}/bin/process_batch.sh --startbot --watch ${FIFO}"
# set additionl parameter, e.g. debug
mode=""
# select logfile for webhook start stop and script errors
hooklog="DEBUG"
hooklog="WEBHOOK"
# END Configuration
#######################
[ "${name}" = "" ] && name="${runas}"
# check for bot status
stat=""
ps -f -u "${runas}" | grep "${name}" | grep -qF "bashbot.sh startbot"
if [ "$?" = "0" ]; then
# printf "bashbot (%s) is running in poll mode\n" "${name}"
stat="${stat} polling"
fi
ps -f -u "${runas}" | grep "${name}" | grep -qF "process_batch.sh --startbot"
if [ "$?" = "0" ]; then
#printf "bashbot (%s) is running in webhook mode\n" "${name}"
stat="${stat} webhook"
elif [ "${name}" != "unknown" ]; then
#printf "bashbot (%s) is stopped\n" "${name}"
stat="stop"
else
stat="unknown"
fi
case "$1" in
'start')
# shellcheck disable=SC2250
[ "${stat}" != "stop" ] && printf "Warning, bot is already running in mode: %s\n" "${stat}"
$runcmd "$bashbot start $mode" # >/dev/null 2>&1 </dev/null
RETVAL=$?
;;
'starthook')
[ -p "${FIFO}" ] || printf "Warning, webhook pipe not found: %s\n" "${FIFO##*/}"
[ "${stat}" != "stop" ] && printf "Warning, bot is already running in mode: %s\n" "${stat}"
printf "Starting bashbot in webhook mode ... "
$runcmd "$webhook $mode </dev/null &>>${bashbotdir}/logs/${hooklog}.log &" # >/dev/null 2>&1 </dev/null
sleep 1
$0 status
RETVAL=$?
;;
'stop')
# shellcheck disable=SC2250
[[ "${stat}" != *"poll"* ]] && printf "Warning, bot is not in poll mode: %s\n" "${stat}"
$runcmd "$bashbot stop $mode"
RETVAL=$?
;;
'status')
ps -f -u "${runas}" | grep "${name}" | grep -qF "bashbot.sh startbot"
if [ "$?" = "0" ]; then
printf "bashbot (%s) is running\n" "${name}"
RETVAL=0
else
printf "bashbot (%s) is stopped\n" "${name}"
RETVAL=1
'stophook')
[[ "${stat}" != *"hook"* ]] && printf "Warning, bot is not in webhook mode: %s\n" "${stat}"
printf "Stopping bashbot webhook mode ... "
KILLID="$(ps -f -u "${runas}" | grep "process_batch.sh --startbot" | sed -E 's/[^0-9]+([0-9]+).*/\1/' | tr -s "\r\n" " ")"
if [ -n "${KILLID}" ]; then
$runcmd "kill ${KILLID} 2>/dev/null; wait ${KILLID} 2>/dev/null"
sleep 1
fi
RETVAL=$?
$0 status
;;
'status')
case "${stat}" in
*"poll"*) printf "bashbot (%s) is running in polling mode\n" "${name}"
RETVAL=0
;;&
*"hook"*) printf "bashbot (%s) is running in webhook mode\n" "${name}"
RETVAL=0
;;
*"stop"*) printf "bashbot (%s) is not running\n" "${name}"
RETVAL=1
;;
*) printf "bashbot (%s) status is %s\n" "${name}" "${stat}"
RETVAL=2
;;
esac
;;
'restart'|'reload')
$0 stop; $0 start
RETVAL=$?
;;
'restarthook'|'reloadhook')
$0 stophook; $0 starthook
RETVAL=$?
;;
'restartback')
$0 suspendback; $0 resumeback
RETVAL=$?
;;
'suspendback'|'resumeback'|'killback')
# shellcheck disable=SC2250
$runcmd "$bashbot $1 $mode"
$runcmd "$bashbot $1"
RETVAL=$?
# kill inotifywait from runuser
if [ "$1" != "resumeback" ]; then
@ -86,7 +146,8 @@ case "$1" in
fi
;;
*)
printf "%s\n" "Usage: $0 { start | stop | restart | reload | restartback | suspendback | resumeback | killback }"
printf "%s\n" "Usage: $0 [ start | stop | restart | starthook | stophook | restarthook ]"
printf "%s\n" " $0 [ status | restartback | suspendback | resumeback | killback ]"
RETVAL=1
;;
esac

File diff suppressed because it is too large Load Diff

85
bin/any_command.sh Executable file
View File

@ -0,0 +1,85 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034,SC2059
#===============================================================================
#
# FILE: bin/any_command.sh
#
USAGE='any_command.sh [-h|--help] [--force|--reference] bot_command args ...'
#
# DESCRIPTION: execute (almost) any bashbot command/function
# can be used for testing commands while bot development
#
# OPTIONS: -- force - execute unknown commands/functions
# by default only commands in 6_reference.md are allowed
#
# -h - display short help
# --help - this help
#
# Set BASHBOT_HOME to your installation directory
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 30.01.2021 10:24
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
COMMAND=""
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "debug" # debug
print_help "$1"
error=""
# check options
if [[ "$1" = "--force" ]]; then
# skip checks
shift
else
# check for --ref
ref="$1"; [[ "$1" == "--ref"* ]] && shift
if [ "${#1}" -lt 11 ];then
printf "${RED}Command must be minimum 11 characters!${NC}\n"
error=3
fi
if [[ "$1" != *"_"* ]];then
printf "${RED}Command must contain _ (underscore)!${NC}\n"
error=3
fi
# simple hack to get allowed commands from doc
if grep -q "^##### $1" <<<"$(sed -n -e '/^##### _is_/,$ d' -e '/^##### /p' "${BASHBOT_HOME:-..}doc/"6_*)"; then
# oiutput reference and exit
if [[ "${ref}" == "--ref"* ]]; then
sed -n -e '/^##### '"$1"'/,/^##/ p' "${BASHBOT_HOME:-..}doc/"6_*
exit
fi
else
printf "Command ${GREY}%s${NC} not found in 6_reference.md, use ${GREY}--force${NC} to execute!\n" "$1"
error=4
fi
[ -n "${error}" ] && exit "${error}"
fi
####
# ready, do stuff here -----
COMMAND="$1"
if [ "$2" == "BOTADMIN" ]; then
ARG1="${BOTADMIN}"
else
ARG1="$2"
fi
# clear result and response
BOTSENT=()
UPD=()
# send message in selected format
"${COMMAND}" "${ARG1}" "${@:3}"
# output result an telegram response
print_result
print_response

View File

@ -13,16 +13,16 @@
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 18.12.2020 12:27
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
############
# set where your bashbot lives
export BASHBOT_HOME BASHBOT_ETC BASHBOT_VAR FILE_REGEX
export BASHBOT_HOME BASHBOT_ETC BASHBOT_VAR FILE_REGEX ME
# default: one dir up
BASHBOT_HOME="$(cd "${BASH_SOURCE[0]%/*}" >/dev/null 2>&1 && pwd)/../"
[ "${BASHBOT_HOME}" = "/../" ] && BASHBOT_HOME="../"
BASHBOT_HOME="$(cd "${BASH_SOURCE[0]%/*}/../" >/dev/null 2>&1 && pwd)"
[ "${BASHBOT_HOME}" = "" ] && BASHBOT_HOME="../"
# set you own BASHBOT_HOME if different, e.g.
# BASHBOT_HOME="/usr/local/telegram-bot-bash"
@ -32,20 +32,21 @@ BASHBOT_ETC="${BASHBOT_HOME}"
#####
# if files are not readable, eviroment is wrong or bashbot is not initialized
# source bashbot
# check for bashbot
if [ ! -r "${BASHBOT_HOME}/bashbot.sh" ]; then
printf "%s\n" "Bashbot.sh not found in \"${BASHBOT_HOME}\""
exit 4
fi
dev=" Are we in dev or did you forget to run init?"
# check for botconfig.jssh readable
if [ ! -r "${BASHBOT_ETC}/botconfig.jssh" ]; then
printf "%s\n" "Bashbot config file in \"${BASHBOT_ETC}\" does not exist or is not readable."
printf "%s\n" "Bashbot config file in \"${BASHBOT_ETC}\" does not exist or is not readable. ${dev}"
exit 3
fi
# check for count.jssh readable
if [ ! -r "${BASHBOT_VAR}/count.jssh" ]; then
printf "%s\n" "Bashbot count file in \"${BASHBOT_VAR}\" does not exist or is not readable. Did you run bashbot init?"
printf "%s\n" "Bashbot count file in \"${BASHBOT_VAR}\" does not exist or is not readable. ${dev}"
exit 3
fi
@ -58,8 +59,33 @@ UPLOADDIR="${BASHBOT_VAR%/bin*}"
FILE_REGEX="${UPLOADDIR}/.*"
# get and check ADMIN and NAME
BOT_ADMIN="$(getConfigKey "botadmin")"
BOT_NAME="$(getConfigKey "botname")"
[[ -z "${BOT_ADMIN}" || "${BOT_ADMIN}" == "?" ]] && printf "%s\n" "${ORANGE}Warning: Botadmin not set, did you forget to sent command${NC} /start"
[[ -z "${BOT_NAME}" ]] && printf "%s\n" "${ORANGE}Warning: Botname not set, did you ever run bashbot?"
BOTNAME="$(getConfigKey "botname")"
ME="${BOTNAME}"
[[ -z "${BOTADMIN}" || "${BOTADMIN}" == "?" ]] && printf "%s\n" "${ORANGE}Warning: Botadmin not set, send bot command${NC} /start"
[[ -z "${BOTNAME}" ]] && printf "%s\n" "${ORANGE}Warning: Botname not set, run bashbot.sh botname"
# default webhook pipe
export WEBHOOK="${DATADIR}/webhook-fifo-${ME}"
# output command result or Telegram response
print_result() { jssh_printDB "BOTSENT" | sort -r; }
print_response() { jssh_printDB "UPD"; }
# check and output help
print_help() {
case "$1" in
'')
printf "missing arguments\n"
;&
"-h"*)
printf 'usage: %s\n' "${USAGE}"
exit 1
;;
'--h'*)
sed -n '/^#====/,/^#====/p' <"$0"
exit 1
;;
esac
}

149
bin/bashbot_init.inc.sh Normal file
View File

@ -0,0 +1,149 @@
#!/bin/bash
#===============================================================================
#
# FILE: bashbot_init.inc.sh
#
# USAGE: source bashbot_init.inc.sh
#
# DESCRIPTION: extend / overwrite bashbot initialisation
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 27.01.2021 13:42
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# shellcheck disable=SC2059
##########
# commands to execute before bot_init() is called
########
# called after default init is finished
my_init() {
: # your init here
}
#########
#
# extended initialisation:
#
# - uograde old config
# - backup of botconfig.jssh
# - running bot as service or other user
# - copy clean and dist files if not exist
# - configure bot for INLINE CALLBACK MEONLY SILENCER
#
# delete from here to disable extended initialisation
bot_init() {
if [ -n "${BASHBOT_HOME}" ] && ! cd "${BASHBOT_HOME}"; then
printf "Can't change to BASHBOT_HOME"
exit 1
fi
local runuser chown touser botname DEBUG="$1"
# upgrade from old version
# currently no action
printf "Check for Update actions ...\n"
printf "Done.\n"
# load addons on startup
printf "Initialize modules and addons ...\n"
for addons in "${ADDONDIR:-.}"/*.sh ; do
# shellcheck source=./modules/aliases.sh
[ -r "${addons}" ] && source "${addons}" "init" "${DEBUG}"
done
printf "Done.\n"
# guess bashbot from botconfig.jssh owner:group
[ -f "${BOTCONFIG}.jssh" ] && runuser="$(stat -c '%U' "${BOTCONFIG}.jssh"):$(stat -c '%G' "${BOTCONFIG}.jssh")"
# empty or ":" use user running init, nobody for root
if [ "${#runuser}" -lt 3 ]; then
# shellcheck disable=SC2153
runuser="${RUNUSER}"
[ "${UID}" = "0" ] && runuser="nobody"
fi
printf "Enter User to run bashbot [${runuser}]: "
read -r chown
[ -z "${chown}" ] && chown="${runuser}"
touser="${chown%:*}"
# check user ...
if ! id "${touser}" &>/dev/null; then
printf "${RED}User \"${touser}\" does not exist!${NN}"
exit 3
elif [ "${UID}" != "0" ]; then
# different user but not root ...
printf "${ORANGE}You are not root, adjusting permissions may fail. Try \"sudo ./bashbot.sh init\"${NN}Press <CTRL+C> to stop or <Enter> to continue..." 1>&2
[ -n "${INTERACTIVE}" ] && read -r runuser
fi
# check if mycommands exist
if [[ ! -r "${BASHBOT_ETC:-.}/mycommands.sh" && -r ${BASHBOT_ETC:-.}/mycommands.sh.dist ]]; then
printf "Mycommands.sh not found, copy ${GREY}<C>lean file, <E>xamples or <N>one${NC} to mycommands.sh? (c/e/N) N\b"
read -r ANSWER
[[ "${ANSWER}" =~ ^[cC] ]] && cp -f "${BASHBOT_ETC:-.}/mycommands.sh.clean" "${BASHBOT_ETC:-.}/mycommands.sh"
[[ "${ANSWER}" =~ ^[eE] ]] && cp -f "${BASHBOT_ETC:-.}/mycommands.sh.dist" "${BASHBOT_ETC:-.}/mycommands.sh"
# offer to copy config also
if [ ! -r "${BASHBOT_ETC:-.}/mycommands.conf" ]; then
printf "Mycommands config file not found, copy ${GREY}mycommands.conf.dist${NC} to mycommands.conf? (Y/n) Y\b"
read -r ANSWER
[[ "${ANSWER}" =~ ^[nN] ]] || cp -f "${BASHBOT_ETC:-.}/mycommands.conf.dist" "${BASHBOT_ETC:-.}/mycommands.conf"
fi
# adjust INLINE CALLBACK MEONLY SILENCER
if [ -w "${BASHBOT_ETC:-.}/mycommands.conf" ]; then
printf "Activate processing for ${GREY}<I>nline queries, <C>allback buttons, <B>oth or <N>one${NC} in mycommands.sh? (i/c/b/N) N\b"
read -r ANSWER
[[ "${ANSWER}" =~ ^[iIbB] ]] && sed -i '/INLINE="/ s/^.*$/export INLINE="1"/' "${BASHBOT_ETC:-.}/mycommands.conf"
[[ "${ANSWER}" =~ ^[cCbB] ]] && sed -i '/CALLBACK="/ s/^.*$/export CALLBACK="1"/' "${BASHBOT_ETC:-.}/mycommands.conf"
printf "Always ignore commands for other Bots in chat ${GREY}(/cmd@other_bot)${NC}? (y/N) N\b"
read -r ANSWER
[[ "${ANSWER}" =~ ^[yY] ]] && sed -i '/MEONLY="/ s/^.*$/export MEONLY="1"/' "${BASHBOT_ETC:-.}/mycommands.conf"
printf "Delete administrative messages in chats ${GREY}(pinned, user join/leave, ...)${NC}? (y/N) N\b"
read -r ANSWER
[[ "${ANSWER}" =~ ^[yY] ]] && sed -i '/SILENCER="/ s/^.*$/export SILENCER="yes"/' "${BASHBOT_ETC:-.}/mycommands.conf"
fi
printf "Done.\n"
fi
# adjust permissions
printf "Adjusting files and permissions for user \"${touser}\" ...\n"
chown -Rf "${chown}" . ./*
chmod 711 .
chmod -R o-w ./*
chmod -R u+w "${COUNTFILE}"* "${BLOCKEDFILE}"* "${DATADIR}" logs "${LOGDIR}/"*.log 2>/dev/null
chmod -R o-r,o-w "${COUNTFILE}"* "${BLOCKEDFILE}"* "${DATADIR}" "${BOTACL}" 2>/dev/null
# jsshDB must writeable by owner
find . -name '*.jssh*' -exec chmod u+w \{\} +
printf "Done.\n"
# adjust values in bashbot.rc
if [ -w "bashbot.rc" ]; then
printf "Adjust user and botname in bashbot.rc ...\n"
sed -i '/^[# ]*runas=/ s|runas=.*$|runas="'"${touser}"'"|' "bashbot.rc"
sed -i '/^[# ]*bashbotdir=/ s|bashbotdir=.*$|bashbotdir="'"${PWD}"'"|' "bashbot.rc"
botname="$(getConfigKey "botname")"
[ -n "${botname}" ] && sed -i '/^[# ]*name=/ s|name=.*$|name="'"${botname}"'"|' "bashbot.rc"
printf "Done.\n"
fi
# ask to check bottoken online
if [ -z "$(getConfigKey "botid")" ]; then
printf "Seems to be your first init. Should I verify your bot token online? (y/N) N\b"
read -r ANSWER
if [[ "${ANSWER}" =~ ^[Yy] ]]; then
printf "${GREEN}Contacting telegram to verify your bot token ...${NN}"
$0 botname
fi
fi
# check if botconf seems valid
printf "${GREEN}This is your bot config:${NN}${GREY}"
sed 's/^/\t/' "${BOTCONFIG}.jssh" | grep -vF '["bot_config_key"]'; printf "${NC}"
if check_token "$(getConfigKey "bottoken")" && [[ "$(getConfigKey "botadmin")" =~ ^[${o9o9o9}]+$ ]]; then
printf "Bot config seems to be valid. Should I make a backup copy? (Y/n) Y\b"
read -r ANSWER
if [[ -z "${ANSWER}" || "${ANSWER}" =~ ^[^Nn] ]]; then
printf "Copy bot config to ${BOTCONFIG}.jssh.ok ...\n"
cp "${BOTCONFIG}.jssh" "${BOTCONFIG}.jssh.ok"
fi
else
printf "${ORANGE}Bot config may incomplete, pls check.${NN}"
fi
# show result
printf "${GREY}"; ls -ldp "${DATADIR}" "${LOGDIR}" ./*.jssh* ./*.sh ./*.conf 2>/dev/null; printf "${NC}"
_exec_if_function my_init
}

View File

@ -1,4 +1,5 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/bashbot_stats.sh
@ -16,30 +17,17 @@ USAGE='bashbot_stats.sh [-h|--help] [debug]'
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 23.12.2020 20:34
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
case "$1" in
"-h"*)
printf "usage: %s\n" "${USAGE}"
exit 1
;;
'--h'*)
sed -n '3,/###/p' <"$0"
exit 1
;;
esac
# set bashbot environment
# shellcheck disable=SC1090
source "${0%/*}/bashbot_env.inc.sh" "$1"
[ -n "$1" ] && print_help "$1"
####
# ready, do stuff here -----
echo -e "${GREEN}Hi I'm ${BOT_NAME}.${NC}"
echo -e "${GREEN}Hi I'm ${BOTNAME}.${NC}"
declare -A STATS
jssh_readDB_async "STATS" "${COUNTFILE}"
for MSG in ${!STATS[*]}

View File

@ -1,4 +1,5 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/delete_message.sh
@ -19,36 +20,21 @@ USAGE='delete_message.sh [-h|--help] "CHAT[ID]" "MESSAGE[ID]" [debug]'
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 03.01.2021 15:37
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
DELETE="delete_message"
case "$1" in
'')
printf "missing arguments\n"
;&
"-h"*)
printf 'usage: %s\n' "${USAGE}"
exit 1
;;
'--h'*)
sed -n '3,/###/p' <"$0"
exit 1
;;
esac
# set bashbot environment
# shellcheck disable=SC1090
source "${0%/*}/bashbot_env.inc.sh" "${3:-debug}" # $3 debug
print_help "$1"
####
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOT_ADMIN}"
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
@ -59,5 +45,4 @@ fi
[ "${BOTSENT[OK]}" = "true" ] && BOTSENT[ID]="$2"
# output send message result
jssh_printDB "BOTSENT" | sort -r
print_result

54
bin/edit_buttons.sh Executable file
View File

@ -0,0 +1,54 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/edit_buttons.sh
#
USAGE='send_message.sh [-h|--help] "CHAT[ID]" "MESSAGE[ID]" "text|url" ...'
#
# DESCRIPTION: send a send buttons in a row to the given user/group
#
# OPTIONS: CHAT[ID] - ID number of CHAT or BOTADMIN to send to yourself
# MESSAGE[ID] - ID of MESSAGE with buttons to edit
# text|url - buttons to send, each button as "text|url" pair or
# "url" only to show url as text also, "" starts new row
# "url" not http(s):// or tg:// is sent as callback_data
#
# -h - display short help
# --help - this help
#
# EXAMPLE: 2 buttons on 2 rows, first shows Amazon, second the url as text
# send_buttons.sh "Amazon|https://www.amazon.com" "" "https://mydealz.de" ...
#
# Set BASHBOT_HOME to your installation directory
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 21.01.2021 08:10
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
SEND="edit_inline_keyboard"
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "debug"
print_help "$1"
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
MESSAGE_ID="$2"
shift 2
# send message in selected format
"${SEND}" "${CHAT}" "${MESSAGE_ID}" "$(_button_row "$@")"
# output send message result
print_result

View File

@ -1,7 +1,8 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/send_message.sh
# FILE: bin/edit_message.sh
#
USAGE='send_edit_message.sh [-h|--help] [format|caption] "CHAT[ID]" "MESSAGE[ID]" "message ...." [debug]'
#
@ -22,7 +23,7 @@ USAGE='send_edit_message.sh [-h|--help] [format|caption] "CHAT[ID]" "MESSAGE[ID]
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 23.12.2020 16:52
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
@ -45,28 +46,16 @@ case "$1" in
SEND="edit_message_caption"
shift
;;
'')
printf "missing arguments\n"
;&
"-h"*)
printf 'usage: %s\n' "${USAGE}"
exit 1
;;
'--h'*)
sed -n '3,/###/p' <"$0"
exit 1
;;
esac
# set bashbot environment
# shellcheck disable=SC1090
source "${0%/*}/bashbot_env.inc.sh" "${4:-debug}" # $4 debug
print_help "$1"
####
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOT_ADMIN}"
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
@ -75,5 +64,4 @@ fi
"${SEND}" "${CHAT}" "$2" "$3"
# output send message result
jssh_printDB "BOTSENT" | sort -r
print_result

47
bin/kickban_user.sh Executable file
View File

@ -0,0 +1,47 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/kickban_user.sh
#
USAGE='kickban_user.sh [-h|--help] [-u|--unban] "CHAT[ID]" "USER[ID]" [debug]'
#
# DESCRIPTION: kickban or unban a user from the given group
#
# OPTIONS: -u | --unban - unban user
# CHAT[ID] - ID number of CHAT or BOTADMIN to send to yourself
# USER[ID] - user to (un)ban
#
# -h - display short help
# --help - this help
#
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 25.01.2021 20:34
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
BAN="kick_chat_member"
case "$1" in
"-u"|"--unban")
BAN="unban_chat_member"
shift
;;
esac
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "${3:-debug}" # $3 debug
print_help "$1"
####
# ready, do stuff here -----
# send message in selected format
"${BAN}" "$1" "$2"
# output send message result
print_result

98
bin/process_batch.sh Executable file
View File

@ -0,0 +1,98 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034,SC2059
#===============================================================================
#
# FILE: bin/process_batch.sh
#
USAGE='process_batch.sh [-h|--help] [-s|--startbot] [-w|--watch] [-n|--lines n] [file] [debug]'
#
# DESCRIPTION: processes last 10 telegram updates in file, one update per line
#
# -s --startbot load addons, start TIMER, trigger startup actions
# -w --watch watch for new updates added to file
# -n --lines read only last "n" lines
# file to read updates from
# empty means read from webhook pipe
#
# -h - display short help
# --help - this help
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 27.02.2021 13:14
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
COMMAND="process_multi_updates"
lines="-n 10"
mode="batch"
opt=0
while [[ "${opt}" -lt 5 && "$1" == "-"* ]]
do
(( opt++ ))
case "$1" in
"-s"|"--startbot")
startbot="yes"
shift
;;
"-w"|"--watch")
follow="-f"
mode="webhook"
shift
;;
"-n"|"--lines")
lines="-n $2"
shift 2
;;
esac
done
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "debug" # debug
print_help "${1:-nix}"
# empty file is webhook
file="${WEBHOOK}"
[ -n "$1" ] && file="$1"
# start bot
if [ -n "${startbot}" ]; then
# warn when starting bot without pipe
[ -p "${file}" ] || printf "%(%c)T: %b\n" -1 "${ORANGE}Warning${NC}: File is not a pipe:${GREY} ${file##*/}${NC}"
start_bot "$2" "${mode}"
printf "%(%c)T: %b\n" -1 "${GREEN}Bot startup actions done, start ${mode} updates ...${NC}"
fi
# check file exist
if [[ ! -r "${file}" || -d "${file}" ]]; then
printf "%(%c)T: %b\n" -1 "${RED}Error${NC}: File not readable:${GREY} ${file}${NC}."
exit 1
fi
####
# ready, do stuff here -----
# kill all sub processes on exit
trap 'printf "%(%c)T: %s\n" -1 "Bot in '"${mode}"' mode stopped"; kill $(jobs -p) 2>/dev/null; wait $(jobs -p) 2>/dev/null; send_normal_message "'"${BOTADMIN}"'" "Bot '"${BOTNAME} ${mode}"' stopped ..."' EXIT HUP QUIT
# wait after (first) update to avoid processing to many in parallel
UPDWAIT="0.5"
# use tail to read appended updates
# shellcheck disable=SC2086,SC2248
tail ${follow} ${lines} "${file}" 2>/dev/null |\
while IFS="" read -r input 2>/dev/null
do
# read json from stdin and convert update format
# replace any ID named BOTADMIN with ID of bot admin
: "${input//\"id\":BOTADMIN,/\"id\":${BOTADMIN},}"
json='{"result": ['"${_}"']}'
UPDATE="$(${JSONSHFILE} -b -n <<<"${json}" 2>/dev/null)"
# process telegram update
"${COMMAND}" "$2"
sleep "${UPDWAIT}"
UPDWAIT="0.05"
done

41
bin/process_update.sh Executable file
View File

@ -0,0 +1,41 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034,SC2059
#===============================================================================
#
# FILE: bin/process_update.sh
#
USAGE='process_update.sh [-h|--help] [debug] [<file]'
#
# DESCRIPTION: processes ONE telegram update read from stdin, e.g. form file or webhook
#
# -h - display short help
# --help - this help
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 30.01.2021 19:14
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
COMMAND="process_multi_updates"
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "debug" # debug
print_help "${1:-nix}"
####
# ready, do stuff here -----
# read json from stdin and convert update format
# replace any ID named BOTADMIN with ID of bot admin
json='{"result": ['"$(cat)"']}'
json="${json//\"id\":BOTADMIN,/\"id\":${BOTADMIN},}"
UPDATE="$(${JSONSHFILE} -b -n <<<"${json}" 2>/dev/null)"
# process telegram update
"${COMMAND}" "$1"

46
bin/promote_user.sh Executable file
View File

@ -0,0 +1,46 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/promote_user.sh
#
USAGE='promote_user.sh [-h|--help] "CHAT[ID]" "USER[ID]" "right[:true|false]" ..'
#
# DESCRIPTION: promote / denote user rights in given group
#
# OPTIONS: CHAT[ID] - ID number of CHAT or BOTADMIN to send to yourself
# USER[ID] - user to (un)ban
# rights[:true|false] - rights to grant in long or short form,
# followed by :true to grant or :false to renove
# long: is_anonymous can_change_info can_post_messages can_edit_messages
# can_delete_messages can_invite_users can_restrict_members
# can_pin_messages can_promote_member`
# short: anon change post edit delete invite restrict pin promote
#
# -h - display short help
# --help - this help
#
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 25.01.2021 22:34
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
PROMOTE="promote_chat_member"
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "debug" # debug
print_help "$1"
####
# ready, do stuff here -----
# send message in selected format
"${PROMOTE}" "$@"
# output send message result
print_result

View File

@ -1,4 +1,5 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
# shellcheck disable=SC2059
#
@ -27,7 +28,7 @@ USAGE='broadcast_message.sh [-h|--help] [--doit] [--groups|--both|--db=file] [fo
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 16.12.2020 16:14
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
@ -75,23 +76,11 @@ case "$1" in
SEND="send_html_message"
shift
;;
'')
printf "missing missing arguments\n"
;&
"-h"*)
printf 'usage: %s\n' "${USAGE}"
exit 1
;;
'--h'*)
sed -n -e '/# shellcheck /d' -e '3,/###/p' <"$0"
exit 1
;;
esac
# set bashbot environment
# shellcheck disable=SC1090
source "${0%/*}/bashbot_env.inc.sh" "$2" # $3 debug
print_help "$1"
# read in users from given DB or count.jssh
database="${USERDB:-${COUNTFILE}}"
@ -102,7 +91,7 @@ if [ -z "${SENDALL[*]}" ]; then
fi
# loop over users
printf "${GREEN}Sending broadcast message to ${SENDTO}${GROUPSALSO} of ${BOT_NAME} using database:${NC}${GREY} ${database##*/}"
printf "${GREEN}Sending broadcast message to ${SENDTO}${GROUPSALSO} of ${BOTNAME} using database:${NC}${GREY} ${database##*/}"
{ # dry run
[ -z "${DOIT}" ] && printf "${NC}\n${ORANGE}DRY RUN! use --doit as first argument to execute broadcast...${NC}\n"

54
bin/send_buttons.sh Executable file
View File

@ -0,0 +1,54 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/send_message.sh
#
USAGE='send_message.sh [-h|--help] "CHAT[ID]" "message" "text|url" ...'
#
# DESCRIPTION: send a send buttons in a row to the given user/group
#
# OPTIONS: CHAT[ID] - ID number of CHAT or BOTADMIN to send to yourself
# message - message to send
# text|url - buttons to send, each button as "text|url" pair or
# "url" not http(s):// or tg:// is sent as callback_data
# "url" only to show url as text also, "" starts new row
#
# -h - display short help
# --help - this help
#
# EXAMPLE: 2 buttons on 2 rows, first shows Amazon, second the url as text
# send_buttons.sh "Amazon|https://www.amazon.com" "" "https://mydealz.de" ...
#
# Set BASHBOT_HOME to your installation directory
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 18.01.2021 11:34
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
SEND="send_inline_keyboard"
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "debug"
print_help "$1"
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
MESSAGE="$2"
shift 2
# send message in selected format
"${SEND}" "${CHAT}" "${MESSAGE}" "$(_button_row "$@")"
# output send message result
print_result

47
bin/send_dice.sh Executable file
View File

@ -0,0 +1,47 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/send_dice.sh
#
USAGE='send_dice.sh [-h|--help] "CHAT[ID]" "emoji" [debug]'
#
# DESCRIPTION: send an animated emoji (dice) to given chat
#
# OPTIONS: CHAT[ID] - ID number of CHAT or BOTADMIN to send to yourself
# emoji - must be one of: “🎲”, “🎯”, “🏀”, “⚽” “🎰” "🎳"
# :game_die: :dart: :basketball: :soccer: :slot_machine: :bowling:
#
# -h - display short help
# --help - this help
#
# Set BASHBOT_HOME to your installation directory
#
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 07.02.2021 18:45
#
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
SEND="send_dice"
# set bashbot environment
source "${0%/*}/bashbot_env.inc.sh" "${3:-debug}" # $5 debug
print_help "$1"
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
# send message in selected format
"${SEND}" "${CHAT}" "$2"
# output send message result
print_result

View File

@ -1,4 +1,5 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/send_file.sh
@ -24,34 +25,21 @@ USAGE='send_file.sh [-h|--help] "CHAT[ID]" "file|URL" "caption ...." [type] [deb
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 25.12.2020 20:24
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
# parse args
SEND="send_file"
case "$1" in
'')
printf "missing arguments\n"
;&
"-h"*)
printf 'usage: %s\n' "${USAGE}"
exit 1
;;
'--h'*)
sed -n '3,/###/p' <"$0"
exit 1
;;
esac
# set bashbot environment
# shellcheck disable=SC1090
source "${0%/*}/bashbot_env.inc.sh" "${5:-debug}" # $5 debug
print_help "$1"
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOT_ADMIN}"
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
@ -64,5 +52,4 @@ FILE="$2"
"${SEND}" "${CHAT}" "${FILE}" "$3" "$4"
# output send message result
jssh_printDB "BOTSENT" | sort -r
print_result

View File

@ -1,4 +1,5 @@
#!/bin/bash
# shellcheck disable=SC1090,SC2034
#===============================================================================
#
# FILE: bin/send_message.sh
@ -7,11 +8,15 @@ USAGE='send_message.sh [-h|--help] [format] "CHAT[ID]" "message ...." [debug]'
#
# DESCRIPTION: send a message to the given user/group
#
# OPTIONS: format - normal, markdown, html (optional)
# OPTIONS: format - normal, markdown, html, stdin, - (optional)
# CHAT[ID] - ID number of CHAT or BOTADMIN to send to yourself
# message - message to send in specified format
# if no format is givern send_message() format is used
#
# use format "stdin" to read message from stdin or from a file:
# send_message.sh stdin "CHAT[ID]" <file
# df -h | send_message.sh - "CHAT[ID]"
#
# -h - display short help
# --help - this help
#
@ -21,7 +26,7 @@ USAGE='send_message.sh [-h|--help] [format] "CHAT[ID]" "message ...." [debug]'
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
# CREATED: 16.12.2020 11:34
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
####
@ -40,34 +45,29 @@ case "$1" in
SEND="send_html_message"
shift
;;
'')
printf "missing arguments\n"
;&
"-h"*)
printf 'usage: %s\n' "${USAGE}"
exit 1
;;
'--h'*)
sed -n '3,/###/p' <"$0"
exit 1
"stdin"|"-")
FILE="stdin"
shift
;;
esac
# set bashbot environment
# shellcheck disable=SC1090
source "${0%/*}/bashbot_env.inc.sh" "${3:-debug}" # $3 debug
print_help "$1"
####
# ready, do stuff here -----
if [ "$1" == "BOTADMIN" ]; then
CHAT="${BOT_ADMIN}"
CHAT="${BOTADMIN}"
else
CHAT="$1"
fi
# send message in selected format
"${SEND}" "${CHAT}" "$2"
if [ "${FILE}" = "stdin" ]; then
"${SEND}" "${CHAT}" "$(cat)"
else
"${SEND}" "${CHAT}" "$2"
fi
# output send message result
jssh_printDB "BOTSENT" | sort -r
print_result

View File

@ -8,14 +8,14 @@
# | |__/ / |_| | | | | | |_| | |__ | |____( (_| | | |__ _
# |_____/ \___/ |_| |_|\___/ \___) |_______)____|_|\___)_|
#
# this file *MUST* not be edited! place your config and commands in
# the file "mycommands.sh". a clean version is provided as "mycommands.sh.clean"
# this file *MUST* not edited! place your config in the file "mycommands.conf"
# and commands in "mycommands.sh", a clean version is provided as "mycommands.sh.clean"
#
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#
# bashbot locale defaults to c.UTF-8, adjust locale in mycommands.sh if needed
@ -42,12 +42,16 @@ bashbot_help='
*• /start*: _Start bot and get this message_.
*• /help*: _Get this message_.
*• /info*: _Get shorter info message about this bot_.
*• /question*: _Start interactive chat (mycommands.dist)_.
*• /cancel*: _Cancel any currently running interactive chat_.
*• /kickme*: _You will be autokicked from the group_.
*• /leavechat*: _The bot will leave the group with this command _.
Additional commands from mycommands.dist ...
*• /game*: _throw a die_.
*• /question*: _Start interactive chat_.
*• /cancel*: _Cancel any currently running interactive chat_.
*• /run_notify*: _Start background job_.
*• /stop_notify*: _Stop notify background job_.
Written by Drew (@topkecleon) and KayM (@gnadelwartz).
Get the code in my [GitHub](http://github.com/topkecleon/telegram-bot-bash)
Get the code on [GitHub](http://github.com/topkecleon/telegram-bot-bash)
'
# load modules on startup and always on on debug
@ -66,6 +70,7 @@ fi
# copy "mycommands.sh.dist" to "mycommands.sh" and change the values there
# defaults to no inline, all commands and nonsense home dir
export INLINE="0"
export CALLBACK="0"
export MEONLY="0"
export FILE_REGEX="${BASHBOT_ETC}/.*"
@ -76,23 +81,26 @@ export FILE_REGEX="${BASHBOT_ETC}/.*"
if [ -z "$1" ] || [[ "$1" == *"debug"* ]];then
# detect inline commands....
# no default commands, all processing is done in myinlines()
if [ "${INLINE}" != "0" ] && [ -n "${iQUERY[ID]}" ]; then
# forward iinline query to optional dispatcher
_exec_if_function myinlines
#################
# detect inline and callback query
if [ -n "${iQUERY[ID]}" ]; then
# forward inline query to optional dispatcher
[ "${INLINE:-0}" != "0" ] && _exec_if_function myinlines
# regular (global) commands ...
# your commands are in mycommands()
elif [ -n "${iBUTTON[ID]}" ]; then
# forward inline query to optional dispatcher
[ "${CALLBACK:-0}" != "0" ] && _exec_if_function mycallbacks
#################
# regular command
else
###################
# if is bashbot is group admin it get commands sent to other bots
# set MEONLY=1 to ignore commands for other bots
if [[ "${MEONLY}" != "0" && "${MESSAGE}" == "/"* && "${MESSAGE%% *}" == *"@"* ]]; then
if [[ "${MEONLY}" != "0" && "${MESSAGE}" == "/"*"@"* ]]; then
# here we have a command with @xyz_bot added, check if it's our bot
MYCHECK="${MESSAGE%% *}"
[ "${MYCHECK}" != "${MYCHECK%%@${ME}}" ] && return
[ "${MESSAGE%%@*}" != "${MESSAGE%%@${ME}}" ] && return
fi
###################
@ -127,7 +135,7 @@ if [ -z "$1" ] || [[ "$1" == *"debug"* ]];then
'/help'*)
send_markdown_message "${CHAT[ID]}" "${bashbot_help}"
;;
'/leavechat'*) # bot leave chat if user is admin in chat
'/leavechat'*) # bot leave chat if user is admin in chat
if user_is_admin "${CHAT[ID]}" "${USER[ID]}" || user_is_allowed "${USER[ID]}" "leave" ; then
send_markdown_message "${CHAT[ID]}" "*LEAVING CHAT...*"
leave_chat "${CHAT[ID]}"

View File

@ -5,7 +5,7 @@
#
# Description: run all tests, exit after failed test
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#############################################################
#shellcheck disable=SC1090

View File

@ -5,7 +5,7 @@
#
# Description: common stuff for all dev scripts
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#############################################################
# magic to ensure that we're always inside the root of our application,
@ -20,3 +20,5 @@ else
printf "Sorry, no git repository %s\n" "$(pwd)" && exit 1
fi
HOOKDIR="dev/hooks"
LASTCOMMIT=".git/.lastcommit"

View File

@ -3,15 +3,21 @@
#
# works together with git pre-push.sh and ADD all changed files since last push
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#shellcheck disable=SC1090
source "${0%/*}/dev.inc.sh"
[ ! -f .git/.lastcommit ] && printf "No previous commit or hooks not installed, use \"git add\" instead ... Abort\n" && exit
# check for last commit date
if [ ! -f "${LASTCOMMIT}" ]; then
if ! touch -d "$(git log -1 --format=%cD)" "${LASTCOMMIT}"; then
printf "No previous commit found, use \"git add\" instead ... Abort\n"
exit
fi
fi
set +f
FILES="$(find ./* -newer .git/.lastcommit| grep -v -e 'DIST\/' -e 'STANDALONE\/' -e 'JSON.sh')"
FILES="$(find ./* -newer "${LASTCOMMIT}" | grep -v -e 'DIST\/' -e 'STANDALONE\/' -e 'JSON.sh')"
set -f
# FILES="$(find ./* -newer .git/.lastpush)"
[ "${FILES}" = "" ] && printf "Nothing changed since last commit ...\n" && exit

View File

@ -1,5 +1,5 @@
#!/usr/bin/env bash
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
############
# NOTE: you MUST run install-hooks.sh again when updating this file!

View File

@ -1,5 +1,5 @@
#!/usr/bin/env bash
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
############
# NOTE: you MUST run install-hooks.sh again when updating this file!
@ -41,16 +41,17 @@ else
exit 1
fi
# get version strings
REMOTEVER="$(git ls-remote -t --refs 2>/dev/null | tail -1 | sed -e 's/.*\/v//' -e 's/-.*//')"
VERSION="$(git describe --tags | sed -e 's/-.*//' -e 's/v//' -e 's/,/./')"
[ -z "${REMOTEVER}" ] && REMOTEVER="${VERSION}"
# LOCAL version must greater than latest REMOTE release version
printf "Update Version of modified files\n"
if ! command -v bc &> /dev/null || (( $(printf "%s\n" "${VERSION} >= ${REMOTEVER}" | bc -l) )); then
# update version in bashbot files on push
set +f
[ -f "${LASTPUSH}" ] && LASTFILES="$(find ./* -newer "${LASTPUSH}")"
[ -f "${LASTPUSH}" ] && LASTFILES="$(find ./* -newer "${LASTPUSH}" ! -path "./DIST/*" ! -path "./STANDALONE/*")"
[ "${LASTFILES}" = "" ] && exit
printf " "
# shellcheck disable=SC2086
@ -64,7 +65,7 @@ fi
if command -v codespell &>/dev/null; then
printf "Running codespell\n............................\n"
codespell -q 3 --skip="*.zip,*gz,*.log,*.html,*.txt,.git*,jsonDB-keyboard" -L "ba"
codespell -q 3 --skip="*.zip,*gz,*.log,*.html,*.txt,.git*,jsonDB-keyboard,DIST,STANDALONE" -L "ba"
printf "if there are (to many) typo's shown, consider running:\ncodespell -i 3 -w --skip=\"*.log,*.html,*.txt,.git*,examples\" -L \"ba\"\n"
else
printf "consider installing codespell: pip install codespell\n"

View File

@ -1,5 +1,5 @@
#!/usr/bin/env bash
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
############
# NOTE: you MUST run install-hooks.sh again when updating this file!

View File

@ -7,7 +7,7 @@
#
# Usage: source inject-json.sh
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
##############################################################
# download JSON.sh

View File

@ -1,13 +1,11 @@
#!/usr/bin/env bash
# this has to run once atfer git clone
# and every time we create new hooks
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#shellcheck disable=SC1090
source "${0%/*}/dev.inc.sh"
HOOKDIR="dev/hooks"
printf "Installing hooks..."
for hook in pre-commit post-commit pre-push
do

View File

@ -7,7 +7,7 @@
#
# Options: --notest - skip tests
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
##############################################################
#shellcheck disable=SC1090
@ -20,6 +20,7 @@ DISTDIR="./DIST/${DISTNAME}"
DISTMKDIR="data-bot-bash logs bin bin/logs addons"
DISTFILES="bashbot.sh commands.sh mycommands.sh.clean bin doc examples scripts modules LICENSE README.md README.txt README.html"
DISTFILESDEV="dev/make-standalone.sh dev/inject-json.sh dev/make-html.sh dev/obfuscate.sh"
DISTFILESDIST="mycommands.sh mycommands.conf bashbot.rc $(echo "addons/"*.sh)"
# run tests first!
@ -39,6 +40,9 @@ mkdir -p "${DISTDIR}" 2>/dev/null
printf "Copy files\n"
# shellcheck disable=SC2086
cp -r ${DISTFILES} "${DISTDIR}"
mkdir -p "${DISTDIR}/dev"
# shellcheck disable=SC2086
cp ${DISTFILESDEV} "${DISTDIR}/dev"
cd "${DISTDIR}" || exit 1
printf "Create directories\n"

View File

@ -1,8 +1,13 @@
STANDALONE
data-bot-bash/*
test
webhook-fifo*
JSON.awk
bashbot.rc
mycommands.sh
mycommands.conf
awk-patch.sh
make-standalone.sh.include
*.jssh*
botacl
*.flock

View File

@ -7,7 +7,7 @@
#
# Usage: source make-hmtl
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
##############################################################
# check for correct dir

View File

@ -11,29 +11,53 @@
# If you your bot is finished you can use make-standalone.sh to create the
# the old all-in-one bashbot: bashbot.sh and commands.sh only!
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
###################################################################
# include git config and change to base dir
incfile="${0%/*}/dev.inc.sh"
#shellcheck disable=SC1090
source "${0%/*}/dev.inc.sh"
[ -f "${incfile}" ] && source "${incfile}"
# seems we are not in a dev env
if [ -z "${BASE_DIR}" ]; then
BASE_DIR="$(pwd)"
[[ "${BASE_DIR}" == *"/dev" ]] && BASE_DIR="${BASE_DIR%/*}"
# go to basedir
cd "${BASE_DIR}" || exit 1
fi
# see if if bashbot is in base dir
[ ! -f "bashbot.sh" ] && printf "bashbot.sh not found in %s\n" " $(pwd)" && exit 1
# run pre_commit if exist
[[ -f "dev/dev.inc.sh" && "$1" != "--notest" ]] && dev/hooks/pre-commit.sh
# files and dirs to copy
#DISTNAME="telegram-bot-bash"
DISTDIR="./STANDALONE"
DISTMKDIR="data-bot-bash logs bin bin/logs addons"
DISTFILES="bashbot.sh bashbot.rc commands.sh mycommands.sh dev/obfuscate.sh modules bin scripts LICENSE README.* doc botacl botconfig.jssh $(echo "addons/"*.sh)"
DISTMKDIR="data-bot-bash logs bin/logs addons"
DISTFILES="bashbot.sh commands.sh mycommands.sh modules scripts LICENSE README.* doc addons"
DISTBINFILES="bin/bashbot_env.inc.sh bin/bashbot_stats.sh bin/process_batch.sh bin/process_update.sh bin/send_broadcast.sh bin/send_message.sh"
# run pre_commit on files
[ "$1" != "--notest" ] && dev/hooks/pre-commit.sh
# add extra files, minimum mycommands.conf
extrafile="${BASE_DIR}/dev/${0##*/}.include"
[ ! -f "${extrafile}" ] && printf "bashbot.rc\nbotacl\nbotconfig.jssh\nmycommands.conf\ndev/obfuscate.sh\n" >"${extrafile}"
DISTFILES+=" $(<"${extrafile}")"
# create dir for distribution and copy files
printf "Create directories and copy files\n"
mkdir -p "${DISTDIR}" 2>/dev/null
mkdir -p "${DISTDIR}/bin" 2>/dev/null
# shellcheck disable=SC2086
cp -r ${DISTFILES} "${DISTDIR}" 2>/dev/null
cp -rp ${DISTFILES} "${DISTDIR}" 2>/dev/null
# shellcheck disable=SC2086
cp -p ${DISTBINFILES} "${DISTDIR}/bin" 2>/dev/null
cd "${DISTDIR}" || exit 1
# remove log files
find . -name '*.log' -delete
# shellcheck disable=SC2250
for dir in $DISTMKDIR
do
@ -67,19 +91,20 @@ printf "OK, now lets do the magic ...\n\t... create unified commands.sh\n"
mv $$commands.sh commands.sh
rm -f mycommands.sh
printf "\n... create unified bashbot.sh\n"
printf "\t... create unified bashbot.sh\n"
{
# first head of bashbot.sh
sed -n '0,/for module in/ p' bashbot.sh | head -n -3
# then mycommands from first non comment line on
# then modules without shebang
printf '\n##############################\n# bashbot modules starts here ...\n'
cat modules/*.sh | sed -e 's/^#\!\/bin\/bash.*//'
# shellcheck disable=SC2016
cat modules/*.sh | sed -e 's/^#\!\/bin\/bash.*//' -e '/^#.*\$\$VERSION\$\$/d'
# last tail of commands.sh
printf '\n##############################\n# bashbot internal functions starts here ...\n\n'
sed -n '/BASHBOT INTERNAL functions/,$ p' bashbot.sh
# last remaining commands.sh
printf '\n##############################\n'
sed -n '/^# read commands file/,$ p' bashbot.sh
} >>$$bashbot.sh
@ -90,11 +115,11 @@ rm -rf modules
printf "Create minimized Version of bashbot.sh and commands.sh\n"
# shellcheck disable=SC2016
sed -E -e '/(shellcheck)|(^#!\/)|(\$\$VERSION\$\$)/! s/^[[:space:]]*#.*//' -e 's/^[[:space:]]*//' -e '/^$/d' -e 'N;s/\\\n/ /;P;D' bashbot.sh |\
sed 'N;s/\\\n/ /;P;D' > bashbot.sh.min
sed -E -e '/(shellcheck)|(^#!\/)|(\$\$VERSION\$\$)/! s/^[[:space:]]*#.*//' -e '/shellcheck/! s/\t+#.*//' -e 's/^[[:space:]]*//'\
-e '/^$/d' bashbot.sh | sed 'N;s/\\\n/ /;P;D' | sed 'N;s/\\\n/ /;P;D' > bashbot.sh.min
# shellcheck disable=SC2016
sed -E -e '/(shellcheck)|(^#!\/)|(\$\$VERSION\$\$)/! s/^[[:space:]]*#.*//' -e 's/^[[:space:]]*//' -e 's/\)[[:space:]]+#.*/)/' -e '/^$/d' commands.sh |\
sed 'N;s/\\\n/ /;P;D' > commands.sh.min
sed -E -e '/(shellcheck)|(^#!\/)|(\$\$VERSION\$\$)/! s/^[[:space:]]*#.*//' -e '/shellcheck/! s/\t+#.*//' -e 's/^[[:space:]]*//'\
-e '/^$/d' commands.sh | sed 'N;s/\\\n/ /;P;D' > commands.sh.min
chmod +x bashbot.sh.min
# make html doc

View File

@ -0,0 +1,5 @@
bashbot.rc
botacl
botconfig.jssh
mycommands.conf
dev/obfuscate.sh

View File

@ -2,7 +2,7 @@
#
# joke hack to obfuscate bashbot.min.sh
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# shellcheck disable=SC2028,SC2016,SC1117
infile="bashbot.sh"

View File

@ -1,4 +1,5 @@
# list of additional files to check from shellcheck
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
bashbot.rc
mycommands.conf
mycommands.sh.clean

View File

@ -1,6 +1,6 @@
#!/bin/bash
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# shellcheck disable=SC2016
#
# Easy Versioning in git:
@ -43,8 +43,15 @@ unset IFS
VERSION="$(git describe --tags --long)"
printf "Update to version %s ...\n" "${VERSION}"
FILES="$(find ./*)"
[ "$1" != "" ] && FILES="$*"
# only regular files, ignore .dot files/dirs, e.g. .git .gitinore in BASEDIR
if [ -n "$1" ]; then
FILES="$*"
else
printf "Update version string in all files? (y/N)\b\b"
read -r answer
[[ "${answer}" != "y" && "${answer}" != "Y" ]] && exit
FILES="$(find ./* -type f ! -path "./DIST/*" ! -path "./STANDALONE/*")"
fi
# autogenerate REMADME.html REMADE.txt
if [[ "${FILES}" == *"README.md"* ]]; then
@ -53,7 +60,7 @@ if [[ "${FILES}" == *"README.md"* ]]; then
cat "doc/bashbot.ascii" >"README.txt"
if [ -r "README.html" ] && type -f html2text >/dev/null; then
# convert html links to text [link]
sed -E 's/<a href="([^>]+)">([^<#]+)<\/a>/\2 [\1]/' <README.html |\
sed -E 's/<a href="([^>]+)">([^<#]+)<\/a>/\2 [\1]/g' <README.html |\
html2text -style pretty -width 90 - >>README.txt
else
type -f fold >/dev/null && fold -s -w 90 README.md >>README.txt
@ -63,7 +70,8 @@ fi
# change version string in given files
for file in ${FILES}
do
[ ! -f "${file}" ] && continue
# symlink is a file :-(
[[ -L "${file}" || ! -f "${file}" ]] && continue
#[ "${file}" == "version" ] && continue
printf "%s" " ${file}" >&2
sed -i 's/^#### $$VERSION$$.*/#### \$\$VERSION\$\$ '"${VERSION}"'/' "${file}"

View File

@ -132,5 +132,5 @@ You must update to [Version 1.20](https://github.com/topkecleon/telegram-bot-bas
#### [Next Create Bot](1_firstbot.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -65,5 +65,5 @@ group. This step is up to you actually.
#### [Prev Installation](0_install.md)
#### [Next Getting started](2_usage.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -30,17 +30,24 @@ Have FUN!
├── bashbot.sh # main bashbot script - DO NOT EDIT!
├── commands.sh # command dispatcher - DO NOT EDIT!
├── JSON.sh # bashbots JSON parser, see https://github.com/dominictarr/JSON.sh
├── JSON.sh # bashbot JSON parsers
│   ├── JSON.sh # sh implementation, https://github.com/dominictarr/JSON.sh
│   └── JSON.awk.dist # faster awk version, https://github.com/step-/JSON.awk
├── bin # ready to use scripts, use `scriptname --help` for help
│   ├── bashbot_stats.sh # does what it says ...
│   ├── send_broadcast.sh # send message to all known chats
│   ├── send_message.sh # send message to given chat
│   ├── edit_message.sh # replace given message id in given chat
│   ├── delete_message.sh # delete given message id in given chat
│   ├── send_broadcast.sh # send message to all known chats
│   ├── send_file.sh # send file to given chat
│   ├── bashbot_stats.sh # does what it says ...
│   ├── delete_message.sh # delete given message id in given chat
│   ├── send_buttons.sh # send message with attached button
│   ├── edit_buttons.sh # attach/edit message buttons
│   ├── kickban_user.sh # kick/unban user from given chat
│   ├── promote_user.sh # promote/dente user rights in given chat
│ │
│   └── bashbot_env.inc.sh # bashbot location included from scripts, adapt if needed
│   ├── bashbot_env.inc.sh # sourced from scripts, adapt locations if needed
│   └── bashbot_init.inc.sh # sourced from bashbot.sh init
├── scripts # place your bashbot interactive and background scripts here
│   └── interactive.sh.clean # interactive script template for new scripts
@ -50,15 +57,15 @@ Have FUN!
├── modules # optional functions, sourced by commands.sh
│   ├── aliases.sh # to disable modules rename them xxx.sh.off
│   ├── answerInline.sh
│   ├── jsshDB.sh # read and store JSON.sh style JSON, mandatory
│   ├── background.sh # interactive and background functions
│   ├── chatMember.sh
│   └── sendMessage.sh # main send message functions, mandatory
│   ├── chatMember.sh # manage chat mambers
│   ├── jsshDB.sh # read and store JSON.sh style JSON, mandatory
│   ├── processUpdates.sh # process updates from telegram, mandatory (run bot)
│   └── sendMessage.sh # send message functions, mandatory
├── addons # optional addons, disabled by default
│   ├── example.sh # to enable addons change their XXX_ENABLE to true
│   ├── antiFlood.sh # simple addon taking actions based on # files and text sent to chat
│   └── xxxxxage.sh
│   └── antiFlood.sh # simple addon taking actions based on # files and text sent to chat
├── bashbot.rc # start/stop script if you run bashbot as service
@ -91,6 +98,7 @@ Start or Stop your Bot use the following commands:
```
### Scripts in bin/
Use `script.sh -h` or `script --help` to get short/long help for script.
To count the total number of users and messages run the following command:
@ -121,7 +129,7 @@ bin/send_message.sh "CHAT[ID]" "Hey, I just wanted to let you know that the bot'
To replace a message already sent to one user or chat run the following command:
```bash
bin/send_edit_message.sh "CHAT[ID]" "12345" "Done!"
bin/edit_message.sh "CHAT[ID]" "12345" "Done!"
["OK"] "true"
["ID"] "12345"
@ -144,9 +152,14 @@ Note: to get help about a script in bin/ run `scriptname.sh --help`
Evertime a Telegram update is received, you can read incoming data using the following variables:
In case you need other update values, the array `UPD` contains complete Telegram response.
### Regular Messages
### Processing Messages
These Variables are always present in regular messages:
If an update is received from Telegram, the message is pre processed by Bashbot and the following bash variables are set for use in `mycommands.sh`.
These variables are always present if a message is pre processed:
* `${ME}`: Name of your bot
* `${BOTADMIN}`: User id of bot administrator
* `${MESSAGE}`: Current message text
* `${MESSAGE[ID]}`: ID of current message
@ -166,6 +179,8 @@ These Variables are always present in regular messages:
The following variables are set if the message contains optional parts:
* `MESSAGE[CAPTION]`: Picture, Audio, Video, File Captions
* `MESSAGE[DICE]`: Animated DICE Emoji DICE values is contained in `MESSAGE[RESULT]`
* `$REPLYTO`: Original message which was replied to
* `$REPLYTO`: This array contains the First name, last name, username and user id of the ORIGINAL sender of the message REPLIED to.
* `${REPLYTO[ID]}`: ID of message which was replied to
@ -179,14 +194,15 @@ The following variables are set if the message contains optional parts:
* `${FORWARD[FIRST_NAME]}`: Original user's first name
* `${FORWARD[LAST_NAME]}`: Original user's' last name
* `${FORWARD[USERNAME]}`: Original user's username
* `$CAPTION`: Picture, Audio, Video, File Captions
* `$URLS`: This array contains documents, audio files, voice recordings and stickers as URL.
* `${URLS[AUDIO]}`: Audio files
* `${URLS[VIDEO]}`: Videos
* `${URLS[PHOTO]}`: Photos (maximum quality)
* `${URLS[VOICE]}`: Voice recordings
* `${URLS[STICKER]}`: Stickers
* `${URLS[DOCUMENT]}`: Any other file
* `$URLS`: This array contains the `path` on Telegram server for files send to chat, e.g. photo, video, audio file.
* `${URLS[AUDIO]}`: Path to audio file
* `${URLS[VIDEO]}`: Path to video
* `${URLS[PHOTO]}`: Path to photo (maximum quality)
* `${URLS[VOICE]}`: Path to voice recording
* `${URLS[STICKER]}`: Path to sticker
* `${URLS[DOCUMENT]}`: Path to any other file
**Important:** This is NOT a full URL, you must use `download_file "${URLS[xxx]}"` or prefix path with telegram api url for manual download
(_e.g. `getJson "${URL}/${URLS[xxx]}" >file`_).
* `$CONTACT`: This array contains info about contacts sent in a chat.
* `${CONTACT[ID]}`: User id
* `${CONTACT[NUMBER]}`: Phone number
@ -206,11 +222,10 @@ The following variables are set if the message contains optional parts:
### Service Messages
Service Messages are regular messages not itended for end users, instead they signal special events to the
client, e.g. new users.
Service Messages are updates not itended for end users, instead they signal special events in a chat, e.g. new users.
If a service message is received bashbot sets MESSAGE to the service message type as a command,
e.g. if a new user joins a chat MESSAGE is set to "/_new_chat_user".
If a service message is received bashbot pre processing sets `${MESSAGE}` according to the service message type,
e.g. if a new user joins a chat MESSAGE is set to `/_new_chat_user ...`.
* `$SERVICE`: This array contains info about received service messages.
* `${SERVICE}`: "yes" if service message is received
@ -232,6 +247,8 @@ e.g. if a new user joins a chat MESSAGE is set to "/_new_chat_user".
* `${MESSAGE}`: /_new_chat_title SENDER TEXT
* `${SERVICE[NEWPHOTO]}`: New Chat Picture
* `${MESSAGE}`: /_new_chat_picture SENDER URL
**Important:** SERVICE[NEWPHOTO] is NOT a full URL, you must use `download_file "${SERVICE[NEWPHOTO]}"` or prefix path with telegram api url for manual download
(_e.g. `getJson "${FILEURL}/${SERVICE[NEWPHOTO]}" >file`_).
* `${SERVICE[PINNED]}`: Pinned MESSAGE ID
* `${MESSAGE}`: /_new_pinned_message SENDER ID
* `${PINNED[ID]}`: Id of pinned message
@ -244,11 +261,17 @@ e.g. if a new user joins a chat MESSAGE is set to "/_new_chat_user".
### Inline query messages
Inline query messages are special messages for direct interaction with your bot.
If an user starts an inline conversation an inline query is sent after each user keystroke.
Inline query messages are small, non regular messages used for interaction with the user,
they contain the following variables only:
To receive inline messages you must set `inline=1` in `mycommands.conf` and in botfather.
THe message contatains all characters so far typed from the user.
* `${iQUERY}`: Current inline query
An received inline query must be anserwered with `answer_inline_query`, see also (Inline Query)[6_reference.md#inline-query]
If an inline query is received only the following variables are available:
* `${iQUERY}`: Inline message typed so far by user
* `$iQUERY`: This array contains the ID, First name, last name, username and user id of the sender of the current inline query.
* `${iQUERY[ID]}`: Inline query ID
* `${iQUERY[USER_ID]}`: User's id
@ -256,11 +279,29 @@ they contain the following variables only:
* `${iQUERY[LAST_NAME]}`: User's last name
### Callback button messages
Callback button messages special messages swend from callback buttons, they contain the following variables only:
* `$iBUTTON`: This array contains the ID, First name, last name, username and user id of the user clicked on the button
* `${iBUTTON[ID]}`: Callback query ID
* `${iBUTTON[DATA]`: Data attached to button, hopefully unique
* `${iBUTTON[CHAT_ID]`: Chat where button was pressed
* `${iBUTTON[MESSAGE_ID]`: Message to which button is attached
* `${iBUTTON[MESSAGE]`: Text of message
* `${iBUTTON[USER_ID]}`: User's id
* `${iBUTTON[FIRST_NAME]}`: User's first name
* `${iBUTTON[LAST_NAME]}`: User's last name
* `${iBUTTON[USERNAME]}`: User's @username
## Send data / get response
After every `send_xxx` `get_xxx` call the array BOTSENT contains the most important values from Telegram response.
In case you need other response values , the array `UPD` contains complete Telegram response.
You can use the array values to check if a commands was successful and get returned values from Telegram.
### BOTSENT array
* `$BOTSENT`: This array contains the parsed results from the last transmission to telegram.
@ -274,7 +315,7 @@ In case you need other response values , the array `UPD` contains complete Teleg
## Usage of bashbot functions
#### sending messages
To send messages use the `send_xxx_message`functions.
To send messages use the `send_xxx_message` functions.
To insert line brakes in a message place `\n` in the text.
To send regular text without any markdown use:
@ -290,7 +331,7 @@ To send text with html:
send_html_message "${CHAT[ID]}" "lol <b>bold</b>"
```
To forward messages use the `forward`function:
To forward messages use the `forward` function:
```bash
forward "${CHAT[ID]}" "from_chat_id" "message_id"
```
@ -328,20 +369,20 @@ To send local files or URL's (photo, video, voice, sticker, documents) use the `
send_file "${CHAT[ID]}" "/home/user/dog.jpg" "Lool" "photo"
send_file "${CHAT[ID]}" "https://images-na.ssl-images-amazon.com/images/I/81DQ0FpoSNL._AC_SL1500_.jpg"
```
To send custom keyboards use the `send_keyboard`function:
To send custom keyboards use the `send_keyboard` function:
```bash
send_keyboard "${CHAT[ID]}" "Text that will appear in chat?" '[ "Yep" , "No" ]' # note the single quotes!
send_keyboard "${CHAT[ID]}" "Text that will appear in chat?" "[ \\"Yep\\" , \\"No\\" ]" # within double quotes you must escape the inside double quots
```
To send locations use the `send_location`function:
To send locations use the `send_location` function:
```bash
send_location "${CHAT[ID]}" "Latitude" "Longitude"
```
To send venues use the `send_venue`function:
To send venues use the `send_venue` function:
```bash
send_venue "${CHAT[ID]}" "Latitude" "Longitude" "Title" "Address" "optional foursquare id"
```
To send a chat action use the `send_action`function.
To send a chat action use the `send_action` function.
Allowed values: typing for text messages, upload_photo for photos, record_video or upload_video for videos, record_audio or upload_audio for audio files, upload_document for general files, find_location for locations.
```bash
send_action "${CHAT[ID]}" "action"
@ -351,5 +392,5 @@ send_action "${CHAT[ID]}" "action"
#### [Prev Create Bot](1_firstbot.md)
#### [Next Advanced Usage](3_advanced.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -73,18 +73,31 @@ You must use the function `user_is_allowed` to check if a user has the capabilit
**See also [Bashbot User Access Control functions](6_reference.md#User-Access-Control)**
### Interactive Chats
Interactive chats are short running scripts, reading user input and echo data to the user.
Interactive chats are simple Bash scripts, reading user input as TEXT and output TEXT to the user.
To create a new interactive chat script copy `scripts/interactive.sh.clean` to e.g. `scripts/mynewinteractive.sh`, make it executable
and then use `start_proc` function from your bot, it's possible to pass two arguments. You find more examples for interactive scripts in 'examples'
**Important**: The script runs standalone in a [pipeline](https://www.geeksforgeeks.org/piping-in-unix-or-linux/), it's **not possible** to use bashbot functions and variables!
```bash
commands.sh send user input as TEXT | script reads TEXT | bashbot.sh recieve output as formated TEXT (see below)
```
In case you want to process any other data then message TEXT, I recommend to switch to a more advanced bot framework.
In Bashbot you have to implement methods yourself to pass additional information in the message TEXT to the script.
(only recommended for advanced bash experts).
#### Example script
*usage*: start_proc chat_id script arg1 arg2
*usage*: kill_proc chat_id
*usage*: check_prog chat_id
**IMPORTANT:** Scripts must read user input from '$3' instead of stdin!
**Note:** Scripts must read user input from '$3' instead of stdin!
```bash
#!/bin/bash
@ -144,7 +157,7 @@ echo "Text that will appear in one message \nwith this text on a new line"
```
In case you want extend a message already containing a location, a file, a keyboard etc.,
with an additionial text simply add ` mytextstartshere additional text`at the end of the string:
with an additionial text simply add ` mytextstartshere additional text` at the end of the string:
```bash
out="Text that will appear mylatstartshere 45 mylongstartshere 45"
[[ "$out" != *'in chat'* ]] && out="$out mytextstartshere in chat."
@ -190,7 +203,7 @@ Note: Background jobs run independent from main bot and continue running until y
In order to enable **inline mode**, send `/setinline` command to [@BotFather](https://telegram.me/botfather) and provide the placeholder text that the user will see in the input field after typing your bots name.
The following commands allows you to send ansers to *inline queries*. To enable bashbot to process inline queries set `INLINE="1"`in 'mycommands.sh'.
The following commands allows you to send ansers to *inline queries*. To enable bashbot to process inline queries set `INLINE="1"` in `mycommands.sh`.
To send messages or links through an *inline query*:
```bash
@ -258,7 +271,7 @@ By default you don't have to care about retry, as bashbot resend the message aft
Only if the retry fails also an error is returned. The downside is that send_message functions will wait until resend is done.
If you want to disable automatic error processing and handle all errors manually (or don't care)
set `BASHBOT_RETRY`to any no zero value.
set `BASHBOT_RETRY` to any no zero value.
[Telegram Bot API error codes](https://github.com/TelegramBotAPI/errors)
@ -266,9 +279,9 @@ set `BASHBOT_RETRY`to any no zero value.
#### Detect bot blocked
If the we can't connect to telegram, e.g. blocked from telegram server but also any other reason,
bashbot set `BOTSENT[ERROR]`to `999`.
bashbot set `BOTSENT[ERROR]` to `999`.
To get a notification on every connection problem create a function named `bashbotBlockRecover`and handle blocks there.
To get a notification on every connection problem create a function named `bashbotBlockRecover` and handle blocks there.
If the function returns true (0 or no value) bashbot will retry once and then return to the calling function.
In case you return any non 0 value bashbot will return to the calling function without retry.
@ -302,5 +315,5 @@ Note: If you disable automatic retry, se above, you disable also connection prob
#### [Prev Getting started](2_usage.md)
#### [Next Expert Use](4_expert.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -154,8 +154,9 @@ To use bashbot as a system service include a working `bashbot.rc` in your init s
An example crontab is provided in `examples/bashbot.cron`.
- If you are running bashbot with your user-ID, copy the examples lines to your crontab and remove username `nobody`.
- if you run bashbot as an other user or a system service edit `examples/bashbot.cron` to fit your needs and replace username `nobody` with the username you want to run bashbot. Copy the modified file to `/etc/cron.d/bashbot`
- if you run bashbot as an other user or a system service edit `examples/bashbot.cron` to fit your needs and replace username `nobody` with the username you want to run bashbot. Insert the modified lines to systm crontab file or copy to `/etc/cron.d/bashbot`
**Warning:** You must use `contab -e` command to modify sytem and user crontabs, see [Cron How-To](https://help.ubuntu.com/community/CronHowto)
### Use bashbot from CLI and scripts
You can use bashbot to send *messages*, *locations*, *venues*, *pictures* etc. from command line and scripts
@ -434,5 +435,5 @@ for every poll until the maximum of BASHBOT_SLEEP ms.
#### [Prev Advanced Use](3_advanced.md)
#### [Next Best Practice](5_practice.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -12,7 +12,7 @@ If you don't have a github account, it may time to [setup a free account now](ht
### Add commands to mycommands.sh only
Do not change `bashbot.sh` and `commands.sh`, instead place your commands in to `mycommands.sh`.
To start with a clean/minimal bot copy `mycommands.sh.clean` to `mycommands.sh` and start editing
the message strings and place commands in the`case ... esac` block of the function mycommands():
the message strings and place commands in the` case ... esac` block of the function mycommands():
```bash
# file: mycommands.sh
# your additional bashbot commands
@ -160,5 +160,5 @@ The second warning is about an unused variable, this is true because in our exam
#### [Prev Best Practice](5_practice.md)
#### [Next Functions Reference](6_reference.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

File diff suppressed because it is too large Load Diff

View File

@ -284,8 +284,9 @@ bar="${_/__x/_c}" # a_b_c
: ${SOMEVAR} # "String in var" $_ -> "var"
: $(<"file") # "Content of\n file" $_ -> "file"
# pitfall test command
[ -n "$MYVAR" ] && echo "$_" # outputs "]"
# pitfall [ vs. test command
[ -n "xxx" ] && echo "$_" # $_ -> "]"
test -n "xxx" && echo "$_" # $_ -> "xxx"
# pitfall command substitution: globbing and IFS is applied!
: "$(echo "a* is born")"# $_ -> a* is globbed even quoted!
@ -386,5 +387,5 @@ fi
#### [Prev Function Reference](6_reference.md)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -56,6 +56,10 @@ convert existing bots.
**jsonDB-keybords** contains a stripped down real world example from my bot showing the usage of jsonDB to store and retrieve values
plus use of keyboards in private chats. It's an extended version of mycommands.sh.dist. Messages and help are in german.
#### $$VERSION$$ v1.30-0-g3266427
### Webhook
**Webhook** contains instructions on how use webhook API to get updates from telegram instead polling Telegram server.
#### $$VERSION$$ v1.52-1-g0dae2db

View File

@ -4,7 +4,7 @@
#
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
######
# parameters

View File

@ -2,7 +2,7 @@
# file: run_filename
# background job to display content of all new files in WATCHDIR
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
######
# parameters

View File

@ -2,7 +2,7 @@
# file: run_filename
# background job to display all new files in WATCHDIR
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
######
# parameters

View File

@ -4,7 +4,7 @@
#
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
######
# parameters

View File

@ -6,7 +6,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
# shellcheck disable=SC1117
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# adjust your language setting here
# https://github.com/topkecleon/telegram-bot-bash#setting-up-your-environment

View File

@ -2,7 +2,7 @@
# file. multibot.sh
# description: run multiple telegram bots from one installation
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
if [ "$2" = "" ] || [ "$2" = "-h" ]; then
echo "Usage: $0 botname command"

View File

@ -7,7 +7,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
SHELL=/bin/sh
@ -23,13 +23,14 @@ MAILTO=root
# │ │ │ │ ┌───────────── day of the week (0 - 6) (Sunday to Saturday;
# │ │ │ │ │ 7 is also Sunday on some systems)
# │ │ │ │ │
# │ │ │ │ │
# │ │ │ │ │ ┌───────────── run as user (must be omited in users crontab
# │ │ │ │ │ |
# * * * * * USER command to execute
# * * * * * root echo "run every minute!"
# run as www every day at 0:00 plus random sleep between 0-3h
0 0 * * * nobody sleep "$((RANDOM \% 180 ))m" ; /usr/local/telegram-bot-bash/bashbot.sh start # (re)start bot
0 0 * * * nobody sleep "$((RANDOM \% 180 ))m" ; /usr/local/telegram-bot-bash/bashbot.sh resumeback # (re)start background jobs
0 0 * * * nobody sleep "$((RANDOM \% 180 ))m" ; /usr/local/telegram-bot-bash/bashbot.rc start # (re)start bot
0 0 * * * nobody sleep "$((RANDOM \% 180 ))m" ; /usr/local/telegram-bot-bash/bashbot.rc resumeback # (re)start background jobs
# run as www on 24 of Dec, 12:00
0 12 24 12 * nobody /usr/local/telegram-bot-bash/bashbot.sh broadcast "X-Mas shopping is over!" # broadcast a message

View File

@ -11,7 +11,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
########################################################################
######

View File

@ -10,7 +10,7 @@
# AUTHOR: KayM (), kay@rrr.de
# DATE: 19.12.2020 19:03
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# shellcheck disable=SC2154
# shellcheck disable=SC2034

View File

@ -13,7 +13,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
########################################################################
######

View File

@ -10,7 +10,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
########################################################################
######
@ -29,6 +29,10 @@ export 'LANGUAGE=C.UTF-8'
unset IFS
# set -f # if you are paranoid use set -f to disable globbing
# kill interactive script if not finished in time, e.g. user away or error
MAXWAIT="1m"
{ sleep "${MAXWAIT}"; printf "Stopping Questionnaire after %s, you need to much time to finish ... BYE\n" "${MAXWAIT}"; kill $$; wait 2>/dev/null ;} &
# simple yes/no question, defaults to no
printf "Hi, hello there\nWould you like some tea (y/n)?\n"
read -r answer <"${INPUT}"

View File

@ -1,7 +1,7 @@
# file: botacl
# a user not listed here, will return false from 'user_is_allowed'
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# Format:
# user:resource:chat

View File

@ -5,7 +5,7 @@
# to show how you can customize bashbot by only editing mycommands.sh
# NOTE: this is not tested, simply copied from original source and reworked!
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#
# shellcheck disable=SC2154
# shellcheck disable=SC2034

View File

@ -0,0 +1,3 @@
/usr/local/github/telegram-bot-bash-develop/DIST/telegram-bot-bash
/usr/local/github/telegram-bot-bash-develop/STANDALONE
/usr/local/telegram-bot-bash

100
examples/webhook/README.md Normal file
View File

@ -0,0 +1,100 @@
#### [Examples](../README.md)
## Bashbot webhook example
### Webhook
Bashbot default mode is to poll Telegram server for updates but Telegram offers webhook as a more efficient method to deliver updates.
If your server is reachable from the Internet its possible to use the method described here.
Prerequisite for receiving Telegram updates with webhook is a valid SSL certificate, a self signed certificate will not be sufficient.
Webhook processing require special setup on server and Telegram side, therefore it's implemented as separate scripts and you need at least sudo rights to setup.
#### Setup Apache webhook
Prerequisite: An Apache webserver with a valid SLL certificate chain and php enabled.\
This should work with other webservers also but it's not testet.
Setup webhook with Apache:
- install bashbot as described in [Bashbot Installation](../../doc/0_install.md)
- create file `data-bot-bash/webhook-fifo-<botname>` (_\<botname\> as in `botconfig.jssh`_)
- run `sudo bashbot.sh init` to setup bashbot to run as same user as web server (_e.g. www_)
- create a directory in web root: `telegram/<your_bot_token>` (_<your_bot_token> as `botconfig.jssh`_)
- give web server access to directory (_e.g.`chown www:www -R telegram`_)
- go into the new directory and copy all files from `examples/webhook` to it
- edit file `BASHBOT_HOME` to contain ithe Bashbot installation directory as first line (_other lines are ignored_)
- execute `php index.php` with user id of web server to test write access to `data-bot-bash/webhook-fifo-<botname>
Calling `https://<yourservername>/telegram/<your_bot_token>/` will execute `index.php`
thus append received data to the file `data-bot-bash/webhook-fifo-<botname>`.
E.g. `https://<yourservername>/telegram/<your_bot_token>/?json={"test":"me"}` will append `{"test":"me"}`.
Now your Server is ready to receive updates from Telegram.
#### Default webhook processing
This is the testet and supported default method for processing Telegram updates over webhook.
To enable update processing delete the file `data-bot-bash/webhook-fifo-<botname>` if webhook is working as described above.
Incoming Telegram updates are now forwarded to the script `bin/process_update.sh` for processing.
On incoming Telegram updates the script is executed, it sources bashbot.sh and forward the update to Bashbot for processing.
Even it seems overhead to source Bashbot for every update, it's more responsive and create less load than Bashbot polling mode.
Nevertheles there are some limitations compared to polling mode:
- no startup actions
- `addons` and `TIMER_EVENTS` are not working
Interactive and background jobs are working as of Bashbot Version 1.51.
#### Full webhook processing
Full webhook processing use an external script to imitate Bashbot polling mode with webhook.
1. Default webook method must work first!
2. run `bashbot.sh init` to setup bashbot to run with your user id
2. Create a named pipe: `mkfifo data-bot-bash/webhook-fifo-botname` and give the web server write access to it
3. execute `php index.php` with user id of web server to test write access to `data-bot-bash/webhook-fifo-<botname>
4. Start script for Bashbot webhook polling mode:\
`bin/process-batch.sh --startbot --watch data-bot-bash/webhook-fifo-<botname>`
The script read updates from given file line by line and forward updates to Bashbot update processing. `--startbot` will run the startup actions
(_e.g. load addons, start TIMER, trigger first run_) and `--watch` will wait for new updates instead of exit on end of file.
Short form: 'bin/process-batch.sh -s -w'
If script works as expected, you may run Bashbot webook polling in background by using `./bachbot.rc starthook/stophook`.
To switch back to default processing delete fifo `data-bot-bash/webhook-fifo-<botname>` and stop `bin/process-batch.sh`.
#### Enable webhook on Telegram side
To get updates via webhook your server must be reachable from the internet and you must
instruct Telegram where to deliver updates, this is done by calling bashbot function `set_webhook`.
*Example:*
```bash
bin/any_command.sh set_webhook "https://myserver.com/telegram"
```
instruct Telegram to use the URL `https://myserver.com/telegram/<your_bot_token>/` to deliver updates.
After you enable webhook to deliver Telegram updates it's no more possible to poll updates with `bashbot.sh start`.
To stop delivering of Telegram updates via webhook run `bin/any_command.sh delete_webhook`.
**Important**: Telegram will refuse to deliver updates if your webhook has no valid SSL certificate chain.
#### Bash webhook
A pure bash webhook implementation is not possible without extra software because Telegram delivers
webhook updates only over secure TLS connections with a valid SSL certificate chain.
`socat` looks like a tool to listen for Telegram updates from bash scripts, let's see ...
#### $$VERSION$$ v1.52-1-g0dae2db

112
examples/webhook/index.php Normal file
View File

@ -0,0 +1,112 @@
<?php
/************************************************************
* @file examples/webhook/index.php
* @description example webhook implementation for apache
* write to fifo/file if writeable, else pipe to command
*
* first line of BASHBOT_HOME is used as bot home (optional)
* must start with /, not contain /. and min 20 characters long
*
* @author KayM (gnadelwartz), kay@rrr.de
* @license http://www.wtfpl.net/txt/copying/ WTFPLv2
* @since 30.01.2021 20:24
*
#### $$VERSION$$ v1.52-1-g0dae2db
***********************************************************/
// bashbot home dir
$CONFIG_HOME='BASHBOT_HOME';
$BASHBOT_HOME='/usr/local/telegram-bot-bash';
// read from config file
if (file_exists($CONFIG_HOME)) {
$tmp = trim(fgets(fopen($CONFIG_HOME, 'r')));
// start with '/', not '/.', min 20 chars
if (substr($tmp,0,1) == '/' && strlen($tmp) >= 20 && strpos($tmp, '/.') === false) {
$BASHBOT_HOME=$tmp;
}
}
// bashbot config file
$CONFIG=$BASHBOT_HOME.'/botconfig.jssh';
// set botname here or read botname from config file if unknown
$botname="unknown";
if ($botname == "unknown" && file_exists($CONFIG)) {
$prefix='["botname"] "';
$len=strlen($prefix);
$arr = file($CONFIG, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
foreach ($arr as $line) {
if(substr($line, 0, $len) == $prefix) {
$botname=substr($line, $len, strlen($line)-$len-1);
}
}
}
// script endpoint
$cmd=$BASHBOT_HOME.'/bin/process_update.sh';
// default fifo endpoint
$fifo=$BASHBOT_HOME.'/data-bot-bash/webhook-fifo-'.$botname;
// prepeare read, e.g. run from CLI
$data='';
$input="php://input";
$json_file="json.txt";
if (php_sapi_name() == "cli") {
if(is_readable($json_file)) {
$input=$json_file;
} else {
$input="php://stdin";
}
}
// read request data
if($json = file_get_contents($input)) {
$data = $json;
} else {
$data = implode(" ",$_POST);
if ($data == '') { $data = implode(" ",$_GET); }
}
// uncomment to save last received JSON
// file_put_contents($json_file, str_replace(array("\n", "\r"), '',$data). PHP_EOL));
// prepare for writing
if ($data == '') {
error_response(400, "No data received");
}
if (! chdir($BASHBOT_HOME)) {
error_response(403, "No route to bot home");
}
// fifo or command?
if (! is_writeable($fifo)) {
// pipe to command
if (! file_exists($cmd)) {
error_response(502, "Webhook endpoint not found");
}
if (! $handle = popen( $cmd.' debug', 'w' )) {
error_response(503, "Can't open webhook command endpoint");
}
} else {
// write to fifo
if (! $handle = fopen( $fifo, 'a' )) {
error_response(503, "Can't open webhook file endpoint");
}
flock($handle, LOCK_EX);
}
if (fwrite( $handle, str_replace(array("\n", "\r"), '',$data). PHP_EOL) === false) {
error_response(504, "Write to webhook failed");
}
flock($handle, LOCK_UN);
pclose($handle);
/**/
function error_response($code, $msg) {
$api = substr(php_sapi_name(), 0, 3);
if ($api == 'cgi' || $api == 'fpm') {
header('Status: '.$code.' '.$msg);
} else {
$protocol = isset($_SERVER['SERVER_PROTOCOL']) ? $_SERVER['SERVER_PROTOCOL'] : 'HTTP/1.0';
header($protocol.' '.$code.' '.$msg);
}
exit('Error '.$code.': '.$msg. PHP_EOL);
}
?>

View File

@ -0,0 +1 @@
{"update_id":665220889,"message":{"message_id":760,"from":{"id":BOTADMIN,"is_bot":false,"first_name":"Kay","last_name":"M","username":"KayM","language_code":"de"},"chat":{"id":BOTADMIN,"first_name":"Kay","last_name":"M","username":"KayM","type":"private"},"date":1612029749,"text":"/info","entities":[{"offset":0,"length":5,"type":"bot_command"}]}}

View File

@ -1,11 +1,11 @@
#!/bin/bash
# file: modules/alaises.sh
# file: modules/aliases.sh
# do not edit, this file will be overwritten on update
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#
# will be automatically sourced from bashbot

View File

@ -5,7 +5,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# will be automatically sourced from bashbot
@ -31,70 +31,70 @@ inline_query_compose(){
# title2Json title caption description markup inlinekeyboard
case "$2" in
# user provided media
"article"|"message") # article ID title message (markup description)
"article"|"message") # article ID title message (markup description)
JSON='{"type":"article","id":"'${ID}'","input_message_content": {"message_text":"'$4'"} '$(title2Json "$3" "" "$5" "$6" "$7")'}'
;;
"photo") # photo ID photoURL (thumbURL title description caption)
"photo") # photo ID photoURL (thumbURL title description caption)
[ -z "$4" ] && tumb="$3"
JSON='{"type":"photo","id":"'${ID}'","photo_url":"'$3'","thumb_url":"'$4${tumb}'"'$(title2Json "$5" "$7" "$6" "$7" "$8")'}'
;;
"gif") # gif ID photoURL (thumbURL title caption)
"gif") # gif ID photoURL (thumbURL title caption)
[ -z "$4" ] && tumb="$3"
JSON='{"type":"gif","id":"'${ID}'","gif_url":"'$3'", "thumb_url":"'$4${tumb}'"'$(title2Json "$5" "$6" "$7" "$8" "$9")'}'
;;
"mpeg4_gif") # mpeg4_gif ID mpegURL (thumbURL title caption)
"mpeg4_gif") # mpeg4_gif ID mpegURL (thumbURL title caption)
[ -n "$4" ] && tumb='","thumb_url":"'$4'"'
JSON='{"type":"mpeg4_gif","id":"'${ID}'","mpeg4_url":"'$3'"'${tumb}$(title2Json "$5" "$6" "" "$7" "$8")'}'
;;
"video") # video ID videoURL mime thumbURL title (caption)
"video") # video ID videoURL mime thumbURL title (caption)
JSON='{"type":"video","id":"'${ID}'","video_url":"'$3'","mime_type":"'$4'","thumb_url":"'$5'"'$(title2Json "$6" "$7" "$8" "$9" "${10}")'}'
;;
"audio") # audio ID audioURL title (caption)
"audio") # audio ID audioURL title (caption)
JSON='{"type":"audio","id":"'${ID}'","audio_url":"'$3'"'$(title2Json "$4" "$5" "" "" "$6")'}'
;;
"voice") # voice ID voiceURL title (caption)
"voice") # voice ID voiceURL title (caption)
JSON='{"type":"voice","id":"'${ID}'","voice_url":"'$3'"'$(title2Json "$4" "$5" "" "" "$6")'}'
;;
"document") # document ID title documentURL mimetype (caption description)
"document") # document ID title documentURL mimetype (caption description)
JSON='{"type":"document","id":"'${ID}'","document_url":"'$4'","mime_type":"'$5'"'$(title2Json "$3" "$6" "$7" "$8" "$9")'}'
;;
"location") # location ID lat long title
"location") # location ID lat long title
JSON='{"type":"location","id":"'${ID}'","latitude":"'$3'","longitude":"'$4'","title":"'$5'"}'
;;
"venue") # venue ID lat long title (address forsquare)
"venue") # venue ID lat long title (address forsquare)
[ -z "$6" ] && addr="$5"
[ -n "$7" ] && fours=',"foursquare_id":"'$7'"'
JSON='{"type":"venue","id":"'${ID}'","latitude":"'$3'","longitude":"'$4'","title":"'$5'","address":"'$6${addr}'"'${fours}'}'
;;
"contact") # contact ID phone first (last thumb)
"contact") # contact ID phone first (last thumb)
[ -n "$5" ] && last=',"last_name":"'$5'"'
[ -n "$6" ] && tumb='","thumb_url":"'$6'"'
JSON='{"type":"contact","id":"'${ID}'","phone_number":"'$3'","first_name":"'$4'"'${last}'"}'
;;
# title2Json title caption description markup inlinekeyboard
# Cached media stored in Telegram server
"cached_photo") # photo ID file (title description caption)
"cached_photo") # photo ID file (title description caption)
JSON='{"type":"photo","id":"'${ID}'","photo_file_id":"'$3'"'$(title2Json "$4" "$6" "$5" "$7" "$8")'}'
;;
"cached_gif") # gif ID file (title caption)
"cached_gif") # gif ID file (title caption)
JSON='{"type":"gif","id":"'${ID}'","gif_file_id":"'$3'"'$(title2Json "$4" "$5" "$6" "$7" "$8" )'}'
;;
"cached_mpeg4_gif") # mpeg ID file (title caption)
"cached_mpeg4_gif") # mpeg ID file (title caption)
JSON='{"type":"mpeg4_gif","id":"'${ID}'","mpeg4_file_id":"'$3'"'$(title2Json "$4" "$5" "" "$6" "$7")'}'
;;
"cached_sticker") # sticker ID file
"cached_sticker") # sticker ID file
JSON='{"type":"sticker","id":"'${ID}'","sticker_file_id":"'$3'"}'
;;
"cached_document") # document ID title file (description caption)
"cached_document") # document ID title file (description caption)
JSON='{"type":"document","id":"'${ID}'","document_file_id":"'$4'"'$(title2Json "$3" "$6" "$5" "$6" "$7")'}'
;;
"cached_video") # video ID file title (description caption)
"cached_video") # video ID file title (description caption)
JSON='{"type":"video","id":"'${ID}'","video_file_id":"'$3'"'$(title2Json "$4" "$6" "$5" "$7" "$8")'}'
;;
"cached_voice") # voice ID file title (caption)
"cached_voice") # voice ID file title (caption)
JSON='{"type":"voice","id":"'${ID}'","voice_file_id":"'$3'"'$(title2Json "$4" "$5" "" "" "$6")'}'
;;
"cached_audio") # audio ID file title (caption)
"cached_audio") # audio ID file title (caption)
JSON='{"type":"audio","id":"'${ID}'","audio_file_id":"'$3'"'$(title2Json "$4" "$5" "" "" "$6")'}'
;;
esac

View File

@ -6,7 +6,7 @@
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
# shellcheck disable=SC1117,SC2059
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# will be automatically sourced from bashbot
@ -46,12 +46,16 @@ start_back() {
printf '%s\n' "$1:$3:$2" >"${cmdfile}"
restart_back "$@"
}
# $1 chatid
# $2 program
# $3 jobname
# $4 $5 parameters
restart_back() {
local fifo; fifo="${DATADIR:-.}/$(procname "$1" "back-$3-")"
log_message "Start background job CHAT=$1 JOB=${fifo##*/} CMD=${2##*/} $4 $5"
log_update "Start background job CHAT=$1 JOB=${fifo##*/} CMD=${2##*/} $4 $5"
check_back "$1" "$3" && kill_proc "$1" "back-$3-"
nohup bash -c "{ $2 \"$4\" \"$5\" \"${fifo}\" | \"${SCRIPT}\" outproc \"$1\" \"${fifo}\"; }" &>>"${fifo}.log" &
sleep 0.5 # give bg job some time to init
sleep 0.5 # give bg job some time to init
}
@ -62,9 +66,9 @@ start_proc() {
[ -z "$2" ] && return
[ -x "${2%% *}" ] || return 1
local fifo; fifo="${DATADIR:-.}/$(procname "$1")"
log_message "Start interactive script CHAT=$1 JOB=${fifo##*/} CMD=$2 $3 $4"
check_proc "$1" && kill_proc "$1"
mkfifo "${fifo}"
log_update "Start interactive script CHAT=$1 JOB=${fifo##*/} CMD=$2 $3 $4"
nohup bash -c "{ $2 \"$4\" \"$5\" \"${fifo}\" | \"${SCRIPT}\" outproc \"$1\" \"${fifo}\"
rm \"${fifo}\"; [ -s \"${fifo}.log\" ] || rm -f \"${fifo}.log\"; }" &>>"${fifo}.log" &
}
@ -99,9 +103,11 @@ kill_proc() {
fifo="$(procname "$1" "$2")"
prid="$(proclist "${fifo}")"
fifo="${DATADIR:-.}/${fifo}"
log_message "Stop interactive / background CHAT=$1 JOB=${fifo##*/}"
# shellcheck disable=SC2086
[ -n "${prid}" ] && kill ${prid}
if [ -n "${prid}" ]; then
log_update "Stop interactive / background CHAT=$1 JOB=${fifo##*/}"
kill ${prid}
fi
[ -s "${fifo}.log" ] || rm -f "${fifo}.log"
[ -p "${fifo}" ] && rm -f "${fifo}";
}
@ -110,7 +116,7 @@ kill_proc() {
# $2 message
send_interactive() {
local fifo; fifo="${DATADIR:-.}/$(procname "$1")"
[ -p "${fifo}" ] && printf '%s\n' "$2" >"${fifo}" & # not blocking!
[ -p "${fifo}" ] && printf '%s\n' "$2" >"${fifo}" & # not blocking!
}
# old style but may not work because of local checks
@ -118,16 +124,15 @@ inproc() {
send_interactive "${CHAT[ID]}" "${MESSAGE[0]}"
}
# start stop all jobs
# $1 command
# killb*
# suspendb*
# resumeb*
# start stop all jobs
# $1 command # kill suspend resume restart
job_control() {
local BOT ADM content proc CHAT job fifo killall=""
BOT="$(getConfigKey "botname")"
ADM="$(getConfigKey "botadmin")"
ADM="${BOTADMIN}"
debug_checks "Enter job_control" "$1"
# cleanup on start
[[ "$1" == "re"* ]] && bot_cleanup "startback"
for FILE in "${DATADIR:-.}/"*-back.cmd; do
[ "${FILE}" = "${DATADIR:-.}/*-back.cmd" ] && printf "${RED}No background processes.${NN}" && break
content="$(< "${FILE}")"
@ -138,23 +143,23 @@ job_control() {
fifo="$(procname "${CHAT}" "${job}")"
debug_checks "Execute job_control" "$1" "${FILE##*/}"
case "$1" in
"resumeb"*|"backgr"*)
"resume"*|"restart"*)
printf "Restart Job: %s %s\n" "${proc}" " ${fifo##*/}"
restart_back "${CHAT}" "${proc}" "${job}"
# inform botadmin about stop
[ -n "${ADM}" ] && send_normal_message "${ADM}" "Bot ${BOT} restart background jobs ..." &
;;
"suspendb"*)
"suspend"*)
printf "Suspend Job: %s %s\n" "${proc}" " ${fifo##*/}"
kill_proc "${CHAT}" "${job}"
# inform botadmin about stop
[ -n "${ADM}" ] && send_normal_message "${ADM}" "Bot ${BOT} suspend background jobs ..." &
killall="y"
;;
"killb"*)
"kill"*)
printf "Kill Job: %s %s\n" "${proc}" " ${fifo##*/}"
kill_proc "${CHAT}" "${job}"
rm -f "${FILE}" # remove job
rm -f "${FILE}" # remove job
# inform botadmin about stop
[ -n "${ADM}" ] && send_normal_message "${ADM}" "Bot ${BOT} kill background jobs ..." &
killall="y"

View File

@ -5,7 +5,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# will be automatically sourced from bashbot
@ -20,6 +20,10 @@ new_chat_invite() {
[ "${BOTSENT[OK]}" = "true" ] && printf "%s\n" "${BOTSENT[RESULT]}"
}
# $1 chat, $2 user_id, $3 title
set_chatadmin_title() {
sendJson "$1" '"user_id":'"$2"',"custom_title": "'"$3"'"' "${URL}/setChatAdministratorCustomTitle"
}
# $1 chat, $2 title
set_chat_title() {
sendJson "$1" '"title": "'"$2"'"' "${URL}/setChatTitle"
@ -30,6 +34,12 @@ set_chat_description() {
sendJson "$1" '"description": "'"$2"'"' "${URL}/setChatDescription"
}
# $1 chat $2 file
set_chat_photo() {
local file; file="$(checkUploadFile "$1" "$2" "set_chat_photo")"
[ -z "${file}" ] && return 1
sendUpload "$1" "photo" "${file}" "${URL}/setChatPhoto"
}
# $1 chat
delete_chat_photo() {
sendJson "$1" "" "${URL}/deleteChatPhoto"
@ -56,18 +66,52 @@ delete_chat_stickers() {
}
# manage chat member functions -------
# $1 chat
chat_member_count() {
sendJson "$1" "" "${URL}/getChatMembersCount"
[ "${BOTSENT[OK]}" = "true" ] && printf "%s\n" "${BOTSENT[RESULT]}"
}
kick_chat_member() {
sendJson "$1" 'user_id: '"$2"'' "${URL}/kickChatMember"
sendJson "$1" '"user_id": '"$2"'' "${URL}/kickChatMember"
}
unban_chat_member() {
sendJson "$1" 'user_id: '"$2"'' "${URL}/unbanChatMember"
sendJson "$1" '"user_id": '"$2"'' "${URL}/unbanChatMember"
}
leave_chat() {
sendJson "$1" "" "${URL}/leaveChat"
}
# $1 chat, $2 userid, $3 ... "right[:true]" default false
# right: is_anonymous change_info post_messages edit_messages delete_messages invite_users restrict_members pin_messages promote_member
promote_chat_member() {
local arg bool json chat="$1" user="$2; shift 2"
for arg in "$@"
do
# default false
bool=false; [ "${arg##*:}" = "true" ] && bool="true"
# expand args
case "${arg}" in
*"anon"*) arg="is_anonymous";;
*"change"*) arg="can_change_info";;
*"post"*) arg="can_post_messages";;
*"edit"*) arg="can_edit_messages";;
*"delete"*) arg="can_delete_messages";;
*"pin"*) arg="can_pin_messages";;
*"invite"*) arg="can_invite_users";;
*"restrict"*) arg="can_restrict_members";;
*"promote"*) arg="can_promote_members";;
*) [ -n "${BASHBOTDEBUG}" ] && log_debug "promote_chat_member: unknown promotion CHAT=${chat} USER=${user} PROM=${arg}"
continue;;
esac
# compose json
[ -n "${json}" ] && json+=","
json+='"'"${arg}"'": "'"${bool}"'"'
done
sendJson "${chat}" '"user_id":'"${user}"','"${json}"'' "${URL}/promoteChatMember"
}
# bashbot specific functions ---------
@ -76,7 +120,7 @@ leave_chat() {
get_chat_member_status() {
sendJson "$1" '"user_id":'"$2"'' "${URL}/getChatMember"
# shellcheck disable=SC2154
JsonGetString '"result","status"' <<< "${res}"
printf "%s\n" "${UPD["result,status"]}"
}
user_is_creator() {
@ -103,10 +147,9 @@ user_is_admin() {
# $1 user
user_is_botadmin() {
[ -z "$1" ] && return 1
local admin; admin="$(getConfigKey "botadmin")"; [ -z "${admin}" ] && return 1
[[ "${admin}" == "$1" || "${admin}" == "$2" ]] && return 0
#[[ "${admin}" = "@*" ]] && [[ "${admin}" = "$2" ]] && return 0
if [ "${admin}" = "?" ]; then setConfigKey "botadmin" "${1:-?}"; return 0; fi
[ -z "${BOTADMIN}" ] && return 1
[[ "${BOTADMIN}" == "$1" || "${BOTADMIN}" == "$2" ]] && return 0
if [ "${BOTADMIN}" = "?" ]; then setConfigKey "botadmin" "${1:-?}"; BOTADMIN="${1:-?}"; return 0; fi
return 1
}

View File

@ -5,7 +5,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#
# source from commands.sh to use jsonDB functions
#
@ -25,7 +25,9 @@ eval "$(basename "${BASH_SOURCE[0]}")(){ :; }"
# tinybox
# lockfile filename.flock is persistent and will be testet with flock for active lock (file open)
export JSSH_LOCKNAME=".flock"
export JSSHDB_LOCKNAME=".flock"
# an array value containing this string will not saveed to DB (unset)
export JSSHDB_UNSET="99999999999999999999_JSSHDB_UNSET_99999999999999999999"
# in UTF-8 äöü etc. are part of [:alnum:] and ranges (e.g. a-z), but we want ASCII a-z ranges!
# for more information see doc/4_expert.md#Character_classes
@ -42,7 +44,7 @@ JSSH_KEYOK="[-${azAZo9},._]"
# $1 - invalid charcaters are replaced with first character
# or deleted if $1 is empty
jssh_stripKey() { # tr: we must escape first - in [-a-z...]
if [[ "$1" =~ ^${JSSH_KEYOK} ]]; then # tr needs [\-...
if [[ "$1" =~ ^${JSSH_KEYOK} ]]; then # tr needs [\-...
tr -c "${JSSH_KEYOK/\[-/[\\-}\r\n" "${1:0:1}"
else
tr -dc "${JSSH_KEYOK/\[-/[\\-}\r\n"
@ -64,7 +66,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
[ -z "${DB}" ] && return 1
[ ! -f "${DB}" ] && return 2
# shared lock, many processes can read, max wait 1s
{ flock -s -w 1 200; Json2Array "$1" <"${DB}"; } 200>"${DB}${JSSH_LOCKNAME}"
{ flock -s -w 1 200; Json2Array "$1" <"${DB}"; } 200>"${DB}${JSSHDB_LOCKNAME}"
}
# write ARRAY content to a file in JSON.sh format
@ -76,7 +78,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
[ -z "${DB}" ] && return 1
[ ! -f "${DB}" ] && return 2
# exclusive lock, no other process can read or write, maximum wait to get lock is 10s
{ flock -e -w 10 200; Array2Json "$1" >"${DB}"; } 200>"${DB}${JSSH_LOCKNAME}"
{ flock -e -w 10 200; Array2Json "$1" >"${DB}"; } 200>"${DB}${JSSHDB_LOCKNAME}"
}
# update/write ARRAY content in file without deleting keys not in ARRAY
@ -86,16 +88,16 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
jssh_updateDB() {
# for atomic update we can't use read/writeDB
[ -z "$2" ] && return 1
local DB="$2.jssh" # check in async
local DB="$2.jssh" # check in async
[ ! -f "${DB}" ] && return 2
{ flock -e -w 10 200; jssh_updateDB_async "$@"; } 200>"${DB}${JSSH_LOCKNAME}"
{ flock -e -w 10 200; jssh_updateDB_async "$@"; } 200>"${DB}${JSSHDB_LOCKNAME}"
}
# insert, update, apped key/value to jsshDB
# $1 key name, can only contain -a-zA-Z0-9,._
# $2 key value
# $3 filename (must exist!), must be relative to BASHBOT_ETC, and not contain '..'
alias jssh_insertDB=jssh_insertKeyDB # backward compatibility
alias jssh_insertDB=jssh_insertKeyDB # backward compatibility
# renamed to be more consistent
jssh_insertKeyDB() {
[[ "$1" =~ ^${JSSH_KEYOK}+$ ]] || return 3
@ -106,7 +108,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
{ flock -e -w 2 200
# it's append, but last one counts, its a simple DB ...
printf '["%s"]\t"%s"\n' "${1//,/\",\"}" "${2//\"/\\\"}" >>"${DB}"
} 200>"${DB}${JSSH_LOCKNAME}"
} 200>"${DB}${JSSHDB_LOCKNAME}"
}
@ -119,7 +121,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
[[ "$1" =~ ^${JSSH_KEYOK}+$ ]] || return 3
local DB="$2.jssh"
# start atomic delete here, exclusive max wait 10s
{ flock -e -w 10 200; jssh_deleteKeyDB_async "$@"; } 200>"${DB}${JSSH_LOCKNAME}"
{ flock -e -w 10 200; jssh_deleteKeyDB_async "$@"; } 200>"${DB}${JSSHDB_LOCKNAME}"
}
# get key/value from jsshDB
@ -133,7 +135,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
# start atomic delete here, exclusive max wait 1s
{ flock -s -w 1 200
[ -r "${DB}" ] && sed -n 's/\["'"$1"'"\]\t*"\(.*\)"/\1/p' "${DB}" | tail -n 1
} 200>"${DB}${JSSH_LOCKNAME}"
} 200>"${DB}${JSSHDB_LOCKNAME}"
}
@ -148,7 +150,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
[[ "$1" =~ ^${JSSH_KEYOK}+$ ]] || return 3
local DB="$2.jssh"
# start atomic delete here, exclusive max wait 5
{ flock -e -w 5 200; jssh_countKeyDB_async "$@"; } 200>"${DB}${JSSH_LOCKNAME}"
{ flock -e -w 5 200; jssh_countKeyDB_async "$@"; } 200>"${DB}${JSSHDB_LOCKNAME}"
}
# update key/value in place to jsshDB
@ -169,7 +171,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
jssh_clearDB() {
local DB; DB="$(jssh_checkDB "$1")"
[ -z "${DB}" ] && return 1
{ flock -e -w 10 200; printf '' >"${DB}"; } 200>"${DB}${JSSH_LOCKNAME}"
{ flock -e -w 10 200; printf '' >"${DB}"; } 200>"${DB}${JSSHDB_LOCKNAME}"
}
# updates Array if DB file has changed since last call
@ -179,7 +181,7 @@ if [ "$(LC_ALL=C type -t "flock")" = "file" ]; then
# medium complex, wrapper async
jssh_updateArray() {
[ -z "$2" ] && return 1
local DB="$2.jssh" # name check in async
local DB="$2.jssh" # name check in async
[ ! -f "${DB}" ] && return 2
declare -n ARRAY="$1"
[[ -z "${ARRAY[*]}" || "${DB}" -nt "${DB}.last$3" ]] && touch "${DB}.last$3" && jssh_readDB "$1" "$2"
@ -216,7 +218,7 @@ jssh_newDB_async() { jssh_newDB "$@"; }
jssh_newDB() {
local DB; DB="$(jssh_checkDB "$1")"
[ -z "${DB}" ] && return 1
[ -f "${DB}" ] && return 2 # already exist
[ -f "${DB}" ] && return 2 # already exist
touch "${DB}"
}
@ -353,9 +355,10 @@ function jssh_updateArray_async() {
# read JSON.sh style data and asssign to an ARRAY
# $1 ARRAY name, must be declared with "declare -A ARRAY" before calling
Json2Array() {
# match ["....."]\t and replace \t with = and print quote true false escape not escaped $
# shellcheck disable=SC1091,SC1090
[ -z "$1" ] || source <( printf "$1"'=( %s )' "$(sed -E -n -e '/\["[-0-9a-zA-Z_,."]+"\]\+*\t/ s/\t/=/p' -e 's/=(true|false)/="\1"/' -e 's/([^\]|^)\$/\1\\$/g')" )
# step 1: output only basic pattern
[ -z "$1" ] || source <( printf "$1"'=( %s )'\
"$(sed -E -n -e 's/[`´]//g' -e 's/\t(true|false)/\t"\1"/' -e 's/([^\]|^)\$/\1\\$/g' -e '/\["[-0-9a-zA-Z_,."]+"\]\+*\t/ s/\t/=/p')" )
}
# get Config Key from jssh file without jsshDB
# output ARRAY as JSON.sh style data
@ -366,7 +369,7 @@ Array2Json() {
declare -n ARRAY="$1"
for key in "${!ARRAY[@]}"
do
[[ "${key}" =~ ^${JSSH_KEYOK}+$ ]] || continue
[[ ! "${key}" =~ ^${JSSH_KEYOK}+$ || "${ARRAY[${key}]}" == "${JSSHDB_UNSET}" ]] && continue
# in case value contains newline convert to \n
: "${ARRAY[${key}]//$'\n'/\\n}"
printf '["%s"]\t"%s"\n' "${key//,/\",\"}" "${_//\"/\\\"}"

507
modules/processUpdates.sh Normal file
View File

@ -0,0 +1,507 @@
#!/bin/bash
##################################################################
#
# File: processUpdates.sh
# Note: DO NOT EDIT! this file will be overwritten on update
#
#### $$VERSION$$ v1.52-1-g0dae2db
##################################################################
##############
# manage webhooks
# $1 URL to sed updates to: https://host.dom[:port][/path], port and path are optional
# port must be 443, 80, 88 8443, TOKEN will be added to URL for security
# e.g. https://myhost.com -> https://myhost.com/12345678:azndfhbgdfbbbdsfg
# $2 max connections 1-100 default 1 (because of bash ;-)
set_webhook() {
local url='"url": "'"$1/${BOTTOKEN}/"'"'
local max=',"max_connections": 1'
[[ "$2" =~ ^[0-9]+$ ]] && max=',"max_connections": '"$2"''
# shellcheck disable=SC2153
sendJson "" "${url}${max}" "${URL}/setWebhook"
unset "BOTSENT[ID]" "BOTSENT[CHAT]"
}
get_webhook_info() {
sendJson "" "" "${URL}/getWebhookInfo"
if [ "${BOTSENT[OK]}" = "true" ]; then
BOTSENT[URL]="${UPD[result,url]}"
BOTSENT[COUNT]="${UPD[result,pending_update_count]}"
BOTSENT[CERT]="${UPD[result,has_custom_certificate]}"
BOTSENT[LASTERR]="${UPD[result,last_error_message]}"
unset "BOTSENT[ID]" "BOTSENT[CHAT]"
fi
}
# $1 drop pending updates true/false, default false
delete_webhook() {
local drop; [ "$1" = "true" ] && drop='"drop_pending_updates": true'
sendJson "" "${drop}" "${URL}/deleteWebhook"
unset "BOTSENT[ID]" "BOTSENT[CHAT]"
}
################
# processing of array of updates starts here
process_multi_updates() {
local max num debug="$1"
# get num array elements
max="$(grep -F ',"update_id"]' <<< "${UPDATE}" | tail -1 | cut -d , -f 2 )"
# escape bash $ expansion bug
UPDATE="${UPDATE//$/\\$}"
# convert updates to bash array
Json2Array 'UPD' <<<"${UPDATE}"
# iterate over array
for ((num=0; num<=max; num++)); do
process_update "${num}" "${debug}"
done
}
################
# processing of a single array item of update
# $1 array index
process_update() {
local chatuser="Chat" num="$1" debug="$2"
pre_process_message "${num}"
# log message on debug
[[ -n "${debug}" ]] && log_message "New Message ==========\n$(grep -F '["result",'"${num}" <<<"${UPDATE}")"
# check for users / groups to ignore, inform them ...
jssh_updateArray_async "BASHBOTBLOCKED" "${BLOCKEDFILE}"
if [ -n "${USER[ID]}" ] && [[ -n "${BASHBOTBLOCKED[${USER[ID]}]}" || -n "${BASHBOTBLOCKED[${CHAT[ID]}]}" ]];then
[ -n "${BASHBOTBLOCKED[${USER[ID]}]}" ] && chatuser="User"
[ "${NOTIFY_BLOCKED_USERS}" == "yes" ] &&\
send_normal_message "${CHAT[ID]}" "${chatuser} blocked because: ${BASHBOTBLOCKED[${USER[ID]}]} ${BASHBOTBLOCKED[${CHAT[ID]}]}" &
return
fi
# process per message type
if [ -n "${iQUERY[ID]}" ]; then
process_inline_query "${num}" "${debug}"
printf "%(%c)T: Inline Query update received FROM=%s iQUERY=%s\n" -1\
"${iQUERY[USERNAME]:0:20} (${iQUERY[USER_ID]})" "${iQUERY[0]}" >>"${UPDATELOG}"
elif [ -n "${iBUTTON[ID]}" ]; then
process_inline_button "${num}" "${debug}"
printf "%(%c)T: Inline Button update received FROM=%s CHAT=%s CALLBACK=%s DATA:%s \n" -1\
"${iBUTTON[USERNAME]:0:20} (${iBUTTON[USER_ID]})" "${iBUTTON[CHAT_ID]}" "${iBUTTON[ID]}" "${iBUTTON[DATA]}" >>"${UPDATELOG}"
else
if grep -qs -e '\["result",'"${num}"',"edited_message"' <<<"${UPDATE}"; then
# edited message
UPDATE="${UPDATE//,${num},\"edited_message\",/,${num},\"message\",}"
Json2Array 'UPD' <<<"${UPDATE}"
MESSAGE[0]="/_edited_message "
fi
process_message "${num}" "${debug}"
printf "%(%c)T: update received FROM=%s CHAT=%s CMD=%s\n" -1 "${USER[USERNAME]:0:20} (${USER[ID]})"\
"${CHAT[USERNAME]:0:20}${CHAT[TITLE]:0:30} (${CHAT[ID]})"\
"${MESSAGE:0:30}${CAPTION:0:30}${URLS[*]}" >>"${UPDATELOG}"
if [[ -z "${USER[ID]}" || -z "${CHAT[ID]}" ]]; then
printf "%(%c)T: IGNORE unknown update type: %s\n" -1 "$(grep '\["result",'"${num}"'.*,"id"\]' <<<"${UPDATE}")" >>"${UPDATELOG}"
return 1
fi
fi
#####
# process inline and message events
# first classic command dispatcher
# shellcheck disable=SC2153,SC1090
{ source "${COMMANDS}" "${debug}"; } &
# then all registered addons
if [ -z "${iQUERY[ID]}" ]; then
event_message "${debug}"
else
event_inline "${debug}"
fi
# last count users
jssh_countKeyDB_async "${CHAT[ID]}" "${COUNTFILE}"
}
pre_process_message(){
local num="$1"
# unset everything to not have old values
CMD=( ); iQUERY=( ); iBUTTON=(); MESSAGE=(); CHAT=(); USER=(); CONTACT=(); LOCATION=(); unset CAPTION
REPLYTO=( ); FORWARD=( ); URLS=(); VENUE=( ); SERVICE=( ); NEWMEMBER=( ); LEFTMEMBER=( ); PINNED=( ); MIGRATE=( )
iQUERY[ID]="${UPD["result,${num},inline_query,id"]}"
iBUTTON[ID]="${UPD["result,${num},callback_query,id"]}"
CHAT[ID]="${UPD["result,${num},message,chat,id"]}"
USER[ID]="${UPD["result,${num},message,from,id"]}"
[ -z "${CHAT[ID]}" ] && CHAT[ID]="${UPD["result,${num},edited_message,chat,id"]}"
[ -z "${USER[ID]}" ] && USER[ID]="${UPD["result,${num},edited_message,from,id"]}"
# always true
return 0
}
process_inline_query() {
local num="$1"
iQUERY[0]="$(JsonDecode "${UPD["result,${num},inline_query,query"]}")"
iQUERY[USER_ID]="${UPD["result,${num},inline_query,from,id"]}"
iQUERY[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},inline_query,from,first_name"]}")"
iQUERY[LAST_NAME]="$(JsonDecode "${UPD["result,${num},inline_query,from,last_name"]}")"
iQUERY[USERNAME]="$(JsonDecode "${UPD["result,${num},inline_query,from,username"]}")"
# always true
return 0
}
process_inline_button() {
local num="$1"
iBUTTON[DATA]="${UPD["result,${num},callback_query,data"]}"
iBUTTON[CHAT_ID]="${UPD["result,${num},callback_query,message,chat,id"]}"
iBUTTON[MESSAGE_ID]="${UPD["result,${num},callback_query,message,message_id"]}"
iBUTTON[MESSAGE]="$(JsonDecode "${UPD["result,${num},callback_query,message,text"]}")"
# XXX should we give back pressed button, all buttons or nothing?
iBUTTON[USER_ID]="${UPD["result,${num},callback_query,from,id"]}"
iBUTTON[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},callback_query,from,first_name"]}")"
iBUTTON[LAST_NAME]="$(JsonDecode "${UPD["result,${num},callback_query,from,last_name"]}")"
iBUTTON[USERNAME]="$(JsonDecode "${UPD["result,${num},callback_query,from,username"]}")"
# always true
return 0
}
process_message() {
local num="$1"
# Message
MESSAGE[0]+="$(JsonDecode "${UPD["result,${num},message,text"]}" | sed 's|\\/|/|g')"
MESSAGE[ID]="${UPD["result,${num},message,message_id"]}"
MESSAGE[CAPTION]="$(JsonDecode "${UPD["result,${num},message,caption"]}")"
CAPTION="${MESSAGE[CAPTION]}" # backward compatibility
# dice received
MESSAGE[DICE]="${UPD["result,${num},message,dice,emoji"]}"
if [ -n "${MESSAGE[DICE]}" ]; then
MESSAGE[RESULT]="${UPD["result,${num},message,dice,value"]}"
MESSAGE[0]="/_dice_received ${MESSAGE[DICE]} ${MESSAGE[RESULT]}"
fi
# Chat ID is now parsed when update is received
CHAT[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,chat,last_name"]}")"
CHAT[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,chat,first_name"]}")"
CHAT[USERNAME]="$(JsonDecode "${UPD["result,${num},message,chat,username"]}")"
# set real name as username if empty
[ -z "${CHAT[USERNAME]}" ] && CHAT[USERNAME]="${CHAT[FIRST_NAME]} ${CHAT[LAST_NAME]}"
CHAT[TITLE]="$(JsonDecode "${UPD["result,${num},message,chat,title"]}")"
CHAT[TYPE]="$(JsonDecode "${UPD["result,${num},message,chat,type"]}")"
CHAT[ALL_ADMIN]="${UPD["result,${num},message,chat,all_members_are_administrators"]}"
# user ID is now parsed when update is received
USER[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,from,first_name"]}")"
USER[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,from,last_name"]}")"
USER[USERNAME]="$(JsonDecode "${UPD["result,${num},message,from,username"]}")"
# set real name as username if empty
[ -z "${USER[USERNAME]}" ] && USER[USERNAME]="${USER[FIRST_NAME]} ${USER[LAST_NAME]}"
# in reply to message from
if [ -n "${UPD["result,${num},message,reply_to_message,from,id"]}" ]; then
REPLYTO[UID]="${UPD["result,${num},message,reply_to_message,from,id"]}"
REPLYTO[0]="$(JsonDecode "${UPD["result,${num},message,reply_to_message,text"]}")"
REPLYTO[ID]="${UPD["result,${num},message,reply_to_message,message_id"]}"
REPLYTO[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,reply_to_message,from,first_name"]}")"
REPLYTO[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,reply_to_message,from,last_name"]}")"
REPLYTO[USERNAME]="$(JsonDecode "${UPD["result,${num},message,reply_to_message,from,username"]}")"
fi
# forwarded message from
if [ -n "${UPD["result,${num},message,forward_from,id"]}" ]; then
FORWARD[UID]="${UPD["result,${num},message,forward_from,id"]}"
FORWARD[ID]="${MESSAGE[ID]}" # same as message ID
FORWARD[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,forward_from,first_name"]}")"
FORWARD[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,forward_from,last_name"]}")"
FORWARD[USERNAME]="$(JsonDecode "${UPD["result,${num},message,forward_from,username"]}")"
fi
# get file URL from telegram, check for any of them!
if grep -qs -e '\["result",'"${num}"',"message","[avpsd].*,"file_id"\]' <<<"${UPDATE}"; then
URLS[AUDIO]="$(get_file "${UPD["result,${num},message,audio,file_id"]}")"
URLS[DOCUMENT]="$(get_file "${UPD["result,${num},message,document,file_id"]}")"
URLS[PHOTO]="$(get_file "${UPD["result,${num},message,photo,0,file_id"]}")"
URLS[STICKER]="$(get_file "${UPD["result,${num},message,sticker,file_id"]}")"
URLS[VIDEO]="$(get_file "${UPD["result,${num},message,video,file_id"]}")"
URLS[VOICE]="$(get_file "${UPD["result,${num},message,voice,file_id"]}")"
fi
# Contact, must have phone_number
if [ -n "${UPD["result,${num},message,contact,phone_number"]}" ]; then
CONTACT[USER_ID]="$(JsonDecode "${UPD["result,${num},message,contact,user_id"]}")"
CONTACT[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,contact,first_name"]}")"
CONTACT[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,contact,last_name"]}")"
CONTACT[NUMBER]="${UPD["result,${num},message,contact,phone_number"]}"
CONTACT[VCARD]="${UPD["result,${num},message,contact,vcard"]}"
fi
# venue, must have a position
if [ -n "${UPD["result,${num},message,venue,location,longitude"]}" ]; then
VENUE[TITLE]="$(JsonDecode "${UPD["result,${num},message,venue,title"]}")"
VENUE[ADDRESS]="$(JsonDecode "${UPD["result,${num},message,venue,address"]}")"
VENUE[LONGITUDE]="${UPD["result,${num},message,venue,location,longitude"]}"
VENUE[LATITUDE]="${UPD["result,${num},message,venue,location,latitude"]}"
VENUE[FOURSQUARE]="${UPD["result,${num},message,venue,foursquare_id"]}"
fi
# Location
LOCATION[LONGITUDE]="${UPD["result,${num},message,location,longitude"]}"
LOCATION[LATITUDE]="${UPD["result,${num},message,location,latitude"]}"
# service messages, group or channel only!
if [[ "${CHAT[ID]}" == "-"* ]] ; then
# new chat member
if [ -n "${UPD["result,${num},message,new_chat_member,id"]}" ]; then
SERVICE[NEWMEMBER]="${UPD["result,${num},message,new_chat_member,id"]}"
NEWMEMBER[ID]="${SERVICE[NEWMEMBER]}"
NEWMEMBER[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,new_chat_member,first_name"]}")"
NEWMEMBER[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,new_chat_member,last_name"]}")"
NEWMEMBER[USERNAME]="$(JsonDecode "${UPD["result,${num},message,new_chat_member,username"]}")"
NEWMEMBER[ISBOT]="${UPD["result,${num},message,new_chat_member,is_bot"]}"
MESSAGE[0]="/_new_chat_member ${NEWMEMBER[ID]} ${NEWMEMBER[USERNAME]:=${NEWMEMBER[FIRST_NAME]} ${NEWMEMBER[LAST_NAME]}}"
fi
# left chat member
if [ -n "${UPD["result,${num},message,left_chat_member,id"]}" ]; then
SERVICE[LEFTMEMBER]="${UPD["result,${num},message,left_chat_member,id"]}"
LEFTMEMBER[ID]="${SERVICE[LEFTMEBER]}"
LEFTMEMBER[FIRST_NAME]="$(JsonDecode "${UPD["result,${num},message,left_chat_member,first_name"]}")"
LEFTMEMBER[LAST_NAME]="$(JsonDecode "${UPD["result,${num},message,left_chat_member,last_name"]}")"
LEFTMEBER[USERNAME]="$(JsonDecode "${UPD["result,${num},message,left_chat_member,username"]}")"
LEFTMEMBER[ISBOT]="${UPD["result,${num},message,left_chat_member,is_bot"]}"
MESSAGE[0]="/_left_chat_member ${LEFTMEMBER[ID]} ${LEFTMEMBER[USERNAME]:=${LEFTMEMBER[FIRST_NAME]} ${LEFTMEMBER[LAST_NAME]}}"
fi
# chat title / photo, check for any of them!
if grep -qs -e '\["result",'"${num}"',"message","new_chat_[tp]' <<<"${UPDATE}"; then
SERVICE[NEWTITLE]="$(JsonDecode "${UPD["result,${num},message,new_chat_title"]}")"
[ -n "${SERVICE[NEWTITLE]}" ] &&\
MESSAGE[0]="/_new_chat_title ${USER[ID]} ${SERVICE[NEWTITLE]}"
SERVICE[NEWPHOTO]="$(get_file "${UPD["result,${num},message,new_chat_photo,0,file_id"]}")"
[ -n "${SERVICE[NEWPHOTO]}" ] &&\
MESSAGE[0]="/_new_chat_photo ${USER[ID]} ${SERVICE[NEWPHOTO]}"
fi
# pinned message
if [ -n "${UPD["result,${num},message,pinned_message,message_id"]}" ]; then
SERVICE[PINNED]="${UPD["result,${num},message,pinned_message,message_id"]}"
PINNED[ID]="${SERVICE[PINNED]}"
PINNED[MESSAGE]="$(JsonDecode "${UPD["result,${num},message,pinned_message,text"]}")"
MESSAGE[0]="/_new_pinned_message ${USER[ID]} ${PINNED[ID]} ${PINNED[MESSAGE]}"
fi
# migrate to super group
if [ -n "${UPD["result,${num},message,migrate_to_chat_id"]}" ]; then
MIGRATE[TO]="${UPD["result,${num},message,migrate_to_chat_id"]}"
MIGRATE[FROM]="${UPD["result,${num},message,migrate_from_chat_id"]}"
# CHAT is already migrated, so set new chat id
[ "${CHAT[ID]}" = "${MIGRATE[FROM]}" ] && CHAT[ID]="${MIGRATE[FROM]}"
SERVICE[MIGRATE]="${MIGRATE[FROM]} ${MIGRATE[TO]}"
MESSAGE[0]="/_migrate_group ${SERVICE[MIGRATE]}"
fi
# set SERVICE to yes if a service message was received
[[ "${SERVICE[*]}" =~ ^[[:blank:]]*$ ]] || SERVICE[0]="yes"
fi
# split message in command and args
[[ "${MESSAGE[0]}" == "/"* ]] && read -ra CMD <<<"${MESSAGE[0]}" && CMD[0]="${CMD[0]%%@*}"
# everything went well
return 0
}
#########################
# bot startup actions, call before start polling or webhook loop
declare -A BASHBOTBLOCKED
start_bot() {
local DEBUGMSG
# startup message
DEBUGMSG="BASHBOT startup actions, mode set to \"${1:-normal}\" =========="
log_update "${DEBUGMSG}"
# redirect to Debug.log
if [[ "$1" == *"debug" ]]; then
# shellcheck disable=SC2153
exec &>>"${DEBUGLOG}"
log_debug "${DEBUGMSG}";
fi
DEBUGMSG="$1"
[[ "${DEBUGMSG}" == "xdebug"* ]] && set -x
# cleaup old pipes and empty logfiles
find "${DATADIR}" -type p -not -name "webhook-fifo-*" -delete
find "${DATADIR}" -size 0 -name "*.log" -delete
# load addons on startup
for addons in "${ADDONDIR:-.}"/*.sh ; do
# shellcheck disable=SC1090
[ -r "${addons}" ] && source "${addons}" "startbot" "${DEBUGMSG}"
done
# shellcheck disable=SC1090
source "${COMMANDS}" "startbot"
# start timer events
if [ -n "${BASHBOT_START_TIMER}" ] ; then
# shellcheck disable=SC2064
trap "event_timer ${DEBUGMSG}" ALRM
start_timer &
# shellcheck disable=SC2064
trap "kill -9 $!; exit" EXIT INT HUP TERM QUIT
fi
# cleanup on start
bot_cleanup "startup"
# read blocked users
jssh_readDB_async "BASHBOTBLOCKED" "${BLOCKEDFILE}"
# inform botadmin about start
send_normal_message "$(getConfigKey "botadmin")" "Bot ${ME} $2 started ..." &
}
# main polling updates loop, should never terminate
get_updates(){
local errsleep="200" DEBUG="$1" OFFSET=0
# adaptive sleep defaults
local nextsleep="100"
local stepsleep="${BASHBOT_SLEEP_STEP:-100}"
local maxsleep="${BASHBOT_SLEEP:-5000}"
printf "%(%c)T: %b\n" -1 "Bot startup actions done, start polling updates ..."
while true; do
# adaptive sleep in ms rounded to next 0.1 s
sleep "$(_round_float "${nextsleep}e-3" "1")"
# get next update
# shellcheck disable=SC2153
UPDATE="$(getJson "${URL}/getUpdates?offset=${OFFSET}" 2>/dev/null | "${JSONSHFILE}" -b -n 2>/dev/null | iconv -f utf-8 -t utf-8 -c)"
# did we get an response?
if [ -n "${UPDATE}" ]; then
# we got something, do processing
[ "${OFFSET}" = "-999" ] && [ "${nextsleep}" -gt "$((maxsleep*2))" ] &&\
log_error "Recovered from timeout/broken/no connection, continue with telegram updates"
# calculate next sleep interval
((nextsleep+= stepsleep , nextsleep= nextsleep>maxsleep ?maxsleep:nextsleep))
# warn if webhook is set
if grep -q '^\["error_code"\] 409' <<<"${UPDATE}"; then
[ "${OFFSET}" != "-999" ] && nextsleep="${stepsleep}"
OFFSET="-999"; errsleep="$(_round_float "$(( errsleep= 300*nextsleep ))e-3")"
log_error "Warning conflicting webhook set, can't get updates until your run delete_webhook! Sleep $((errsleep/60)) min ..."
sleep "${errsleep}"
continue
fi
# Offset
OFFSET="$(grep <<<"${UPDATE}" '\["result",[0-9]*,"update_id"\]' | tail -1 | cut -f 2)"
((OFFSET++))
if [ "${OFFSET}" != "1" ]; then
nextsleep="100"
process_multi_updates "${DEBUG}"
fi
else
# oops, something bad happened, wait maxsleep*10
(( nextsleep=nextsleep*2 , nextsleep= nextsleep>maxsleep*10 ?maxsleep*10:nextsleep ))
# second time, report problem
if [ "${OFFSET}" = "-999" ]; then
log_error "Repeated timeout/broken/no connection on telegram update, sleep $(_round_float "${nextsleep}e-3")s"
# try to recover
if _is_function bashbotBlockRecover && [ -z "$(getJson "${ME_URL}")" ]; then
log_error "Try to recover, calling bashbotBlockRecover ..."
bashbotBlockRecover >>"${ERRORLOG}"
fi
fi
OFFSET="-999"
fi
done
}
declare -Ax BASHBOT_EVENT_INLINE BASHBOT_EVENT_MESSAGE BASHBOT_EVENT_CMD BASHBOT_EVENT_REPLYTO BASHBOT_EVENT_FORWARD BASHBOT_EVENT_SEND
declare -Ax BASHBOT_EVENT_CONTACT BASHBOT_EVENT_LOCATION BASHBOT_EVENT_FILE BASHBOT_EVENT_TEXT BASHBOT_EVENT_TIMER BASHBOT_BLOCKED
start_timer(){
# send alarm every ~60 s
while :; do
sleep 59.5
kill -ALRM $$
done;
}
EVENT_TIMER="0"
event_timer() {
local key timer debug="$1"
(( EVENT_TIMER++ ))
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_TIMER[@]}"
do
timer="${key##*,}"
[[ ! "${timer}" =~ ^-*[1-9][0-9]*$ ]] && continue
if [ "$(( EVENT_TIMER % timer ))" = "0" ]; then
_exec_if_function "${BASHBOT_EVENT_TIMER[${key}]}" "timer" "${key}" "${debug}"
[ "$(( EVENT_TIMER % timer ))" -lt "0" ] && \
unset BASHBOT_EVENT_TIMER["${key}"]
fi
done
}
event_inline() {
local key debug="$1"
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_INLINE[@]}"
do
_exec_if_function "${BASHBOT_EVENT_INLINE[${key}]}" "inline" "${key}" "${debug}"
done
}
event_message() {
local key debug="$1"
# ${MESSAEG[*]} event_message
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_MESSAGE[@]}"
do
_exec_if_function "${BASHBOT_EVENT_MESSAGE[${key}]}" "message" "${key}" "${debug}"
done
# ${TEXT[*]} event_text
if [ -n "${MESSAGE[0]}" ]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_TEXT[@]}"
do
_exec_if_function "${BASHBOT_EVENT_TEXT[${key}]}" "text" "${key}" "${debug}"
done
# ${CMD[*]} event_cmd
if [ -n "${CMD[0]}" ]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_CMD[@]}"
do
_exec_if_function "${BASHBOT_EVENT_CMD[${key}]}" "command" "${key}" "${debug}"
done
fi
fi
# ${REPLYTO[*]} event_replyto
if [ -n "${REPLYTO[UID]}" ]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_REPLYTO[@]}"
do
_exec_if_function "${BASHBOT_EVENT_REPLYTO[${key}]}" "replyto" "${key}" "${debug}"
done
fi
# ${FORWARD[*]} event_forward
if [ -n "${FORWARD[UID]}" ]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_FORWARD[@]}"
do
_exec_if_function && "${BASHBOT_EVENT_FORWARD[${key}]}" "forward" "${key}" "${debug}"
done
fi
# ${CONTACT[*]} event_contact
if [ -n "${CONTACT[FIRST_NAME]}" ]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_CONTACT[@]}"
do
_exec_if_function "${BASHBOT_EVENT_CONTACT[${key}]}" "contact" "${key}" "${debug}"
done
fi
# ${VENUE[*]} event_location
# ${LOCATION[*]} event_location
if [ -n "${LOCATION[LONGITUDE]}" ] || [ -n "${VENUE[TITLE]}" ]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_LOCATION[@]}"
do
_exec_if_function "${BASHBOT_EVENT_LOCATION[${key}]}" "location" "${key}" "${debug}"
done
fi
# ${URLS[*]} event_file
# NOTE: compare again #URLS -1 blanks!
if [[ "${URLS[*]}" != " " ]]; then
# shellcheck disable=SC2153
for key in "${!BASHBOT_EVENT_FILE[@]}"
do
_exec_if_function "${BASHBOT_EVENT_FILE[${key}]}" "file" "${key}" "${debug}"
done
fi
}

View File

@ -6,7 +6,7 @@
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
# shellcheck disable=SC1117
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# will be automatically sourced from bashbot
@ -25,7 +25,6 @@ EDIT_URL=${URL}'/editMessageText'
# $1 CHAT $2 message
send_normal_message() {
local len text; text="$(JsonEscape "$2")"
text="${text//$'\n'/\\n}"
until [ -z "${text}" ]; do
if [ "${#text}" -le 4096 ]; then
sendJson "$1" '"text":"'"${text}"'"' "${MSG_URL}"
@ -38,46 +37,74 @@ send_normal_message() {
text="${text:$((len+2))}"
fi
done
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 CHAT $2 message
send_markdown_message() {
_format_message_url "$1" "$2" ',"parse_mode":"markdown"' "${MSG_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 CHAT $2 message
send_markdownv2_message() {
_markdownv2_message_url "$1" "$2" ',"parse_mode":"markdownv2"' "${MSG_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 CHAT $2 message
send_html_message() {
_format_message_url "$1" "$2" ',"parse_mode":"html"' "${MSG_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 CHAT $2 msg-id $3 message
edit_normal_message() {
_format_message_url "$1" "$3" ',"message_id":'"$2"'' "${EDIT_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 CHAT $2 msg-id $3 message
edit_markdown_message() {
_format_message_url "$1" "$3" ',"message_id":'"$2"',"parse_mode":"markdown"' "${EDIT_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 CHAT $2 msg-id $3 message
edit_markdownv2_message() {
_markdownv2_message_url "$1" "$3" ',"message_id":'"$2"',"parse_mode":"markdownv2"' "${EDIT_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 CHAT $2 msg-id $3 message
edit_html_message() {
_format_message_url "$1" "$3" ',"message_id":'"$2"',"parse_mode":"html"' "${EDIT_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 chat $2 mesage_id, $3 caption
edit_message_caption() {
sendJson "$1" '"message_id":'"$2"',"caption":"'"$3"'"' "${URL}/editMessageCaption"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $ chat $2 msg_id $3 nolog
delete_message() {
[ -z "$3" ] && log_update "Delete Message CHAT=$1 MSG_ID=$2"
sendJson "$1" '"message_id": '"$2"'' "${URL}/deleteMessage"
[ "${BOTSENT[OK]}" = "true" ] && BOTSENT[CHAT]="$1"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
@ -85,7 +112,6 @@ edit_message_caption() {
# $1 CHAT $2 message $3 action $4 URL
_format_message_url(){
local text; text="$(JsonEscape "$2")"
text="${text//$'\n'/\\n}"
[ "${#text}" -ge 4096 ] && log_error "Warning: html/markdown message longer than 4096 characters, message is rejected if formatting crosses 4096 border."
until [ -z "${text}" ]; do
sendJson "$1" '"text":"'"${text:0:4096}"'"'"$3"'' "$4"
@ -97,7 +123,6 @@ _format_message_url(){
# $1 CHAT $2 message $3 action $4 URL
_markdownv2_message_url() {
local text; text="$(JsonEscape "$2")"
text="${text//$'\n'/\\n}"
[ "${#text}" -ge 4096 ] && log_error "Warning: markdownv2 message longer than 4096 characters, message is rejected if formatting crosses 4096 border."
# markdown v2 needs additional double escaping!
text="$(sed -E -e 's|([_|~`>+=#{}()!.-])|\\\1|g' <<< "${text}")"
@ -119,9 +144,17 @@ send_keyboard() {
text="$(JsonEscape "$2")"
text='"text":"'"${text//$'\n'/\\n}"'"'
fi
# text longer than 4096, send text and keyboard separate
if [ "${#2}" -gt 4096 ]; then
send_normal_message "$1" "$2"
send_keyboard "$1" "..." "$3"
return
fi
local one_time=', "one_time_keyboard":true' && [ -n "$4" ] && one_time=""
sendJson "$1" "${text}"', "reply_markup": {"keyboard": [ '"$3"' ] '"${one_time}"'}' "${MSG_URL}"
# '"text":"$2", "reply_markup": {"keyboard": [ $3 ], "one_time_keyboard": true}'
sendJson "$1" "${text}"', "reply_markup": {"keyboard": [ '"$3"' ] '"${one_time}"'}' "${MSG_URL}"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 CHAT $2 message $3 remove
@ -133,24 +166,79 @@ remove_keyboard() {
fi
sendJson "$1" "${text}"', "reply_markup": {"remove_keyboard":true}' "${MSG_URL}"
# delete message if no message or $3 not empty
[[ -z "$2" || -n "$3" ]] && delete_message "$1" "${BOTSENT[ID]}" "nolog"
#JSON='"text":"$2", "reply_markup": {"remove_keyboard":true}'
[[ -z "$2" || -n "$3" ]] && delete_message "$1" "${BOTSENT[ID]}" "nolog"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# buttons will specified as "texts
#|url" ... "text|url" empty arg starts new row
# url not starting with http:// or https:// will be send as callback_data
send_inline_buttons(){
send_inline_keyboard "$1" "$2" "$(_button_row "${@:3}")"
}
# $1 CHAT $2 message-id $3 buttons
# buttons will specified as "text|url" ... "text|url" empty arg starts new row
# url not starting with http:// or https:// will be send as callback_data
edit_inline_buttons(){
edit_inline_keyboard "$1" "$2" "$(_button_row "${@:3}")"
}
# $1 CHAT $2 message $3 button text $4 button url
send_button() {
send_inline_keyboard "$1" "$2" '[{"text":"'"$(JsonEscape "$3")"'", "url":"'"$4"'"}]'
}
# helper function to create json for a button row
# buttons will specified as "text|url" ... "text|url" empty arg starts new row
# url not starting with http:// or https:// will be send as callback_data
_button_row() {
[ -z "$1" ] && return 1
local arg type json sep
for arg in "$@"
do
[ -z "${arg}" ] && sep="],[" && continue
type="callback_data"
[[ "${arg##*|}" =~ ^(https*://|tg://) ]] && type="url"
json+="${sep}"'{"text":"'"$(JsonEscape "${arg%|*}")"'", "'"${type}"'":"'"${arg##*|}"'"}'
sep=","
done
printf "[%s]" "${json}"
}
# raw inline functions, for special use
# $1 CHAT $2 message-id $3 keyboard
edit_inline_keyboard() {
# JSON='"message_id":"$2", "reply_markup": {"inline_keyboard": [ $3->[{"text":"text", "url":"url"}]<- ]}'
sendJson "$1" '"message_id":'"$2"', "reply_markup": {"inline_keyboard": [ '"$3"' ]}' "${URL}/editMessageReplyMarkup"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 CHAT $2 message $3 keyboard
send_inline_keyboard() {
local text; text='"text":"'$(JsonEscape "$2")'"'; [ -z "$2" ] && text='"text":"'"Keyboard:"'"'
local text; text='"text":"'$(JsonEscape "$2")'"'; [ -z "$2" ] && text='"text":"..."'
sendJson "$1" "${text}"', "reply_markup": {"inline_keyboard": [ '"$3"' ]}' "${MSG_URL}"
# JSON='"text":"$2", "reply_markup": {"inline_keyboard": [ $3->[{"text":"text", "url":"url"}]<- ]}'
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 CHAT $2 message $3 button text $4 URL
send_button() {
send_inline_keyboard "$1" "$2" '[ {"text":"'"$(JsonEscape "$3")"'", "url":"'"$4"'"}]'
# $1 callback id, $2 text to show, alert if not empty
answer_callback_query() {
local alert
[ -n "$3" ] && alert='","show_alert": true'
sendJson "" '"callback_query_id": "'"$1"'","text":"'"$2${alert}"'"' "${URL}/answerCallbackQuery"
}
# $1 chat, $2 file_id on telegram server
send_sticker() {
sendJson "$1" '"sticker": "'"$2"'"' "${URL}/sendSticker"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
@ -160,7 +248,7 @@ if detect_curl ; then
# $1 chat $3 ... $n URL or ID
send_album(){
[ -z "$1" ] && return 1
[ -z "$3" ] && return 2 # minimum 2 files
[ -z "$3" ] && return 2 # minimum 2 files
local CHAT JSON IMAGE; CHAT="$1"; shift
for IMAGE in "$@"
do
@ -181,13 +269,10 @@ else
}
fi
UPLOADDIR="${BASHBOT_UPLOAD:-${DATADIR}/upload}"
# supports local file, URL and file_id
# $1 chat, $2 file https::// file_id:// , $3 caption, $4 extension (optional)
send_file(){
local url what num stat err media capt file="$2" ext="$4"
capt="$(JsonEscape "$3")"
local url what num stat media capt="$3" file="$2" ext="$4"
if [[ "${file}" =~ ^https*:// ]]; then
media="URL"
elif [[ "${file}" == file_id://* ]]; then
@ -196,28 +281,8 @@ send_file(){
else
# we have a file, check file location ...
media="FILE"
[[ "${file}" = *'..'* || "${file}" = '.'* ]] && err=1 # no directory traversal
if [[ "${file}" = '/'* ]] ; then
[[ ! "${file}" =~ ${FILE_REGEX} ]] && err=2 # absolute must match REGEX
else
file="${UPLOADDIR:-NOUPLOADDIR}/${file}" # others must be in UPLOADDIR
fi
[ ! -r "${file}" ] && err=3 # and file must exits of course
# file path error, generate error response
if [ -n "${err}" ]; then
BOTSENT=(); BOTSENT[OK]="false"
case "${err}" in
1) BOTSENT[ERROR]="Path to file $2 contains to much '../' or starts with '.'";;
2) BOTSENT[ERROR]="Path to file $2 does not match regex: ${FILE_REGEX} ";;
3) if [[ "$2" == "/"* ]];then
BOTSENT[ERROR]="File not found: $2"
else
BOTSENT[ERROR]="File not found: ${UPLOADDIR}/$2"
fi;;
esac
[ -n "${BASHBOTDEBUG}" ] && log_message "Error in upload_file: ${BOTSENT[ERROR]}"
return
fi
file="$(checkUploadFile "$1" "$2" "send_file")"
[ -z "${file}" ] && return 1
# file OK, let's continue
fi
@ -265,24 +330,55 @@ send_file(){
return 0
}
# $1 typing upload_photo record_video upload_video record_audio upload_audio upload_document find_location
# $1 chat $2 typing upload_photo record_video upload_video record_audio upload_audio upload_document find_location
send_action() {
[ -z "$2" ] && return
sendJson "$1" '"action": "'"$2"'"' "${URL}/sendChatAction" &
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
}
# $1 chat $2 emoji “🎲”, “🎯”, “🏀”, “⚽”, “🎰" "🎳"
# code: "\ud83c\udfb2" "\ud83c\udfaf" "\ud83c\udfc0" "\u26bd" "\ud83c\udfb0"
# text: ":game_die:" ":dart:" ":basketball:" ":soccer:" :slot_machine:"
# $3 reply_to_id
send_dice() {
local reply emoji='\ud83c\udfb2' # default "🎲"
[[ "$3" =~ ^[${o9o9o9}-]+$ ]] && reply=',"reply_to_message_id":'"$3"',"allow_sending_without_reply": true'
case "$2" in # convert input to single character emoji
*🎲*|*game*|*dice*|*'dfb2'*|*'DFB2'*) : ;;
*🎯*|*dart* |*'dfaf'*|*'DFAF'*) emoji='\ud83c\udfaf' ;;
*🏀*|*basket*|*'dfc0'*|*'DFC0'*) emoji='\ud83c\udfc0' ;;
*⚽*|*soccer*|*'26bd'*|*'26BD'*) emoji='\u26bd' ;;
*🎰*|*slot* |*'dfb0'*|*'DFB0'*) emoji='\ud83c\udfb0' ;;
*🎳*|*bowl* |*'dfb3'*|*'DFB3'*) emoji='\ud83c\udfb3' ;;
esac
sendJson "$1" '"emoji": "'"${emoji}"'"'"${reply}" "${URL}/sendDice"
if [ "${BOTSENT[OK]}" = "true" ]; then
BOTSENT[DICE]="${UPD["result,dice,emoji"]}"
BOTSENT[RESULT]="${UPD["result,dice,value"]}"
else
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2"
fi
}
# $1 CHAT $2 lat $3 long
send_location() {
[ -z "$3" ] && return
sendJson "$1" '"latitude": '"$2"', "longitude": '"$3"'' "${URL}/sendLocation"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 CHAT $2 lat $3 long $4 title $5 address $6 foursquard id
# $1 CHAT $2 lat $3 long $4 title $5 address $6 foursquare id
send_venue() {
local add=""
[ -z "$5" ] && return
[ -n "$6" ] && add=', "foursquare_id": '"$6"''
sendJson "$1" '"latitude": '"$2"', "longitude": '"$3"', "address": "'"$5"'", "title": "'"$4"'"'"${add}" "${URL}/sendVenue"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3" "$4" "$5" "$6"
}
@ -294,9 +390,16 @@ send_venue() {
forward_message() {
[ -z "$3" ] && return
sendJson "$1" '"from_chat_id": '"$2"', "message_id": '"$3"'' "${URL}/forwardMessage"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
forward() { # backward compatibility
forward_message "$@" || return
# $1 CHAT $2 from chat $3 from msg id
copy_message() {
[ -z "$3" ] && return
sendJson "$1" '"from_chat_id": '"$2"', "message_id": '"$3"'' "${URL}/copyMessage"
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
[ -n "${BOTSENT[ERROR]}" ] && processError "${FUNCNAME[0]}" "${BOTSENT[ERROR]}" "$1" "" "${BOTSENT[DESCRIPTION]}" "$2" "$3"
}
# $1 CHAT $2 bashbot formatted message, see manual advanced usage
@ -323,7 +426,7 @@ send_message() {
sent=y
fi
if [ -n "${keyboard}" ]; then
if [[ "${keyboard}" != *"["* ]]; then # pre 0.60 style
if [[ "${keyboard}" != *"["* ]]; then # pre 0.60 style
keyboard="[ ${keyboard//\" \"/\" \] , \[ \"} ]"
fi
send_keyboard "$1" "${text}" "${keyboard}"

View File

@ -1,4 +1,5 @@
#!/bin/bash
# shellcheck disable=SC2034
#######################################################
#
# File: mycommands.conf
@ -11,7 +12,7 @@
# Author: KayM (gnadelwartz), kay@rrr.de
# Created: 09.01.2021 07:27
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#######################################################
##########
@ -46,6 +47,10 @@ Edit commands and messages in mycommands.sh!
# To enable this option in your bot, send the /setinline command to @BotFather.
export INLINE="0"
# Set CALLBACK to 1 in order to receive callback queries.
# callbacks are sent from inline_keyboards (buttons) attached tp bot messages
export CALLBACK="0"
# if your bot is group admin it get commands sent to other bots
# Set MEONLY to 1 to ignore commands sent to other bots
export MEONLY="0"
@ -63,7 +68,11 @@ unset BASHBOT_RETRY
# set value for adaptive sleeping while waiting for uodates in millisconds
# max slepp between polling updates 10s (default 5s)
export BASHBOT_SLEEP="10000"
# export BASHBOT_SLEEP="10000"
# max slepp between polling updates 2s (default 5s)
# export BASHBOT_SLEEP="2000"
# add 0.2s if no update available, up to BASHBOT_SLEEP (default 0.1s)
export BASHBOT_SLEEP_STEP="200"
@ -87,6 +96,9 @@ WELCOME_MSG="Welcome"
# export REPORT_NEWMEMBER="yes"
# export REPORT_LEFTMEMBER="yes"
# uncomment to send user blocked by bot a warning if they send commands
# export NOTIFY_BLOCKED_USERS="yes"
# messages for admin only commands
NOTADMIN="Sorry, this command is allowed for admin or owner only"
NOTBOTADMIN="Sorry, this command is allowed for bot owner only"

View File

@ -13,7 +13,7 @@
# License: WTFPLv2 http://www.wtfpl.net/txt/copying/
# Author: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#######################################################
# shellcheck disable=SC1117
@ -106,12 +106,12 @@ else
"${WELCOME_MSG} ${NEWMEMBER[FIRST_NAME]} ${NEWMEMBER[LAST_NAME]} (@${NEWMEMBER[USERNAME]})"
MYSENTID="${BOTSENT[ID]}"
{ sleep 5; delete_message "${CHAT[ID]}" "${MYSENTID}"; } &
[ -n "${REPORT_NEWMEMBER}" ] && send_normal_message "$(getConfigKey "botadmin")"\
[ -n "${REPORT_NEWMEMBER}" ] && send_normal_message "${BOTADMIN}"\
"New member: ${CHAT[TITLE]} (${CHAT[ID]}): ${NEWMEMBER[FIRST_NAME]} ${NEWMEMBER[LAST_NAME]} (@${NEWMEMBER[USERNAME]})"
fi
;;
'/_left_chat_member'*)
[ -n "${REPORT_LEFTMEMBER}" ] && send_normal_message "$(getConfigKey "botadmin")"\
[ -n "${REPORT_LEFTMEMBER}" ] && send_normal_message "${BOTADMIN}"\
"Left member: ${CHAT[TITLE]} (${CHAT[ID]}): ${LEFTMEMBER[FIRST_NAME]} ${LEFTMEMBER[LAST_NAME]} (@${LEFTMEMBER[USERNAME]})"
;;
'/_migrate_group'*)
@ -123,7 +123,26 @@ else
case "${MESSAGE}" in
##################
# example commands, replace thm by your own
# example commands, replace them by your own
'/_dice_re'*) # dice from user received
sleep 5
local gameresult="*Congratulation ${USER[FIRST_NAME]} ${USER[LAST_NAME]}* you got *${MESSAGE[RESULT]} Points*."
[ -z "${FORWARD[UID]}" ] && send_markdownv2_message "${CHAT[ID]}" "${gameresult}"
;;
'/game'*) # send random dice, edit list to fit your needs
send_dice "${CHAT[ID]}" ":$(printf "slot_machine\ngame_die\ndart\nbasketball\nsoccer\nslot_machine"|sort -R|shuf -n 1shuf -n 1):"
if [ "${BOTSENT[OK]}" = "true" ]; then
local gameresult="*Congratulation ${USER[FIRST_NAME]}* ${USER[LAST_NAME]} you got *${BOTSENT[RESULT]} Points*."
sleep 5
case "${BOTSENT[RESULT]}" in
1) gameresult="*Sorry* only *one Point* ...";;
2) gameresult="*Hey*, 2 Points are *more then one!*";;
5|6) [[ "${BOTSENT[EMOJI]}" =~ fb0$ ]] || gameresult="*Super! ${BOTSENT[RESULT]} Points!*";;
6*) gameresult="*JACKPOT! ${BOTSENT[RESULT]} Points!*";;
esac
send_markdownv2_message "${CHAT[ID]}" "${gameresult}"
fi
;;
'/unpin'*) # unpin all messages if (bot)admin or allowed for user
user_is_allowed "${USER[ID]}" "unpin" "${CHAT[ID]}" &&\
unpinall_chat_messages "${CHAT[ID]}"
@ -131,6 +150,9 @@ else
'/echo'*) # example echo command
send_normal_message "${CHAT[ID]}" "${MESSAGE}"
;;
'/button'*)# inline button, set CALLBACK=1 for processing callbacks
send_inline_buttons "${CHAT[ID]}" "Press Button ..." " Button |RANDOM-BUTTON"
;;
'/question'*) # start interactive questions
checkproc
if [ "${res}" -gt 0 ] ; then
@ -179,6 +201,47 @@ else
esac
}
mycallbacks() {
#######################
# callbacks from buttons attached to messages will be processed here
# no standard use case for processing callbacks, let's log them for some users and chats
case "${iBUTTON[USER_ID]}+${iBUTTON[CHAT_ID]}" in
'USERID1+'*) # do something for all callbacks from USER
printf "%s: U=%s C=%s D=%s\n" "$(date)" "${iBUTTON[USER_ID]}" "${iBUTTON[CHAT_ID]}" "${iBUTTON[DATA]}"\
>>"${DATADIR}/${iBUTTON[USER_ID]}.log"
answer_callback_query "${iBUTTON[ID]}" "Request has been logged in your user log..."
return
;;
*'+CHATID1') # do something for all callbacks from CHAT
printf "%s: U=%s C=%s D=%s\n" "$(date)" "${iBUTTON[USER_ID]}" "${iBUTTON[CHAT_ID]}" "${iBUTTON[DATA]}"\
>>"${DATADIR}/${iBUTTON[CHAT_ID]}.log"
answer_callback_query "${iBUTTON[ID]}" "Request has been logged in chat log..."
return
;;
'USERID2+CHATID2') # do something only for callbacks form USER in CHAT
printf "%s: U=%s C=%s D=%s\n" "$(date)" "${iBUTTON[USER_ID]}" "${iBUTTON[CHAT_ID]}" "${iBUTTON[DATA]}"\
>>"${DATADIR}/${iBUTTON[USER_ID]}-${iBUTTON[CHAT_ID]}.log"
answer_callback_query "${iBUTTON[ID]}" "Request has been logged in user-chat log..."
return
;;
*) # all other callbacks are processed here
local callback_answer
# your processing here ...
# message available?
if [[ -n "${iBUTTON[CHAT_ID]}" && -n "${iBUTTON[MESSAGE_ID]}" ]]; then
if [ "${iBUTTON[DATA]}" = "RANDOM-BUTTON" ]; then
callback_answer="Button pressed"
edit_inline_buttons "${iBUTTON[CHAT_ID]}" "${iBUTTON[MESSAGE_ID]}" "Button ${RANDOM}|RANDOM-BUTTON"
fi
else
callback_answer="Button to old, sorry."
fi
# Telegram needs an ack each callback query, default empty
answer_callback_query "${iBUTTON[ID]}" "${callback_answer}"
;;
esac
}
myinlines() {
#######################
# Inline query examples, do not use them in production (except image search ;-)
@ -237,6 +300,8 @@ else
[ -f ".jssh" ] && printf "%s: %s\n" "$1" "Ups, found file \"${PWD:-.}/.jssh\"! =========="
}
###########################
# example recover from telegram block function
# called when bashbot send_xxx command failed because we can not connect to telegram
# return 0 to retry, return non 0 to give up
bashbotBlockRecover() {
@ -247,7 +312,35 @@ else
return 1
}
# place your processing functions here
###########################
# example error processing
# called when delete Message failed
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
bashbotError_delete_message() {
log_debug "custom errorProcessing delete_message: ERR=$2 CHAT=$3 MSGID=$6 ERTXT=$5"
}
# called when error 403 is returned (and no func processing)
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
bashbotError_403() {
log_debug "custom errorProcessing error 403: FUNC=$1 CHAT=$3 USER=${4:-no-user} MSGID=$6 ERTXT=$5"
local user="$4"; [[ -z "$4" && -n "$3" ]] && user="$3"
if [ -n "${user}" ]; then
# block chat/user
case "$5" in
*"blocked"*)
jssh_insertKeyDB "${user}" "User blocked bot on $(LANG=C date)" "${BLOCKEDFILE}";;
*"kicked"*)
jssh_insertKeyDB "${user}" "Bot kicked from chat on $(LANG=C date)" "${BLOCKEDFILE}";;
*)
jssh_insertKeyDB "${user}" "Reason: $6 on $(LANG=C date)" "${BLOCKEDFILE}";;
esac
fi
}
###########################
# place your processing functions here --------------
# $1 search parameter
my_image_search(){
@ -263,3 +356,4 @@ else
}
fi

View File

@ -10,7 +10,7 @@
# License: WTFPLv2 http://www.wtfpl.net/txt/copying/
# Author: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#######################################################
# shellcheck disable=SC1117
@ -55,6 +55,8 @@ else
[ -n "${REMOVEKEYBOARD}" ] && remove_keyboard "${CHAT[ID]}" &
[[ -n "${REMOVEKEYBOARD_PRIVATE}" && "${CHAT[ID]}" == "${USER[ID]}" ]] && remove_keyboard "${CHAT[ID]}" &
# uncommet to fix first letter upper case because of smartphone auto correction
#[[ "${MESSAGE}" =~ ^/[[:upper:]] ]] && MESSAGE="${MESSAGE:0:1}$(tr '[:upper:]' '[:lower:]' <<<"${MESSAGE:1:1}")${MESSAGE:2}"
case "${MESSAGE}" in
##################
# example command, replace them by your own
@ -77,6 +79,19 @@ else
esac
}
mycallbacks() {
#######################
# callbacks from buttons attached to messages will be processed here
case "${iBUTTON[USER_ID]}+${iBUTTON[CHAT_ID]}" in
*) # all other callbacks are processed here
local callback_answer
: # your processing here ...
:
# Telegram needs an ack each callback query, default empty
answer_callback_query "${iBUTTON[ID]}" "${callback_answer}"
;;
esac
}
myinlines() {
#######################
# this fuinction is called only if you has set INLINE=1 !!
@ -111,4 +126,17 @@ else
done <<<"${result}"
}
###########################
# example error processing
# called when delete Message failed
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
bashbotError_delete_message() {
log_debug "custom errorProcessing delete_message: ERR=$2 CHAT=$3 MSGID=$6 ERTXT=$5"
}
# called when error 403 is returned (and no func processing)
# func="$1" err="$2" chat="$3" user="$4" emsg="$5" remaining args
bashbotError_403() {
log_debug "custom errorProcessing error 403: FUNC=$1 CHAT=$3 USER=${4:-no-user} MSGID=$6 ERTXT=$5"
}
fi

View File

@ -12,7 +12,7 @@
# This file is public domain in the USA and all free countries.
# Elsewhere, consider it to be WTFPLv2. (wtfpl.net/txt/copying)
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
########################################################################
######

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# magic to ensure that we're always inside the root of our application,

View File

@ -11,7 +11,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# common variables
@ -39,12 +39,12 @@ export SUCCESS NOSUCCESS
NOSUCCESS=" FAILED!"
# default input, reference and output files
export INPUTFILE REFFILE INPUTFILE2 REFFILE2 OUTPUTFILE
export INPUTFILE REFFILE OUTPUTFILE INPUTFILELIST
# shellcheck disable=SC2125
INPUTFILELIST="${DIRME}/${REFDIR}/${REFDIR}-"*".input"
OUTPUTFILE="${TESTDIR}/${REFDIR}.out"
INPUTFILE="${DIRME}/${REFDIR}/${REFDIR}.input"
REFFILE="${DIRME}/${REFDIR}/${REFDIR}.result"
INPUTFILE2="${DIRME}/${REFDIR}/${REFDIR}2.input"
REFFILE2="${DIRME}/${REFDIR}/${REFDIR}2.result"
# reset ENVIRONMENT
export BASHBOT_URL TESTTOKEN BOTTOKEN BASHBOT_HOME BASHBOT_VAR BASHBOT_ETC

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
../dev/hooks/pre-commit.sh

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# include common functions and definitions

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# include common functions and definitions

View File

@ -1,5 +1,5 @@
#!/usr/bin/env bash
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
# include common functions and definitions
# shellcheck source=test/ALL-tests.inc.sh

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# include common functions and definitions
@ -41,7 +41,7 @@ source <( printf 'UPD=( %s )' "$(sed <<<"${UPDATE}" -E -e 's/\t/=/g' -e 's/=(tru
printf "Check process_inline ...\n"
printf " ... with JsonDecode Bash\n"
set -x
{ process_inline "0"; set +x; } >>"${LOGFILE}" 2>&1;
{ process_inline_query "0"; set +x; } >>"${LOGFILE}" 2>&1;
# output processed input
print_array "iQUERY" >"${OUTPUTFILE}"

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# include common functions and definitions
@ -38,34 +38,24 @@ declare -Ax UPD
# run process_message --------------
ARRAYS="USER CHAT REPLYTO FORWARD URLS CONTACT CAPTION LOCATION MESSAGE VENUE SERVICE NEWMEMBER LEFTMEMBER PINNED"
printf "Check process_message regular message...\n"
printf "Check process_message ...\n"
UPDATE="$(< "${INPUTFILE}")"
Json2Array 'UPD' <"${INPUTFILE}"
set -x
{ pre_process_message "0"; process_message "0"; set +x; } >>"${LOGFILE}" 2>&1;
USER[ID]="123456789"; CHAT[ID]="123456789"
for testfile in ${INPUTFILELIST}
do
printf " ... %s\n" "${testfile##*/}"
testref="${testfile%.input}.result"
UPDATE="$(< "${testfile}")"
Json2Array 'UPD' <"${testfile}"
set -x
{ pre_process_message "0"; process_message "0"; set +x; } >>"${LOGFILE}" 2>&1;
USER[ID]="123456789"; CHAT[ID]="123456789"
# output processed input
# shellcheck disable=SC2086
print_array ${ARRAYS} >"${OUTPUTFILE}"
compare_sorted "${REFFILE}" "${OUTPUTFILE}" || exit 1
# output processed input
# shellcheck disable=SC2086
print_array ${ARRAYS} >"${OUTPUTFILE}"
compare_sorted "${testref}" "${OUTPUTFILE}" || exit 1
printf "%s\n" "${SUCCESS}"
# run process_message ------------
printf "Check process_message service message...\n"
UPDATE="$(cat "${INPUTFILE2}")"
Json2Array 'UPD' <"${INPUTFILE2}"
set -x
{ pre_process_message "0"; process_message "0"; set +x; } >>"${LOGFILE}" 2>&1;
USER[ID]="123456789"; CHAT[ID]="123456789"
# output processed input
# shellcheck disable=SC2086
print_array ${ARRAYS} >"${OUTPUTFILE}"
compare_sorted "${REFFILE2}" "${OUTPUTFILE}" || exit 1
printf "%s\n" "${SUCCESS}"
done
cd "${DIRME}" || exit 1

View File

@ -0,0 +1,25 @@
["ok"] true
["result",0,"update_id"] 123456789
["result",0,"message","message_id"] 123456789
["result",0,"message","from","id"] 123456789
["result",0,"message","from","is_bot"] false
["result",0,"message","from","first_name"] "Kay"
["result",0,"message","from","last_name"] "M"
["result",0,"message","from","username"] "Gnadelwartz"
["result",0,"message","from","language_code"] "de"
["result",0,"message","chat","id"] -123456789
["result",0,"message","chat","title"] "Testgruppe bot only test"
["result",0,"message","chat","type"] "group"
["result",0,"message","chat","all_members_are_administrators"] true
["result",0,"message","date"] 1592372719
["result",0,"message","left_chat_participant","id"] 123456789
["result",0,"message","left_chat_participant","is_bot"] false
["result",0,"message","left_chat_participant","first_name"] "Kay"
["result",0,"message","left_chat_participant","last_name"] "M"
["result",0,"message","left_chat_participant","username"] "Gnadelwartz"
["result",0,"message","left_chat_member","id"] 123456789
["result",0,"message","left_chat_member","is_bot"] false
["result",0,"message","left_chat_member","first_name"] "Kay"
["result",0,"message","left_chat_member","last_name"] "M"
["result",0,"message","left_chat_member","username"] "Gnadelwartz"

View File

@ -0,0 +1,25 @@
USER: FIRST_NAME Kay
USER: ID 123456789
USER: LAST_NAME M
USER: USERNAME Gnadelwartz
CHAT: ALL_ADMIN true
CHAT: FIRST_NAME
CHAT: ID 123456789
CHAT: LAST_NAME
CHAT: TITLE Testgruppe bot only test
CHAT: TYPE group
CHAT: USERNAME
CAPTION: 0
LOCATION: LATITUDE
LOCATION: LONGITUDE
MESSAGE: 0 /_left_chat_member Kay M
MESSAGE: CAPTION
MESSAGE: DICE
MESSAGE: ID 123456789
SERVICE: 0 yes
SERVICE: LEFTMEMBER 123456789
LEFTMEMBER: FIRST_NAME Kay
LEFTMEMBER: ID
LEFTMEMBER: ISBOT false
LEFTMEMBER: LAST_NAME M
LEFTMEMBER: USERNAME Kay M

View File

@ -31,11 +31,13 @@ CONTACT: LAST_NAME Pannenhilfe
CONTACT: NUMBER 222222
CONTACT: USER_ID
CONTACT: VCARD BEGIN:VCARD\nVERSION:2.1\nN:Pannenhilfe;ADAC;;;\nFN:ADAC Pannenhilfe\nTEL;CELL;PREF:+49179222222\nTEL;X-Mobil:222222\nEND:VCARD
CAPTION: 0
CAPTION: 0 Myproteine kein spell check
LOCATION: LATITUDE 49.631824
LOCATION: LONGITUDE 8.377072
MESSAGE: 0 😂😝👌☺❤😕😈#⃣🌏🎉🙊🙉☕🚀✈🚂💯✔〽🔚
MESSAGE: ID 6541
MESSAGE: CAPTION Myproteine kein spell check
MESSAGE: DICE
VENUE: ADDRESS Am Rhein 1
VENUE: FOURSQUARE 4c4321afce54e21eee980d1a
VENUE: LATITUDE 49.631824

View File

@ -89,3 +89,7 @@
["result",0,"message","voice","duration"] 2
["result",0,"message","voice","mime_type"] "audio/ogg"
["result",0,"message","voice","file_size"] 4262
["result",0,"message","caption"] "Myproteine kein spell check"
["result","dice","emoji"] "\ud83c\udfb2"
["result","dice","value"] 5

View File

@ -0,0 +1,45 @@
USER: FIRST_NAME Kay
USER: ID 123456789
USER: LAST_NAME M
USER: USERNAME Gnadelwartz
CHAT: ALL_ADMIN
CHAT: FIRST_NAME Test
CHAT: ID 123456789
CHAT: LAST_NAME Bot
CHAT: TITLE BotTestTitle
CHAT: TYPE private
CHAT: USERNAME BotTest
REPLYTO: 0 Ich bin der Deal-O-Mat Bot. Für eine Liste der Befehle sende /help
REPLYTO: FIRST_NAME dealzbot
REPLYTO: ID 6542
REPLYTO: LAST_NAME
REPLYTO: UID 987654321
REPLYTO: USERNAME Deal_O_Mat_bot
FORWARD: FIRST_NAME Kay
FORWARD: ID 6541
FORWARD: LAST_NAME M
FORWARD: UID 123456789
FORWARD: USERNAME Gnadelwartz
URLS: AUDIO audio-AgADAgADL6oxG-Gw4EndCWGl2WUfUo1pXw8ABOusSilDGzAYa
URLS: DOCUMENT document-AgADAgADL6oxG-Gw4EndCWGl2WUfUo1pXw8ABOusSilDGzAYa
URLS: PHOTO photo-AgADAgADL6oxG-Gw4EndCWGl2WUfUo1pXw8ABOusSilDGzAYa
URLS: STICKER sticker-AgADAgADL6oxG-Gw4EndCWGl2WUfUo1pXw8ABOusSilDGzAYa
URLS: VIDEO video-AgADAgADL6oxG-Gw4EndCWGl2WUfUo1pXw8ABOusSilDGzAYa
URLS: VOICE voice-AgADAgADL6oxG-Gw4EndCWGl2WUfUo1pXw8ABOusSilDGzAYa
CONTACT: FIRST_NAME ADAC
CONTACT: LAST_NAME Pannenhilfe
CONTACT: NUMBER 222222
CONTACT: USER_ID
CONTACT: VCARD BEGIN:VCARD\nVERSION:2.1\nN:Pannenhilfe;ADAC;;;\nFN:ADAC Pannenhilfe\nTEL;CELL;PREF:+49179222222\nTEL;X-Mobil:222222\nEND:VCARD
CAPTION: 0 Myproteine kein spell check
LOCATION: LATITUDE 49.631824
LOCATION: LONGITUDE 8.377072
MESSAGE: 0 😂😝👌☺❤😕😈#⃣🌏🎉🙊🙉☕🚀✈🚂💯✔〽🔚
MESSAGE: CAPTION Myproteine kein spell check
MESSAGE: DICE
MESSAGE: ID 6541
VENUE: ADDRESS Am Rhein 1
VENUE: FOURSQUARE 4c4321afce54e21eee980d1a
VENUE: LATITUDE 49.631824
VENUE: LONGITUDE 8.377072
VENUE: TITLE Kolb's Biergarten

View File

@ -0,0 +1,25 @@
["ok"] true
["result",0,"update_id"] 123456789
["result",0,"message","message_id"] 123456789
["result",0,"message","from","id"] 123456789
["result",0,"message","from","is_bot"] false
["result",0,"message","from","first_name"] "Kay"
["result",0,"message","from","last_name"] "M"
["result",0,"message","from","username"] "Gnadelwartz"
["result",0,"message","from","language_code"] "de"
["result",0,"message","chat","id"] -123456789
["result",0,"message","chat","title"] "Testgruppe bot only test"
["result",0,"message","chat","type"] "group"
["result",0,"message","chat","all_members_are_administrators"] true
["result",0,"message","date"] 1592372719
["result",0,"message","new_chat_participant","id"] 123456789
["result",0,"message","new_chat_participant","is_bot"] false
["result",0,"message","new_chat_participant","first_name"] "Kay"
["result",0,"message","new_chat_participant","last_name"] "M"
["result",0,"message","new_chat_participant","username"] "Gnadelwartz"
["result",0,"message","new_chat_member","id"] 123456789
["result",0,"message","new_chat_member","is_bot"] false
["result",0,"message","new_chat_member","first_name"] "Kay"
["result",0,"message","new_chat_member","last_name"] "M"
["result",0,"message","new_chat_member","username"] "Gnadelwartz"

View File

@ -13,21 +13,15 @@ CAPTION: 0
LOCATION: LATITUDE
LOCATION: LONGITUDE
MESSAGE: 0 /_new_chat_member 123456789 Gnadelwartz
MESSAGE: CAPTION
MESSAGE: DICE
MESSAGE: ID 123456789
SERVICE: 0 yes
SERVICE: LEFTMEMBER 123456789
SERVICE: NEWMEMBER 123456789
SERVICE: NEWPHOTO AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANhAAM3SAMAARoE
SERVICE: NEWTITLE new Testgruppe bot only
SERVICE: PINNED 3022
SERVICE: NEWPHOTO
SERVICE: NEWTITLE
NEWMEMBER: FIRST_NAME Kay
NEWMEMBER: ID 123456789
NEWMEMBER: ISBOT false
NEWMEMBER: LAST_NAME M
NEWMEMBER: USERNAME Gnadelwartz
LEFTMEMBER: FIRST_NAME Kay
LEFTMEMBER: ID
LEFTMEMBER: ISBOT false
LEFTMEMBER: LAST_NAME M
PINNED: ID 3022
PINNED: MESSAGE new pinned Message

View File

@ -0,0 +1,30 @@
["ok"] true
["result",0,"update_id"] 123456789
["result",0,"message","message_id"] 123456789
["result",0,"message","from","id"] 123456789
["result",0,"message","from","is_bot"] false
["result",0,"message","from","first_name"] "Kay"
["result",0,"message","from","last_name"] "M"
["result",0,"message","from","username"] "Gnadelwartz"
["result",0,"message","from","language_code"] "de"
["result",0,"message","chat","id"] -123456789
["result",0,"message","chat","title"] "Testgruppe bot only test"
["result",0,"message","chat","type"] "group"
["result",0,"message","chat","all_members_are_administrators"] true
["result",0,"message","date"] 1592372719
["result",0,"message","new_chat_photo",0,"file_id"] "AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANhAAM3SAMAARoE"
["result",0,"message","new_chat_photo",0,"file_unique_id"] "AQADK6S6ki4AAzdIAwAB"
["result",0,"message","new_chat_photo",0,"file_size"] 5939
["result",0,"message","new_chat_photo",0,"width"] 160
["result",0,"message","new_chat_photo",0,"height"] 160
["result",0,"message","new_chat_photo",1,"file_id"] "AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANiAAM4SAMAARoE"
["result",0,"message","new_chat_photo",1,"file_unique_id"] "AQADK6S6ki4AAzhIAwAB"
["result",0,"message","new_chat_photo",1,"file_size"] 14124
["result",0,"message","new_chat_photo",1,"width"] 320
["result",0,"message","new_chat_photo",1,"height"] 320
["result",0,"message","new_chat_photo",2,"file_id"] "AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANjAAM5SAMAARoE"
["result",0,"message","new_chat_photo",2,"file_unique_id"] "AQADK6S6ki4AAzlIAwAB"
["result",0,"message","new_chat_photo",2,"file_size"] 34052
["result",0,"message","new_chat_photo",2,"width"] 640
["result",0,"message","new_chat_photo",2,"height"] 640

View File

@ -0,0 +1,21 @@
USER: FIRST_NAME Kay
USER: ID 123456789
USER: LAST_NAME M
USER: USERNAME Gnadelwartz
CHAT: ALL_ADMIN true
CHAT: FIRST_NAME
CHAT: ID 123456789
CHAT: LAST_NAME
CHAT: TITLE Testgruppe bot only test
CHAT: TYPE group
CHAT: USERNAME
CAPTION: 0
LOCATION: LATITUDE
LOCATION: LONGITUDE
MESSAGE: 0 /_new_chat_photo 123456789 AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANhAAM3SAMAARoE
MESSAGE: CAPTION
MESSAGE: DICE
MESSAGE: ID 123456789
SERVICE: 0 yes
SERVICE: NEWPHOTO AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANhAAM3SAMAARoE
SERVICE: NEWTITLE

View File

@ -0,0 +1,16 @@
["ok"] true
["result",0,"update_id"] 123456789
["result",0,"message","message_id"] 123456789
["result",0,"message","from","id"] 123456789
["result",0,"message","from","is_bot"] false
["result",0,"message","from","first_name"] "Kay"
["result",0,"message","from","last_name"] "M"
["result",0,"message","from","username"] "Gnadelwartz"
["result",0,"message","from","language_code"] "de"
["result",0,"message","chat","id"] -123456789
["result",0,"message","chat","title"] "Testgruppe bot only test"
["result",0,"message","chat","type"] "group"
["result",0,"message","chat","all_members_are_administrators"] true
["result",0,"message","date"] 1592372719
["result",0,"message","new_chat_title"] "new Testgruppe bot only"

View File

@ -0,0 +1,21 @@
USER: FIRST_NAME Kay
USER: ID 123456789
USER: LAST_NAME M
USER: USERNAME Gnadelwartz
CHAT: ALL_ADMIN true
CHAT: FIRST_NAME
CHAT: ID 123456789
CHAT: LAST_NAME
CHAT: TITLE Testgruppe bot only test
CHAT: TYPE group
CHAT: USERNAME
CAPTION: 0
LOCATION: LATITUDE
LOCATION: LONGITUDE
MESSAGE: 0 /_new_chat_title 123456789 new Testgruppe bot only
MESSAGE: CAPTION
MESSAGE: DICE
MESSAGE: ID 123456789
SERVICE: 0 yes
SERVICE: NEWPHOTO
SERVICE: NEWTITLE new Testgruppe bot only

View File

@ -0,0 +1,27 @@
["ok"] true
["result",0,"update_id"] 123456789
["result",0,"message","message_id"] 123456789
["result",0,"message","from","id"] 123456789
["result",0,"message","from","is_bot"] false
["result",0,"message","from","first_name"] "Kay"
["result",0,"message","from","last_name"] "M"
["result",0,"message","from","username"] "Gnadelwartz"
["result",0,"message","from","language_code"] "de"
["result",0,"message","chat","id"] -123456789
["result",0,"message","chat","title"] "Testgruppe bot only test"
["result",0,"message","chat","type"] "group"
["result",0,"message","chat","all_members_are_administrators"] true
["result",0,"message","date"] 1592372719
["result",0,"message","pinned_message","message_id"] 3022
["result",0,"message","pinned_message","from","id"] 796814662
["result",0,"message","pinned_message","from","is_bot"] true
["result",0,"message","pinned_message","from","first_name"] "DealOMat"
["result",0,"message","pinned_message","from","username"] "Deal_O_Mat_bot"
["result",0,"message","pinned_message","chat","id"] -1001220313778
["result",0,"message","pinned_message","chat","title"] "Testgruppe bot only test"
["result",0,"message","pinned_message","chat","type"] "supergroup"
["result",0,"message","pinned_message","date"] 1593121152
["result",0,"message","pinned_message","text"] "new pinned Message"
["result",0,"message","new_chat_title"] "new Testgruppe bot only"

View File

@ -0,0 +1,24 @@
USER: FIRST_NAME Kay
USER: ID 123456789
USER: LAST_NAME M
USER: USERNAME Gnadelwartz
CHAT: ALL_ADMIN true
CHAT: FIRST_NAME
CHAT: ID 123456789
CHAT: LAST_NAME
CHAT: TITLE Testgruppe bot only test
CHAT: TYPE group
CHAT: USERNAME
CAPTION: 0
LOCATION: LATITUDE
LOCATION: LONGITUDE
MESSAGE: 0 /_new_pinned_message 123456789 3022 new pinned Message
MESSAGE: CAPTION
MESSAGE: DICE
MESSAGE: ID 123456789
SERVICE: 0 yes
SERVICE: NEWPHOTO
SERVICE: NEWTITLE new Testgruppe bot only
SERVICE: PINNED 3022
PINNED: ID 3022
PINNED: MESSAGE new pinned Message

View File

@ -1,65 +0,0 @@
["ok"] true
["result",0,"update_id"] 123456789
["result",0,"message","message_id"] 123456789
["result",0,"message","from","id"] 123456789
["result",0,"message","from","is_bot"] false
["result",0,"message","from","first_name"] "Kay"
["result",0,"message","from","last_name"] "M"
["result",0,"message","from","username"] "Gnadelwartz"
["result",0,"message","from","language_code"] "de"
["result",0,"message","chat","id"] -123456789
["result",0,"message","chat","title"] "Testgruppe bot only test"
["result",0,"message","chat","type"] "group"
["result",0,"message","chat","all_members_are_administrators"] true
["result",0,"message","date"] 1592372719
["result",0,"message","left_chat_participant","id"] 123456789
["result",0,"message","left_chat_participant","is_bot"] false
["result",0,"message","left_chat_participant","first_name"] "Kay"
["result",0,"message","left_chat_participant","last_name"] "M"
["result",0,"message","left_chat_participant","username"] "Gnadelwartz"
["result",0,"message","left_chat_member","id"] 123456789
["result",0,"message","left_chat_member","is_bot"] false
["result",0,"message","left_chat_member","first_name"] "Kay"
["result",0,"message","left_chat_member","last_name"] "M"
["result",0,"message","left_chat_member","username"] "Gnadelwartz"
["result",0,"message","new_chat_participant","id"] 123456789
["result",0,"message","new_chat_participant","is_bot"] false
["result",0,"message","new_chat_participant","first_name"] "Kay"
["result",0,"message","new_chat_participant","last_name"] "M"
["result",0,"message","new_chat_participant","username"] "Gnadelwartz"
["result",0,"message","new_chat_member","id"] 123456789
["result",0,"message","new_chat_member","is_bot"] false
["result",0,"message","new_chat_member","first_name"] "Kay"
["result",0,"message","new_chat_member","last_name"] "M"
["result",0,"message","new_chat_member","username"] "Gnadelwartz"
["result",0,"message","new_chat_photo",0,"file_id"] "AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANhAAM3SAMAARoE"
["result",0,"message","new_chat_photo",0,"file_unique_id"] "AQADK6S6ki4AAzdIAwAB"
["result",0,"message","new_chat_photo",0,"file_size"] 5939
["result",0,"message","new_chat_photo",0,"width"] 160
["result",0,"message","new_chat_photo",0,"height"] 160
["result",0,"message","new_chat_photo",1,"file_id"] "AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANiAAM4SAMAARoE"
["result",0,"message","new_chat_photo",1,"file_unique_id"] "AQADK6S6ki4AAzhIAwAB"
["result",0,"message","new_chat_photo",1,"file_size"] 14124
["result",0,"message","new_chat_photo",1,"width"] 320
["result",0,"message","new_chat_photo",1,"height"] 320
["result",0,"message","new_chat_photo",2,"file_id"] "AgACAgIAAxkBAAEBFute6a3vIpB99vim811hxeu2tyQWfwACrKwxG0TMUUtDBH10RqlzGCukupIuAAMBAAMCAANjAAM5SAMAARoE"
["result",0,"message","new_chat_photo",2,"file_unique_id"] "AQADK6S6ki4AAzlIAwAB"
["result",0,"message","new_chat_photo",2,"file_size"] 34052
["result",0,"message","new_chat_photo",2,"width"] 640
["result",0,"message","new_chat_photo",2,"height"] 640
["result",0,"message","pinned_message","message_id"] 3022
["result",0,"message","pinned_message","from","id"] 796814662
["result",0,"message","pinned_message","from","is_bot"] true
["result",0,"message","pinned_message","from","first_name"] "DealOMat"
["result",0,"message","pinned_message","from","username"] "Deal_O_Mat_bot"
["result",0,"message","pinned_message","chat","id"] -1001220313778
["result",0,"message","pinned_message","chat","title"] "Testgruppe bot only test"
["result",0,"message","pinned_message","chat","type"] "supergroup"
["result",0,"message","pinned_message","date"] 1593121152
["result",0,"message","pinned_message","text"] "new pinned Message"
["result",0,"message","new_chat_title"] "new Testgruppe bot only"

View File

@ -10,7 +10,7 @@
# LICENSE: WTFPLv2 http://www.wtfpl.net/txt/copying/
# AUTHOR: KayM (gnadelwartz), kay@rrr.de
#
#### $$VERSION$$ v1.30-0-g3266427
#### $$VERSION$$ v1.52-1-g0dae2db
#===============================================================================
# include common functions and definitions

Some files were not shown because too many files have changed in this diff Show More