diff --git a/.gitignore b/.gitignore index fc2a76b..0f7d726 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ exe *.exe *.swp tmp +testbot* diff --git a/tg/action.go b/action.go similarity index 100% rename from tg/action.go rename to action.go diff --git a/tg/beh.go b/beh.go similarity index 100% rename from tg/beh.go rename to beh.go diff --git a/tg/bot.go b/bot.go similarity index 100% rename from tg/bot.go rename to bot.go diff --git a/tg/button.go b/button.go similarity index 100% rename from tg/button.go rename to button.go diff --git a/cmd/json/go.mod b/cmd/json/go.mod deleted file mode 100644 index d0fb628..0000000 --- a/cmd/json/go.mod +++ /dev/null @@ -1,13 +0,0 @@ -module jsoned - -go 1.20 - -require ( - github.com/mojosa-software/goscript v0.0.0-20230626091305-86a004b7769c - github.com/mojosa-software/got v0.0.0-20230812125405-bbe076f29abe -) - -require github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1 // indirect - -replace github.com/mojosa-software/got => ./../.. - diff --git a/cmd/json/go.sum b/cmd/json/go.sum deleted file mode 100644 index f0fe3cf..0000000 --- a/cmd/json/go.sum +++ /dev/null @@ -1,6 +0,0 @@ -github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1 h1:wG8n/XJQ07TmjbITcGiUaOtXxdrINDz1b0J1w0SzqDc= -github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1/go.mod h1:A2S0CWkNylc2phvKXWBBdD3K0iGnDBGbzRpISP2zBl8= -github.com/mojosa-software/goscript v0.0.0-20230626091305-86a004b7769c h1:y7RQZz/zJDARRJkn4szD8N2rK6K9NU1vUNPwahtW5zw= -github.com/mojosa-software/goscript v0.0.0-20230626091305-86a004b7769c/go.mod h1:LtBn7lQTgA/TMEL8Y+dGkD6XWHV2gxRPZXiqCZt3HRc= -github.com/mojosa-software/got v0.0.0-20230812125405-bbe076f29abe h1:k42GTLSdShyzNC2BAuIwg6FV3ShwMt/42ezBJWCxVgI= -github.com/mojosa-software/got v0.0.0-20230812125405-bbe076f29abe/go.mod h1:eNRBO08YxKEj75u65VRCDpMGCgZ1sqPN6pi6aFdkfK8= diff --git a/cmd/json/main.go b/cmd/json/main.go deleted file mode 100644 index 2056bd1..0000000 --- a/cmd/json/main.go +++ /dev/null @@ -1,223 +0,0 @@ -package main - -import ( - "encoding/json" - "fmt" - "os" - - //"strings" - - _ "github.com/mojosa-software/goscript/packages" - - "github.com/mojosa-software/goscript/env" - "github.com/mojosa-software/goscript/vm" - "github.com/mojosa-software/got/tg" -) - -type UserData struct { - Counter int -} - -type Code struct { - Code string - Add int -} - -func NewCode(code string) *Code { - return &Code{ - Code: code, - } -} - -func (c *Code) Act(a *tg.Context) { - var err error - fmt.Println("In Act") - e := env.NewEnv() - e.Define("a", a) - e.Define("NotAvailableErr", tg.NotAvailableErr) - e.Define("panic", func(v any) { panic(v) }) - err = e.DefineType("UserData", UserData{}) - if err != nil { - panic(err) - } - - _, err = vm.Execute(e, nil, c.Code) - if err != nil { - panic(err) - } -} - -func main() { - tg.DefineAction("goscript", &Code{}) - - var startScreenButton = tg.NewButton("🏠 To the start screen"). - WithAction(NewCode(` - a.ChangeScreen("start") - `)) - - var ( - incDecKeyboard = tg.NewKeyboard("").Row( - tg.NewButton("+").WithAction(NewCode(` - d = a.V - d.Counter++ - a.Sendf("%d", d.Counter) - `)), - tg.NewButton("-").WithAction(NewCode(` - d = a.V - d.Counter-- - a.Sendf("%d", d.Counter) - `)), - ).Row( - startScreenButton, - ) - - // The navigational keyboard. - navKeyboard = tg.NewKeyboard("").Row( - tg.NewButton("Inc/Dec").WithAction(NewCode(`a.ChangeScreen("inc/dec")`)), - ).Row( - tg.NewButton("Upper case").WithAction(NewCode(`a.ChangeScreen("upper-case")`)), - tg.NewButton("Lower case").WithAction(NewCode(`a.ChangeScreen("lower-case")`)), - ).Row( - tg.NewButton("Send location"). - WithSendLocation(true). - WithAction(NewCode(` - err = nil - if a.U.Message.Location != nil { - l = a.U.Message.Location - err = a.Sendf("Longitude: %f\nLatitude: %f\nHeading: %d", l.Longitude, l.Latitude, l.Heading) - } else { - err = a.Send("Somehow wrong location was sent") - } - if err != nil { - a.Send(err) - } - `)), - ) - - inlineKeyboard = tg.NewKeyboard("").Row( - tg.NewButton("My Telegram"). - WithUrl("https://t.me/surdeus"), - ) - - // The keyboard to return to the start screen. - navToStartKeyboard = tg.NewKeyboard("nav-start").Row( - startScreenButton, - ) - ) - var beh = tg.NewBehaviour(). - // The function will be called every time - // the bot is started. - WithInit(NewCode(` - a.V = new(UserData) - `)). - WithScreens( - tg.NewScreen("start"). - WithText( - "The bot started!"+ - " The bot is supposed to provide basic"+ - " understand of how the API works, so just"+ - " horse around a bit to guess everything out"+ - " by yourself!", - ).WithKeyboard(navKeyboard). - WithIKeyboard(inlineKeyboard), - - tg.NewScreen("inc/dec"). - WithText( - "The screen shows how "+ - "user separated data works "+ - "by saving the counter for each of users "+ - "separately. ", - ). - WithKeyboard(incDecKeyboard). - // The function will be called when reaching the screen. - WithAction(NewCode(` - d = a.V - a.Sendf("Current counter value = %d", d.Counter) - `)), - - tg.NewScreen("upper-case"). - WithText("Type text and the bot will send you the upper case version to you"). - WithKeyboard(navToStartKeyboard). - WithAction(NewCode(` - strings = import("strings") - for { - msg, err = a.ReadTextMessage() - if err == NotAvailableErr { - break - } else if err != nil { - panic(err) - } - - err = a.Sendf("%s", strings.ToUpper(msg)) - if err != nil { - panic(err) - } - } - `)), - - tg.NewScreen("lower-case"). - WithText("Type text and the bot will send you the lower case version"). - WithKeyboard(navToStartKeyboard). - WithAction(NewCode(` - strings = import("strings") - for { - msg, err = a.ReadTextMessage() - if err == NotAvailableErr { - break - } else if err != nil { - panic(err) - } - - err = a.Sendf("%s", strings.ToLower(msg)) - if err != nil { - panic(err) - } - } - `)), - ).WithCommands( - tg.NewCommand("start"). - Desc("start or restart the bot"). - WithAction(NewCode(` - a.ChangeScreen("start") - `)), - tg.NewCommand("hello"). - Desc("sends the 'Hello, World!' message back"). - WithAction(NewCode(` - a.Send("Hello, World!") - `)), - tg.NewCommand("read"). - Desc("reads a string and sends it back"). - WithAction(NewCode(` - a.Send("Type some text:") - msg, err = a.ReadTextMessage() - if err != nil { - return - } - a.Sendf("You typed %q", msg) - `)), - ) - bts, err := json.MarshalIndent(beh, "", "\t") - if err != nil { - panic(err) - } - fmt.Printf("%s", bts) - - jBeh := &tg.Behaviour{} - err = json.Unmarshal(bts, jBeh) - if err != nil { - panic(err) - } - - bot, err := tg.NewBot(os.Getenv("BOT_TOKEN")) - if err != nil { - panic(err) - } - - bot = bot.WithBehaviour(jBeh) - - err = bot.Run() - if err != nil { - panic(err) - } - -} diff --git a/cmd/json/mkfile b/cmd/json/mkfile deleted file mode 100644 index 96a8df2..0000000 --- a/cmd/json/mkfile +++ /dev/null @@ -1,5 +0,0 @@ -all: - go build - -run:V: - ./jsoned diff --git a/cmd/test/main.go b/cmd/test/main.go index 21c98ae..d3bbd44 100644 --- a/cmd/test/main.go +++ b/cmd/test/main.go @@ -6,9 +6,7 @@ import ( "strings" "fmt" - "github.com/mojosa-software/got/tg" - //"math/rand" - //"strconv" + "github.com/reklesio/tg" ) type BotData struct { @@ -57,8 +55,8 @@ func ExtractSessionData(c *tg.Context) *SessionData { } var ( - homeButton = tg.NewButton("Home").Go("/") - backButton = tg.NewButton("Back").Go("-") + homeButton = tg.NewButton("Home").Go("/") + backButton = tg.NewButton("Back").Go("-") backKeyboard = tg.NewKeyboard().Row( backButton, ) @@ -70,9 +68,9 @@ var ( l := c.Message.Location c.Sendf( "Longitude: %f\n"+ - "Latitude: %f\n"+ - "Heading: %d"+ - "", + "Latitude: %f\n"+ + "Heading: %d"+ + "", l.Longitude, l.Latitude, l.Heading, @@ -84,13 +82,13 @@ var ( ) var beh = tg.NewBehaviour(). -WithInitFunc(func(c *tg.Context) { - // The session initialization. - c.Session.Data = &SessionData{} -}).WithRootNode(tg.NewRootNode( + WithInitFunc(func(c *tg.Context) { + // The session initialization. + c.Session.Data = &SessionData{} + }).WithRootNode(tg.NewRootNode( // The "/" widget. tg.RenderFunc(func(c *tg.Context) tg.UI { - return tg.UI { + return tg.UI{ tg.NewMessage(fmt.Sprintf( fmt.Sprint( "Hello, %s!\n", @@ -108,15 +106,15 @@ WithInitFunc(func(c *tg.Context) { tg.NewMessage("Choose your interest").Reply( tg.NewKeyboard().Row( - tg.NewButton("Inc/Dec").Go("/inc-dec"), - ).Row( - tg.NewButton("Mutate messages").Go("/mutate-messages"), - ).Row( - tg.NewButton("Send location").Go("/send-location"), - ).Reply(), + tg.NewButton("Inc/Dec").Go("/inc-dec"), + ).Row( + tg.NewButton("Mutate messages").Go("/mutate-messages"), + ).Row( + tg.NewButton("Send location").Go("/send-location"), + ).Reply(), ), - tg.Func(func(c *tg.Context){ + tg.Func(func(c *tg.Context) { for u := range c.Input() { if u.EditedMessage != nil { c.Sendf2("The new message is `%s`", u.EditedMessage.Text) @@ -188,32 +186,31 @@ WithInitFunc(func(c *tg.Context) { inline, std, onlyInc, onlyDec *tg.Inline ) - d := ExtractSessionData(c) format := "Press the buttons to increment and decrement.\n" + "Current counter value = %d" incBtn := tg.NewButton("+").ActionFunc(func(c *tg.Context) { - d.Counter++ - kbd.Text = fmt.Sprintf(format, d.Counter) - if d.Counter == 5 { - kbd.Inline = onlyDec - } else { - kbd.Inline = std - } - kbd.Update(c) - }) + d.Counter++ + kbd.Text = fmt.Sprintf(format, d.Counter) + if d.Counter == 5 { + kbd.Inline = onlyDec + } else { + kbd.Inline = std + } + kbd.Update(c) + }) decBtn := tg.NewButton("-").ActionFunc(func(c *tg.Context) { - d.Counter-- - kbd.Text = fmt.Sprintf(format, d.Counter) - if d.Counter == -5 { - kbd.Inline = onlyInc - } else { - kbd.Inline = std - } - kbd.Update(c) - //c.Sendf("%d", d.Counter) - }) + d.Counter-- + kbd.Text = fmt.Sprintf(format, d.Counter) + if d.Counter == -5 { + kbd.Inline = onlyInc + } else { + kbd.Inline = std + } + kbd.Update(c) + //c.Sendf("%d", d.Counter) + }) onlyInc = tg.NewKeyboard().Row(incBtn).Inline() onlyDec = tg.NewKeyboard().Row(decBtn).Inline() @@ -227,7 +224,6 @@ WithInitFunc(func(c *tg.Context) { inline = std } - kbd = tg.NewMessage( fmt.Sprintf(format, d.Counter), ).Inline(inline) @@ -243,11 +239,11 @@ WithInitFunc(func(c *tg.Context) { tg.NewNode( "send-location", tg.RenderFunc(func(c *tg.Context) tg.UI { - return tg.UI { + return tg.UI{ tg.NewMessage( "Press the button to display your counter", ).Inline( - tg.NewKeyboard().Row( + tg.NewKeyboard().Row( tg.NewButton( "Check", ).WithData( @@ -268,13 +264,13 @@ WithInitFunc(func(c *tg.Context) { }), ), )).WithRoot(tg.NewCommandCompo(). -WithUsage(tg.Func(func(c *tg.Context){ - c.Sendf("There is no such command %q", c.Message.Command()) -})).WithPreStart(tg.Func(func(c *tg.Context){ + WithUsage(tg.Func(func(c *tg.Context) { + c.Sendf("There is no such command %q", c.Message.Command()) + })).WithPreStart(tg.Func(func(c *tg.Context) { c.Sendf("Please, use /start ") })).WithCommands( tg.NewCommand("info", "info desc"). - ActionFunc(func(c *tg.Context){ + ActionFunc(func(c *tg.Context) { c.SendfHTML(`cockcock die`) }), tg.NewCommand( @@ -287,7 +283,7 @@ WithUsage(tg.Func(func(c *tg.Context){ }), tg.NewCommand("read", "reads a string and sends it back"). WithWidget( - tg.Func(func(c *tg.Context){ + tg.Func(func(c *tg.Context) { str := c.ReadString("Type a string and I will send it back") c.Sendf2("You typed `%s`", str) }), @@ -303,14 +299,14 @@ WithUsage(tg.Func(func(c *tg.Context){ c.Sendf("My name is %q", bd.Name) })), tg.NewCommand("dynamic", "check of the dynamic work"). - WithWidget(tg.Func(func(c *tg.Context){ + WithWidget(tg.Func(func(c *tg.Context) { })), tg.NewCommand("history", "print go history"). - WithAction(tg.Func(func(c *tg.Context){ + WithAction(tg.Func(func(c *tg.Context) { c.Sendf("%q", c.History()) })), tg.NewCommand("washington", "send location of the Washington"). - WithAction(tg.Func(func(c *tg.Context){ + WithAction(tg.Func(func(c *tg.Context) { c.Sendf("Washington location") c.Send( tg.NewMessage("").Location( @@ -319,9 +315,10 @@ WithUsage(tg.Func(func(c *tg.Context){ ) })), tg.NewCommand("invoice", "invoice check"). - WithAction(tg.Func(func(c *tg.Context){ + WithAction(tg.Func(func(c *tg.Context) { })), - )) +)) + func main() { log.Println(beh.Screens) token := os.Getenv("BOT_TOKEN") diff --git a/tg/command.go b/command.go similarity index 100% rename from tg/command.go rename to command.go diff --git a/tg/context.go b/context.go similarity index 100% rename from tg/context.go rename to context.go diff --git a/tg/errors.go b/errors.go similarity index 100% rename from tg/errors.go rename to errors.go diff --git a/tg/file.go b/file.go similarity index 100% rename from tg/file.go rename to file.go diff --git a/tg/filter.go b/filter.go similarity index 100% rename from tg/filter.go rename to filter.go diff --git a/go.mod b/go.mod index 6d26af9..798d13e 100644 --- a/go.mod +++ b/go.mod @@ -1,8 +1,5 @@ -module github.com/mojosa-software/got +module github.com/reklesio/tg go 1.20 -require ( - github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1 // indirect - github.com/mojosa-software/godat v0.0.0-20230711170316-a335bad31575 // indirect -) +require github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1 diff --git a/go.sum b/go.sum index 087e333..db8e45c 100644 --- a/go.sum +++ b/go.sum @@ -1,4 +1,2 @@ github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1 h1:wG8n/XJQ07TmjbITcGiUaOtXxdrINDz1b0J1w0SzqDc= github.com/go-telegram-bot-api/telegram-bot-api/v5 v5.5.1/go.mod h1:A2S0CWkNylc2phvKXWBBdD3K0iGnDBGbzRpISP2zBl8= -github.com/mojosa-software/godat v0.0.0-20230711170316-a335bad31575 h1:wtaYzLbEND7JSY7L+huFU4IDT4nbuDolKRfnQ1d6KTc= -github.com/mojosa-software/godat v0.0.0-20230711170316-a335bad31575/go.mod h1:E6ohOj8PpUJBQOSRdrLygjoO+Te6yfeox3ZtaItsHUg= diff --git a/tg/inline.go b/inline.go similarity index 100% rename from tg/inline.go rename to inline.go diff --git a/tg/invoice.go b/invoice.go similarity index 100% rename from tg/invoice.go rename to invoice.go diff --git a/tg/json.go b/json.go similarity index 100% rename from tg/json.go rename to json.go diff --git a/tg/keyboard.go b/keyboard.go similarity index 100% rename from tg/keyboard.go rename to keyboard.go diff --git a/license.txt b/license.txt index 5b0a270..e943bcb 100644 --- a/license.txt +++ b/license.txt @@ -1,6 +1,6 @@ MIT License -Copyright (c) 2023 Andrey Parhomenko +Copyright (c) 2023 surdeus Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/tg/location.go b/location.go similarity index 100% rename from tg/location.go rename to location.go diff --git a/media/bot.png b/media/bot.png deleted file mode 100644 index 10968bd..0000000 Binary files a/media/bot.png and /dev/null differ diff --git a/media/gopher.png b/media/gopher.png new file mode 100644 index 0000000..b440676 Binary files /dev/null and b/media/gopher.png differ diff --git a/tg/message.go b/message.go similarity index 100% rename from tg/message.go rename to message.go diff --git a/mkfile b/mkfile deleted file mode 100644 index 4c32c16..0000000 --- a/mkfile +++ /dev/null @@ -1,11 +0,0 @@ -all: build - -run-air:V: - air -c airfile - -build:V: - go build -o exe/ ./cmd/... - -clean: - rm -rf exe/* - diff --git a/tg/page.go b/page.go similarity index 100% rename from tg/page.go rename to page.go diff --git a/tg/poll.go b/poll.go similarity index 68% rename from tg/poll.go rename to poll.go index c7a6336..57ba555 100644 --- a/tg/poll.go +++ b/poll.go @@ -1,5 +1,6 @@ package tg +// Still to be implemented. type Poll struct { } diff --git a/readme.md b/readme.md index f4965ef..773fdf5 100644 --- a/readme.md +++ b/readme.md @@ -1,7 +1,14 @@ -# got v0.3.2 +# TeleGopher -Go Telegram. +![Put here TeleGopher image, please]() -The module implements behaviour based interactions with user, -screens with buttons, etc. +The high level API to implement complicated +behaviour based Telegram bots in W3 manner +with URLs, screens, UIs and so on. +## Tasks + +- [] Tech + - [] Added easy way to work with payments + - [] Make more documentation including the Go embedded one +- [] Do some examples to show how it works diff --git a/tg/reply.go b/reply.go similarity index 100% rename from tg/reply.go rename to reply.go diff --git a/tg/screen.go b/screen.go similarity index 100% rename from tg/screen.go rename to screen.go diff --git a/tg/send.go b/send.go similarity index 100% rename from tg/send.go rename to send.go diff --git a/tg/server.go b/server.go similarity index 100% rename from tg/server.go rename to server.go diff --git a/tg/session.go b/session.go similarity index 100% rename from tg/session.go rename to session.go diff --git a/taskfile.yml b/taskfile.yml new file mode 100644 index 0000000..a86fbd8 --- /dev/null +++ b/taskfile.yml @@ -0,0 +1,6 @@ +version: 3 + +tasks: + build: + cmds: + - go build -o testbot ./cmd/test/ diff --git a/tg/encoding.go b/tg/encoding.go deleted file mode 100644 index ab48df1..0000000 --- a/tg/encoding.go +++ /dev/null @@ -1,37 +0,0 @@ -package tg - -import ( - "reflect" -) - -var ( - actionMapByReflect = make(map[reflect.Type]string) - actionMapByTypeName = make(map[string]reflect.Type) - Init func() -) - -func initEncoding() { - actions := map[string]Action{ - "action-func": ActionFunc(nil), - "screen-change": ScreenGo{}, - } - for k, action := range actions { - DefineAction(k, action) - } -} - -// Define interface to make it marshalable to JSON etc. -// Like in GOB. Must be done both on client and server -// if one is provided. -func DefineAction(typeName string, a Action) error { - t := reflect.TypeOf(a) - - actionMapByReflect[t] = typeName - actionMapByTypeName[typeName] = t - - return nil -} - -/*func DefineGroupAction(typ string, a GroupAction) error { - return nil -}*/ diff --git a/tg/group.go b/tg/group.go deleted file mode 100644 index a1dbcb3..0000000 --- a/tg/group.go +++ /dev/null @@ -1,2 +0,0 @@ -package tg - diff --git a/tg/main.go b/tg/main.go deleted file mode 100644 index 261c852..0000000 --- a/tg/main.go +++ /dev/null @@ -1,5 +0,0 @@ -package tg - -func init() { - initEncoding() -} diff --git a/tg/make.go b/tg/make.go deleted file mode 100644 index a1dbcb3..0000000 --- a/tg/make.go +++ /dev/null @@ -1,2 +0,0 @@ -package tg - diff --git a/tg/private.go b/tg/private.go deleted file mode 100644 index a1dbcb3..0000000 --- a/tg/private.go +++ /dev/null @@ -1,2 +0,0 @@ -package tg - diff --git a/tg/read.go b/tg/read.go deleted file mode 100644 index 77cfbc1..0000000 --- a/tg/read.go +++ /dev/null @@ -1,3 +0,0 @@ -package tg - - diff --git a/tg/compo.go b/ui.go similarity index 100% rename from tg/compo.go rename to ui.go diff --git a/tg/update.go b/update.go similarity index 100% rename from tg/update.go rename to update.go diff --git a/tg/widget.go b/widget.go similarity index 100% rename from tg/widget.go rename to widget.go