augustjune on master
Update log4cats-core, log4cats-… (compare)
augustjune on v0.6.0
augustjune on github-actions-release
augustjune on bump-cats-core-laws-version
augustjune on sbt-github-actions
augustjune on dependencies-update
augustjune on master
Updated code examples (#380) (compare)
augustjune on dependencies-update
removed sbt assembly dependency updated examples (compare)
def run(args: List[String]): IO[ExitCode] =
Stream
.resource(TelegramClient.global[IO](token))
.flatMap { implicit client =>
Stream.eval(Store.make[IO]).flatMap { store =>
Bot
.fromStream(Bot.polling[IO].updates.through(answerCallbacks(store)))
.follow(createButton, trigger(store)(reaction))
}
}
.compile
.drain
.as(ExitCode.Success)
def createButton[F[_]: TelegramClient]: Scenario[F, Unit] =
for {
msg <- Scenario.expect(command("callback"))
_ <- Scenario.eval(
msg.chat.send(content = "pretty message", keyboard = setupMarkupWithSungleCallbackButton("button", "xx"))
)
} yield ()
def trigger[F[_]: TelegramClient](lastCallback: Store[F])(main: Scenario[F, Unit]): Scenario[F, Unit] =
Scenario.eval(lastCallback.check("xx")).ifM(main, Scenario.done)
def reaction[F[_]: TelegramClient]: Scenario[F, Unit] = ???
def answerCallbacks[F[_]: Monad: TelegramClient](lastCallback: Store[F]): Pipe[F, Update, Update] =
_.evalTap {
case CallbackButtonSelected(_, query) =>
query.data match {
case Some(cbd) => lastCallback.save(cbd) *> query.finish
case _ => lastCallback.clean
}
case _ => lastCallback.clean
}
def setupMarkupWithSungleCallbackButton(text: String, data: String): Keyboard.Inline = {
val inlineBtn = InlineKeyboardButton.callbackData(text = text, cbd = data)
val inlineKeyboardMarkUp = InlineKeyboardMarkup.singleButton(inlineBtn)
Keyboard.Inline(inlineKeyboardMarkUp)
}
trait Store[F[_]] {
def save(id: String): F[Unit]
def clean: F[Unit]
def check(id: String): F[Boolean]
}
object Store {
def make[F[_]: Concurrent]: F[Store[F]] =
Ref[F].of(none[String]).map { ref =>
new Store[F] {
def save(id: String): F[Unit] = ref.set(id.some)
def clean: F[Unit] = ref.set(none)
def check(id: String): F[Boolean] = ref.get.map(_.contains(id))
}
}
}
import canoe.api._
import canoe.api.models.Keyboard
import canoe.models.{CallbackButtonSelected, InlineKeyboardButton, InlineKeyboardMarkup, Update}
import canoe.syntax._
import cats.Monad
import cats.effect.concurrent.Ref
import cats.effect.{Concurrent, ExitCode, IO, IOApp}
import cats.implicits._
import fs2.{Pipe, Stream}
0.5.0
?
Scenario
though
InlineKeyboardButton
constructor methods don't expose this param, my bad
InlineKeyboardButton
companion object with some description