Add tests

This commit is contained in:
Mike Cifelli 2024-05-07 10:10:37 -04:00
parent c5bbc439eb
commit b0872a4fed
Signed by: mike
GPG Key ID: 6B08C6BE47D08E4C
6 changed files with 222 additions and 5 deletions

View File

@ -7,7 +7,7 @@ defmodule ChronoscopeWeb.API.V1.Gemini.ConnectionController do
@default_port 1965 @default_port 1965
@default_path "/" @default_path "/"
@max_host_length 255 @max_parameter_length 255
@gemini Application.compile_env(:chronoscope, :gemini, Gemini) @gemini Application.compile_env(:chronoscope, :gemini, Gemini)
@ -54,10 +54,9 @@ defmodule ChronoscopeWeb.API.V1.Gemini.ConnectionController do
end end
defp connect(host, port, path) do defp connect(host, port, path) do
# TODO - max path length
host host
|> String.slice(0, @max_host_length) |> String.slice(0, @max_parameter_length)
|> @gemini.connect(port, path) |> @gemini.connect(port, String.slice(path, 0, @max_parameter_length))
end end
defp format_response(response) do defp format_response(response) do

View File

@ -0,0 +1,11 @@
defmodule Chronoscope.Gemini.RequestTest do
use Chronoscope.Case, async: true
import Chronoscope.Gemini.Request
describe "Chronoscope.Gemini.Request.create()" do
test "builds a request" do
assert create(%{host: "example.org", port: 9999, path: "/radish"}) == "gemini://example.org:9999/radish\r\n"
end
end
end

View File

@ -0,0 +1,32 @@
defmodule Chronoscope.Gemini.ResponseTest do
use Chronoscope.Case, async: true
import Chronoscope.Gemini.Response
describe "Chronoscope.Gemini.Response.parse()" do
test "handles an empty response" do
assert parse([]) == {:error, "bad response: "}
end
test "handles an bad http response" do
response =
("HTTP/1.1 400 Bad Request\r\nServer: nginx\r\nDate: Tue, 07 May 2024 14:03:56 GMT\r\nContent-Type: text/html\r\nContent-Length: 150\r\nConnection: close\r\n" <>
"\r\n<html>\r\n<head><title>400 Bad Request</title></head>\r\n<body>\r\n<center><h1>400 Bad Request</h1></center>\r\n<hr><center>nginx</center>\r\n</body>\r\n</html>\r\n")
|> String.to_charlist()
assert parse(response) == {:error, "bad response: " <> to_string(response)}
end
test "handles a good response" do
response = "20 text/gemini\r\nHello, world!\r\n" |> String.to_charlist()
assert parse(response) == {:ok, %{body: "Hello, world!\r\n", meta: "text/gemini", status_code: 20}}
end
test "handles a redirect" do
response = "31 gemini://localhost/grapes\r\n" |> String.to_charlist()
assert parse(response) == {:ok, %{body: "", meta: "gemini://localhost/grapes", status_code: 31}}
end
end
end

View File

@ -4,7 +4,7 @@ defmodule Chronoscope.NTS.KeyEstablishmentRequestTest do
import Chronoscope.NTS.KeyEstablishmentRequest import Chronoscope.NTS.KeyEstablishmentRequest
describe "Chronoscope.NTS.KeyEstablishmentRequest.create()" do describe "Chronoscope.NTS.KeyEstablishmentRequest.create()" do
test "builds request" do test "builds a request" do
assert create() == assert create() ==
<<0x80, 0x01, 0x00, 0x02, 0x00, 0x00, 0x80, 0x04, 0x00, 0x04, 0x00, 0x1E, 0x00, 0x0F, 0x80, 0x00, 0x00, 0x00>> <<0x80, 0x01, 0x00, 0x02, 0x00, 0x00, 0x80, 0x04, 0x00, 0x04, 0x00, 0x1E, 0x00, 0x0F, 0x80, 0x00, 0x00, 0x00>>
end end

View File

@ -0,0 +1,163 @@
defmodule ChronoscopeWeb.API.V1.Gemini.ConnectionControllerTest do
use ChronoscopeWeb.ConnCase, async: true
alias Chronoscope.GeminiMock
import Mox
setup :verify_on_exit!
describe "GET /api/v1/gemini/connect" do
test "requires a host name", %{conn: conn} do
response =
conn
|> get(~p"/api/v1/gemini/connect")
|> json_response(400)
assert %{"error" => "missing host"} == response
end
test "uses the given host name", %{conn: conn} do
GeminiMock
|> expect(:connect, fn "localhost", 1965, "/" -> {:ok, %{status: :ok}} end)
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost")
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "truncates the host name", %{conn: conn} do
GeminiMock
|> expect(
:connect,
fn "test.example.com.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456",
1965,
"/" ->
{:ok, %{status: :ok}}
end
)
response =
conn
|> get(
~p"/api/v1/gemini/connect?host=test.example.com.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789"
)
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "uses the given path", %{conn: conn} do
GeminiMock
|> expect(:connect, fn "localhost", 1965, "/test" -> {:ok, %{status: :ok}} end)
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost&path=/test")
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "truncates the path", %{conn: conn} do
GeminiMock
|> expect(
:connect,
fn "localhost",
1965,
"test.example.com.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456" ->
{:ok, %{status: :ok}}
end
)
response =
conn
|> get(
~p"/api/v1/gemini/connect?host=localhost&path=test.example.com.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789.0123456789"
)
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "uses the given port number", %{conn: conn} do
GeminiMock
|> expect(:connect, fn "localhost", 1966, "/" -> {:ok, %{status: :ok}} end)
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost&port=1966")
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "handles an out of range port number", %{conn: conn} do
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost&port=65536")
|> json_response(400)
assert %{"error" => "port out of range"} == response
end
test "handles a negative port number", %{conn: conn} do
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost&port=-1965")
|> json_response(400)
assert %{"error" => "port out of range"} == response
end
test "handles a bad port number", %{conn: conn} do
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost&port=AA60")
|> json_response(400)
assert %{"error" => "invalid port"} == response
end
test "uses both the port and path", %{conn: conn} do
GeminiMock
|> expect(:connect, fn "localhost", 1966, "/radish" -> {:ok, %{status: :ok}} end)
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost&port=1966&path=/radish")
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "returns an empty successful response", %{conn: conn} do
GeminiMock
|> expect(:connect, fn "localhost", 1965, "/" -> {:ok, %{status: :ok}} end)
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost")
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
test "returns a full successful response", %{conn: conn} do
GeminiMock
|> expect(:connect, fn "localhost", 1965, "/" ->
{:ok, %{}}
end)
response =
conn
|> get(~p"/api/v1/gemini/connect?host=localhost")
|> json_response(200)
assert %{"status" => "ok", "response" => %{}} == response
end
end
end

View File

@ -17,6 +17,18 @@ defmodule ChronoscopeWeb.API.V1.NTS.KeyEstablishmentControllerTest do
assert %{"error" => "missing host"} == response assert %{"error" => "missing host"} == response
end end
test "uses the given host name", %{conn: conn} do
NTSMock
|> expect(:key_establishment, fn "localhost", 4460 -> {:ok, %{status: :ok}} end)
response =
conn
|> get(~p"/api/v1/nts/key-establishment?host=localhost")
|> json_response(200)
assert %{"status" => "ok", "response" => %{"cookies" => 0}} == response
end
test "truncates the host name", %{conn: conn} do test "truncates the host name", %{conn: conn} do
NTSMock NTSMock
|> expect( |> expect(