aboutsummaryrefslogtreecommitdiff
path: root/shard/lib/cli/cli.ex
diff options
context:
space:
mode:
Diffstat (limited to 'shard/lib/cli/cli.ex')
-rw-r--r--shard/lib/cli/cli.ex109
1 files changed, 73 insertions, 36 deletions
diff --git a/shard/lib/cli/cli.ex b/shard/lib/cli/cli.ex
index bf3a555..3778b2d 100644
--- a/shard/lib/cli/cli.ex
+++ b/shard/lib/cli/cli.ex
@@ -3,22 +3,45 @@ defmodule SCLI do
Small command line interface for the chat application
"""
+ defmodule State do
+ defstruct [:room_pid, :id_pid, :pk]
+ end
+
def run() do
- for {_chid, _manifest, chpid} <- Shard.Manager.list_shards do
+ for {_chid, %SApp.Chat.Manifest{}, chpid} <- Shard.Manager.list_shards do
GenServer.cast(chpid, {:subscribe, self()})
end
- run(nil)
+ pk = case Shard.Keys.list_identities do
+ [pk1|_] -> pk1
+ _ ->
+ IO.puts "Generating a new identity..."
+ Shard.Keys.new_identity
+ end
+
+ run(%State{room_pid: nil, id_pid: nil, pk: pk})
end
- defp run(pid) do
+ defp run(state) do
handle_messages()
- nick = Shard.Identity.get_nickname
- prompt = case pid do
+ id_pid = case state.id_pid do
+ nil -> SApp.Identity.find_proc(state.pk)
+ x -> x
+ end
+ state = put_in(state.id_pid, id_pid)
+
+ nick = case id_pid do
+ nil -> SApp.Identity.default_nick(state.pk)
+ _ ->
+ info = GenServer.call(id_pid, :get_info)
+ info.nick
+ end
+
+ prompt = case state.room_pid do
nil -> "(no channel) #{nick}: "
_ ->
- %SApp.Chat.Manifest{channel: chan} = GenServer.call(pid, :manifest)
+ %SApp.Chat.Manifest{channel: chan} = GenServer.call(state.room_pid, :manifest)
"##{chan} #{nick}: "
end
@@ -28,13 +51,13 @@ defmodule SCLI do
nil
String.slice(str, 0..0) == "/" ->
command = str |> String.slice(1..-1) |> String.split(" ")
- pid2 = handle_command(pid, command)
- run(pid2)
+ state = handle_command(state, command)
+ run(state)
true ->
if str != "" do
- GenServer.cast(pid, {:chat_send, str})
+ GenServer.cast(state.room_pid, {:chat_send, state.pk, str})
end
- run(pid)
+ run(state)
end
end
@@ -50,57 +73,71 @@ defmodule SCLI do
end
end
- defp handle_command(pid, ["connect", ipstr, portstr]) do
+ defp handle_command(state, ["connect", ipstr, portstr]) do
{:ok, ip} = :inet.parse_address (to_charlist ipstr)
{port, _} = Integer.parse portstr
Shard.Manager.add_peer(ip, port)
- pid
+ state
end
- defp handle_command(pid, ["list"]) do
+ defp handle_command(state, ["list"]) do
IO.puts "List of known channels:"
- for {_chid, manifest, _chpid} <- Shard.Manager.list_shards do
- %SApp.Chat.Manifest{channel: chan} = manifest
+ for {_chid, %SApp.Chat.Manifest{channel: chan}, _chpid} <- Shard.Manager.list_shards do
IO.puts "##{chan}"
end
- pid
+ state
end
- defp handle_command(pid, ["hist"]) do
- if pid == nil do
+ defp handle_command(state, ["hist"]) do
+ if state.room_pid == nil do
IO.puts "Not currently on a channel!"
else
- GenServer.call(pid, {:read_history, nil, 25})
- |> Enum.each(fn {{ts, nick, msg}, true} ->
- IO.puts "#{ts |> DateTime.from_unix! |> DateTime.to_iso8601} <#{nick}> #{msg}"
+ GenServer.call(state.room_pid, {:read_history, nil, 25})
+ |> Enum.each(fn {{pk, msgbin, _sign}, true} ->
+ {ts, msg} = SData.term_unbin msgbin
+ nick = case SApp.Identity.find_proc pk do
+ nil ->
+ SApp.Identity.default_nick pk
+ pid ->
+ info = GenServer.call(pid, :get_info)
+ info.nick
+ end
+ IO.puts "#{ts |> DateTime.from_unix! |> DateTime.to_iso8601} <#{nick} #{pk|>binary_part(0, 4)|>Base.encode16|>String.downcase}> #{msg}"
end)
- pid
end
+ state
end
- defp handle_command(_pid, ["join", qchan]) do
- list = for {_chid, manifest, chpid} <- Shard.Manager.list_shards,
- %SApp.Chat.Manifest{channel: chan} = manifest,
- do: {chan, chpid}
- case List.keyfind(list, qchan, 0) do
+ defp handle_command(state, ["join", qchan]) do
+ pid = SApp.Chat.find_proc qchan
+ case pid do
nil ->
- {:ok, pid} = DynamicSupervisor.start_child(Shard.DynamicSupervisor, {SApp.Chat, qchan})
+ {:ok, pid} = Shard.Manifest.start %SApp.Chat.Manifest{channel: qchan}
GenServer.cast(pid, {:subscribe, self()})
- pid
- {_, pid} ->
+ %{state | room_pid: pid}
+ pid ->
IO.puts "Switching to ##{qchan}"
- pid
+ %{state | room_pid: pid}
end
end
- defp handle_command(pid, ["nick", nick]) do
- Shard.Identity.set_nickname nick
- pid
+ defp handle_command(state, ["nick", nick]) do
+ pid = case state.id_pid do
+ nil -> SApp.Identity.find_proc state.pk
+ x -> x
+ end
+ if pid == nil do
+ IO.puts "Sorry, we have a problem with the identity shard"
+ else
+ info = GenServer.call(pid, :get_info)
+ GenServer.call(pid, {:set_info, %{info | nick: nick}})
+ end
+ state
end
- defp handle_command(pid, _cmd) do
+ defp handle_command(state, _cmd) do
IO.puts "Invalid command"
- pid
+ state
end
end