You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
118 lines
3.5 KiB
118 lines
3.5 KiB
module Server
|
|
|
|
using Markdown
|
|
|
|
using Mux
|
|
|
|
using ..Markov
|
|
using ..Bot
|
|
|
|
# Middlewares
|
|
|
|
function extract_chatid(app, req)
|
|
@debug "Looking for chan ID" req
|
|
req[:params][:chatid] = req[:message][:chat][:id]
|
|
app(req)
|
|
end
|
|
|
|
function ignore_if_not_allowed(app, req)
|
|
|
|
if req[:params][:chatid] == Bot.CHAT_ID
|
|
return app(req)
|
|
else
|
|
@debug "Ignoring request"
|
|
return nothing
|
|
end
|
|
end
|
|
|
|
function extract_command(command, parameters...; botname="")
|
|
if command[1] == '/'
|
|
command = command[2:end]
|
|
end
|
|
function middleware(app, req)
|
|
if !(:entities in keys(req[:message]))
|
|
return app(req)
|
|
end
|
|
@debug "Looking for commands"
|
|
command_entities_id = findall(e->e[:type] == "bot_command", req[:message][:entities])
|
|
@debug "There are commands" command_entities_id
|
|
@debug "Looking for commands names"
|
|
commands = map(
|
|
e->(
|
|
req[:message][:text][
|
|
(req[:message][:entities][e][:offset]+1):(req[:message][:entities][e][:offset]+req[:message][:entities][e][:length])
|
|
], req[:message][:entities][e]),
|
|
command_entities_id
|
|
)
|
|
@debug "Commands found" commands
|
|
first_command_id = findfirst(
|
|
c->c[1] == ("/" * command) || c[1] .== ("/" * command * "@" * botname),
|
|
commands
|
|
)
|
|
if isnothing(first_command_id)
|
|
return app(req)
|
|
end
|
|
parameters_values = []
|
|
command_offset = commands[first_command_id][2][:offset]
|
|
command_length = commands[first_command_id][2][:length]
|
|
end_of_text = split(req[:message][:text][command_offset+command_length+1:end])
|
|
req[:command] = Dict()
|
|
req[:command][:name] = command
|
|
req[:command][:parameters] = Dict{Symbol, Union{Nothing, String}}(p=>nothing for p in parameters)
|
|
for (i,param) in enumerate(parameters)
|
|
if i > length(end_of_text)
|
|
break
|
|
end
|
|
@debug "Parameter attributed" param end_of_text[i]
|
|
req[:command][:parameters][param] = end_of_text[i]
|
|
end
|
|
app(req)
|
|
end
|
|
end
|
|
|
|
function branch_to_callback(calback, command)
|
|
branching_f(req) = if :command in keys(req)
|
|
@debug "branching" req[:command][:name] command
|
|
req[:command][:name] == command
|
|
else
|
|
@debug "branching" req
|
|
false
|
|
end
|
|
branch(branching_f, calback)
|
|
end
|
|
|
|
command(command, callback, parameters...; botname="") = stack(extract_command(command, parameters...; botname=botname), branch_to_callback(callback, command))
|
|
|
|
|
|
# Endpoints
|
|
|
|
function show_help(req)
|
|
"""
|
|
Hi ! I'm the Markovian bot. Here is what I can do :
|
|
* /help Prints this list of commands !
|
|
* /talk [username [word]] Creates a Markov chain for the given `user` (chosen at random if not set) containing `word` (chosen at random if not set)
|
|
* /list Lists registered usernames.
|
|
|
|
🐺
|
|
"""
|
|
end
|
|
|
|
function list_usernames(req)
|
|
users = join(" * " .* sort(Markov.list_usernames()), "\n")
|
|
"""
|
|
Here are the users I know of :
|
|
""" * users
|
|
end
|
|
|
|
function talk(req)
|
|
user = req[:command][:parameters][:user]
|
|
word = req[:command][:parameters][:word]
|
|
@debug "Time to talk" user word
|
|
Markov.make_sentence(user, word)
|
|
end
|
|
|
|
authentication() = stack(extract_chatid, ignore_if_not_allowed)
|
|
commands() = stack(command("help", show_help), command("list", list_usernames), command("talk", talk, :user, :word))
|
|
application() = mux(stack(authentication(), commands()), _->nothing)
|
|
|
|
end
|
|
|