Static blog with front page summary
Goal: have a personal blog, and try out another point in the 'modular app design with elixir' space. Designing OTP systems with elixir had some interesting ideas.
This commit is contained in:
@@ -0,0 +1,123 @@
|
||||
defmodule Blogex.RouterTest do
|
||||
use ExUnit.Case
|
||||
use Plug.Test
|
||||
|
||||
import Blogex.Test.PostBuilder
|
||||
alias Blogex.Test.FakeBlog
|
||||
|
||||
setup do
|
||||
posts = [
|
||||
build(id: "first-post", title: "First", tags: ["elixir"], date: ~D[2026-03-10]),
|
||||
build(id: "second-post", title: "Second", tags: ["otp"], date: ~D[2026-02-01]),
|
||||
build(id: "draft", published: false, date: ~D[2026-03-12])
|
||||
]
|
||||
|
||||
{:ok, _} = FakeBlog.start(posts,
|
||||
blog_id: :test,
|
||||
title: "Test Blog",
|
||||
description: "Test",
|
||||
base_path: "/blog/test"
|
||||
)
|
||||
|
||||
:ok
|
||||
end
|
||||
|
||||
defp call(method, path) do
|
||||
conn(method, path)
|
||||
|> Blogex.Router.call(Blogex.Router.init(blog: FakeBlog))
|
||||
end
|
||||
|
||||
describe "GET /feed.xml" do
|
||||
test "returns RSS XML" do
|
||||
conn = call(:get, "/feed.xml")
|
||||
|
||||
assert conn.status == 200
|
||||
assert get_content_type(conn) =~ "application/rss+xml"
|
||||
assert conn.resp_body =~ "<rss version=\"2.0\""
|
||||
end
|
||||
|
||||
test "includes published posts" do
|
||||
conn = call(:get, "/feed.xml")
|
||||
|
||||
assert conn.resp_body =~ "first-post"
|
||||
refute conn.resp_body =~ "draft"
|
||||
end
|
||||
end
|
||||
|
||||
describe "GET /atom.xml" do
|
||||
test "returns Atom XML" do
|
||||
conn = call(:get, "/atom.xml")
|
||||
|
||||
assert conn.status == 200
|
||||
assert get_content_type(conn) =~ "application/atom+xml"
|
||||
assert conn.resp_body =~ "<feed xmlns="
|
||||
end
|
||||
end
|
||||
|
||||
describe "GET /:slug" do
|
||||
test "returns post as JSON" do
|
||||
conn = call(:get, "/first-post")
|
||||
|
||||
assert conn.status == 200
|
||||
body = Jason.decode!(conn.resp_body)
|
||||
assert body["id"] == "first-post"
|
||||
assert body["title"] == "First"
|
||||
end
|
||||
|
||||
test "returns 404 for unknown slug" do
|
||||
conn = call(:get, "/nonexistent")
|
||||
|
||||
assert conn.status == 404
|
||||
end
|
||||
|
||||
test "returns 404 for draft post" do
|
||||
conn = call(:get, "/draft")
|
||||
|
||||
assert conn.status == 404
|
||||
end
|
||||
end
|
||||
|
||||
describe "GET /tag/:tag" do
|
||||
test "returns posts matching tag" do
|
||||
conn = call(:get, "/tag/elixir")
|
||||
|
||||
assert conn.status == 200
|
||||
body = Jason.decode!(conn.resp_body)
|
||||
assert body["tag"] == "elixir"
|
||||
assert length(body["posts"]) == 1
|
||||
assert hd(body["posts"])["id"] == "first-post"
|
||||
end
|
||||
|
||||
test "returns empty list for unknown tag" do
|
||||
conn = call(:get, "/tag/unknown")
|
||||
|
||||
body = Jason.decode!(conn.resp_body)
|
||||
assert body["posts"] == []
|
||||
end
|
||||
end
|
||||
|
||||
describe "GET /" do
|
||||
test "returns paginated post list" do
|
||||
conn = call(:get, "/")
|
||||
|
||||
assert conn.status == 200
|
||||
body = Jason.decode!(conn.resp_body)
|
||||
assert is_list(body["posts"])
|
||||
assert body["total_entries"] == 2
|
||||
end
|
||||
|
||||
test "excludes draft posts from listing" do
|
||||
conn = call(:get, "/")
|
||||
|
||||
body = Jason.decode!(conn.resp_body)
|
||||
ids = Enum.map(body["posts"], & &1["id"])
|
||||
refute "draft" in ids
|
||||
end
|
||||
end
|
||||
|
||||
defp get_content_type(conn) do
|
||||
conn
|
||||
|> Plug.Conn.get_resp_header("content-type")
|
||||
|> List.first("")
|
||||
end
|
||||
end
|
||||
Reference in New Issue
Block a user