From 20a0b45954cf7819cd9d51c401db06be0f47666b Mon Sep 17 00:00:00 2001 From: Amogh Lele Date: Sat, 7 May 2022 00:04:59 +0530 Subject: [PATCH] feat(pastes): add REST routes to view and create pastes Signed-off-by: Amogh Lele --- lib/ketbin/pastes/paste.ex | 1 + .../controllers/api/paste_controller.ex | 46 +++++++++++++++++++ lib/ketbin_web/router.ex | 8 ++++ lib/ketbin_web/views/api/paste_view.ex | 18 ++++++++ 4 files changed, 73 insertions(+) create mode 100644 lib/ketbin_web/controllers/api/paste_controller.ex create mode 100644 lib/ketbin_web/views/api/paste_view.ex diff --git a/lib/ketbin/pastes/paste.ex b/lib/ketbin/pastes/paste.ex index b0e36bf..a54b552 100644 --- a/lib/ketbin/pastes/paste.ex +++ b/lib/ketbin/pastes/paste.ex @@ -1,6 +1,7 @@ defmodule Ketbin.Pastes.Paste do use Ecto.Schema import Ecto.Changeset + @derive {Jason.Encoder, only: [:content, :is_url, :belongs_to]} @primary_key {:id, :string, autogenerate: false} @derive {Phoenix.Param, key: :id} diff --git a/lib/ketbin_web/controllers/api/paste_controller.ex b/lib/ketbin_web/controllers/api/paste_controller.ex new file mode 100644 index 0000000..1bd8c41 --- /dev/null +++ b/lib/ketbin_web/controllers/api/paste_controller.ex @@ -0,0 +1,46 @@ +defmodule KetbinWeb.Api.PasteController do + use KetbinWeb, :controller + + alias Ketbin.Pastes + alias Ketbin.Pastes.Paste + alias Ketbin.Pastes.Utils + + def show(conn, %{"id" => id}) do + [head | _tail] = String.split(id, ".") + + # fetch paste from db + paste = Pastes.get_paste!(head) + render(conn, "paste.json", paste: paste) + end + + def create(%{assigns: %{current_user: current_user}} = conn, %{"paste" => paste_params}) do + # generate phonetic key + id = Utils.generate_key() + + # check if content is a url + is_url = + Map.get(paste_params, "content") + |> Utils.is_url?() + + # put id and is_url values into changeset + paste_params = + Map.put(paste_params, "id", id) + |> Map.put("is_url", is_url) + |> Map.put("belongs_to", current_user && current_user.id) + + # attempt to create a paste + case Pastes.create_paste(paste_params) do + # all good + {:ok, paste} -> + conn + |> put_status(:created) + |> render("paste.json", paste: paste) + + # something went wrong, bail + {:error, %Ecto.Changeset{} = _changeset} -> + conn + |> put_status(:internal_server_error) + |> render("error.json") + end + end +end diff --git a/lib/ketbin_web/router.ex b/lib/ketbin_web/router.ex index 647fac1..7ed284d 100644 --- a/lib/ketbin_web/router.ex +++ b/lib/ketbin_web/router.ex @@ -14,6 +14,8 @@ defmodule KetbinWeb.Router do pipeline :api do plug :accepts, ["json"] + plug :fetch_session + plug :fetch_current_user end scope "/", KetbinWeb do @@ -42,6 +44,12 @@ defmodule KetbinWeb.Router do put "/:id", PageController, :update end + scope "/api", KetbinWeb.Api, as: :api do + pipe_through :api + + resources "/paste", PasteController, only: [:show, :index, :create] + end + # Other scopes may use custom stacks. # scope "/api", KetbinWeb do # pipe_through :api diff --git a/lib/ketbin_web/views/api/paste_view.ex b/lib/ketbin_web/views/api/paste_view.ex new file mode 100644 index 0000000..4de264f --- /dev/null +++ b/lib/ketbin_web/views/api/paste_view.ex @@ -0,0 +1,18 @@ +defmodule KetbinWeb.Api.PasteView do + use KetbinWeb, :view + + def render("paste.json", %{paste: paste}) do + %{ + id: paste.id, + content: paste.content, + is_url: paste.is_url + } + end + + def render("error.json", _assigns) do + %{ + success: false, + msg: "Something went wrong" + } + end +end