From 4998e0ac5b9e477e82fe194a3dd95d95610a188d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Moritz=20B=C3=B6hme?= Date: Sat, 3 Aug 2024 08:51:48 +0200 Subject: [PATCH] feat: add TodoServer --- todo_list.ex | 78 ++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 76 insertions(+), 2 deletions(-) diff --git a/todo_list.ex b/todo_list.ex index 47abb7e..3f2c794 100644 --- a/todo_list.ex +++ b/todo_list.ex @@ -1,3 +1,77 @@ +defmodule TodoServer do + def start(entries \\ []) do + spawn(fn -> loop(TodoList.new(entries)) end) + end + + def from_list(todo_list) do + spawn(fn -> loop(todo_list) end) + end + + defp loop(todo_list) do + new_todo_list = + receive do + message -> + process_message(todo_list, message) + after + 1000 -> todo_list + end + + loop(new_todo_list) + end + + defp process_message(todo_list, {:add, entry}) do + TodoList.add(todo_list, entry) + end + + defp process_message(todo_list, {:entries, sender, date}) do + entries = TodoList.entries(todo_list, date) + + send(sender, {:entries, entries}) + + todo_list + end + + defp process_message(todo_list, {:update, id, update_fun}) do + TodoList.update(todo_list, id, update_fun) + end + + defp process_message(todo_list, {:delete, id}) do + TodoList.delete(todo_list, id) + end + + defp process_message(todo_list, invalid_message) do + IO.puts("Invalid message: #{IO.inspect(invalid_message)}") + + todo_list + end + + def add(pid, entry) do + send(pid, {:add, entry}) + nil + end + + def entries(pid, date) do + send(pid, {:entries, self(), date}) + + receive do + {:entries, value} -> + {:ok, value} + after + 1000 -> {:error} + end + end + + def update(pid, id, update_fun) do + send(pid, {:update, id, update_fun}) + nil + end + + def delete(pid, id) do + send(pid, {:delete, id}) + nil + end +end + defmodule TodoList do defstruct entries: %{}, next_id: 1 @@ -16,8 +90,8 @@ defmodule TodoList do %__MODULE__{todo_list | entries: new_entries, next_id: next_id + 1} end - def entries(%__MODULE__{entries: entries}, date) do - entries + def entries(%__MODULE__{} = todo_list, date) do + todo_list.entries |> Map.filter(fn {_, entry} -> entry.date == date end) |> Map.values() end