Adds focused tests across multiple modules to push toward the 87% threshold: - CoreComponents: pagination/1 (multi-page, ellipsis, params), list/1 (slot rendering), and signal_badge/1 across all RSSI bands. - ApiDocs/GraphQLDocs controllers: bypass-the-router pattern so the "scope-with-organization" branches are actually exercised (the public routes are unscoped, so the org branch is unreachable via get/2). - Mix.Tasks.Unused: text + JSON output, --only / --skip filters. - Mix.Tasks.JobCleanupTask: prod path with phoenix snmp enabled vs disabled (uses :job_cleanup_settle_ms = 0 to avoid the 1s sleep). - Member resolver: success path for remove/update_role on non-owner membership, and the changeset-error branch for an invalid role. - Check resolver: unauthenticated fallback clauses for list / get / create / update / delete. - RfLinks: nil-signal sort ordering, :unknown classification for nil/nil signal+snr, :degraded filter, capacity_utilization edge cases (max_rate 0/missing, both rates nil). - StatusHelpers: status_emoji + title_with_status across green / red branches (warning is unreachable given the active-alerts query). - ApiTokens: spawn_async_update/2 path with env != :test. - ImpactAnalysis: to_json/1 across nil and populated levels. - Maintenance: query helpers (default-arity wrappers, active range) and Show LiveView delete event redirecting to /maintenance. - Coverage map: probe_point event handler. - InvitationQuery: default-arity pending/1.
64 lines
2 KiB
Elixir
64 lines
2 KiB
Elixir
defmodule ToweropsWeb.ApiDocsControllerTest do
|
|
use ToweropsWeb.ConnCase, async: true
|
|
|
|
import Towerops.AccountsFixtures
|
|
import Towerops.OrganizationsFixtures
|
|
|
|
alias Towerops.Accounts.Scope
|
|
alias Towerops.ApiTokens
|
|
|
|
describe "GET /docs/api" do
|
|
test "renders index without login", %{conn: conn} do
|
|
conn = get(conn, "/docs/api")
|
|
assert html_response(conn, 200) =~ "API"
|
|
end
|
|
|
|
test "renders index for logged-in user without API tokens", %{conn: conn} do
|
|
user = user_fixture()
|
|
org = organization_fixture(user.id)
|
|
|
|
# /docs/api is unscoped (no org slug in path), so the browser pipeline
|
|
# never populates `scope.organization`. Bypass the router and dispatch
|
|
# the controller action directly with a scope that has organization set.
|
|
scope = user |> Scope.for_user() |> Scope.put_organization(org)
|
|
|
|
conn =
|
|
conn
|
|
|> Phoenix.ConnTest.bypass_through(ToweropsWeb.Router, [:browser])
|
|
|> get("/")
|
|
|> Plug.Conn.assign(:current_scope, scope)
|
|
|> Phoenix.Controller.put_view(ToweropsWeb.ApiDocsHTML)
|
|
|> ToweropsWeb.ApiDocsController.index(%{})
|
|
|
|
body = html_response(conn, 200)
|
|
assert body =~ "API"
|
|
assert body =~ "create one in your organization settings"
|
|
end
|
|
|
|
test "renders index for logged-in user with API tokens", %{conn: conn} do
|
|
user = user_fixture()
|
|
org = organization_fixture(user.id)
|
|
|
|
{:ok, {_token, _raw}} =
|
|
ApiTokens.create_api_token(%{
|
|
organization_id: org.id,
|
|
user_id: user.id,
|
|
name: "Test Token"
|
|
})
|
|
|
|
scope = user |> Scope.for_user() |> Scope.put_organization(org)
|
|
|
|
conn =
|
|
conn
|
|
|> Phoenix.ConnTest.bypass_through(ToweropsWeb.Router, [:browser])
|
|
|> get("/")
|
|
|> Plug.Conn.assign(:current_scope, scope)
|
|
|> Phoenix.Controller.put_view(ToweropsWeb.ApiDocsHTML)
|
|
|> ToweropsWeb.ApiDocsController.index(%{})
|
|
|
|
body = html_response(conn, 200)
|
|
assert body =~ "API"
|
|
assert body =~ "use: Test Token"
|
|
end
|
|
end
|
|
end
|