Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add tests for Kaffy.ResourceQuery #310

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
64 changes: 34 additions & 30 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,30 +2,30 @@ name: Kaffy CI (Elixir)

on:
push:
branches: [ master ]
branches: [master]
pull_request:
branches: [ master ]
branches: [master]

jobs:
test:
name: Test ${{matrix.otp}} / Elixir ${{matrix.elixir}}
runs-on: ubuntu-20.04
strategy:
matrix:
otp: ['22', '23', '24', '25']
elixir: ['1.12.3', '1.13.4', '1.14.5', '1.15.5']
otp: ["22", "23", "24", "25"]
elixir: ["1.12.3", "1.13.4", "1.14.5", "1.15.5"]
# Exclude invalid combinations of Elixir and OTP
exclude:
- otp: '22'
elixir: '1.14.5'
- otp: '22'
elixir: '1.15.5'
- otp: '23'
elixir: '1.15.5'
- otp: '25'
elixir: '1.12.3'
- otp: '25'
elixir: '1.13.4'
- otp: "22"
elixir: "1.14.5"
- otp: "22"
elixir: "1.15.5"
- otp: "23"
elixir: "1.15.5"
- otp: "25"
elixir: "1.12.3"
- otp: "25"
elixir: "1.13.4"
# Include the release candidate for the next Elixir, but don't
# fail CI.
# include:
Expand All @@ -34,19 +34,23 @@ jobs:
# experimental: true

steps:
- uses: actions/checkout@v3
- name: Set up Elixir
uses: erlef/setup-beam@v1
with:
elixir-version: ${{matrix.elixir}} # Define the elixir version [required]
otp-version: ${{matrix.otp}} # Define the OTP version [required]
- name: Restore dependencies cache
uses: actions/cache@v2
with:
path: deps
key: ${{ runner.os }}-${{ matrix.elixir }}-${{ matrix.otp }}-mix-${{ hashFiles('**/mix.lock') }}
restore-keys: ${{ runner.os }}-${{ matrix.elixir }}-${{ matrix.otp }}-mix-
- name: Install dependencies
run: mix deps.get
- name: Run tests
run: mix test
- uses: actions/checkout@v3
- name: Set up Elixir
uses: erlef/setup-beam@v1
with:
elixir-version: ${{matrix.elixir}} # Define the elixir version [required]
otp-version: ${{matrix.otp}} # Define the OTP version [required]
- name: Restore dependencies cache
uses: actions/cache@v2
with:
path: deps
key: ${{ runner.os }}-${{ matrix.elixir }}-${{ matrix.otp }}-mix-${{ hashFiles('**/mix.lock') }}
restore-keys: ${{ runner.os }}-${{ matrix.elixir }}-${{ matrix.otp }}-mix-
- name: Setup Postgres Database
run: docker compose up -d
- name: Install dependencies
run: mix deps.get
- name: Run tests
env:
MIX_ENV: test
run: mix do test.setup, test
12 changes: 12 additions & 0 deletions config/config.exs
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,15 @@ import Config

# Use Jason for JSON parsing in Phoenix
# config :phoenix, :json_library, Jason

config :kaffy, ecto_repos: [KaffyTest.Repo]

config :logger, level: :warning

config :kaffy, KaffyTest.Repo,
name: KaffyTest.Repo,
pool: Ecto.Adapters.SQL.Sandbox,
pool_size: System.schedulers_online() * 2,
priv: "test/support/postgres",
stacktrace: true,
url: "postgres://postgres:postgres@localhost:5432/kaffy_test"
11 changes: 11 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
name: "kaffy"

services:
postgres:
image: postgres:16.2
ports:
- "5432:5432"
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
POSTGRES_DB: kaffy_test
20 changes: 18 additions & 2 deletions mix.exs
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,16 @@ defmodule Kaffy.MixProject do
def project do
[
app: :kaffy,
aliases: aliases(),
version: @version,
elixir: "~> 1.12",
compilers: Mix.compilers(),
elixirc_paths: elixirc_paths(Mix.env()),
preferred_cli_env: [
"test.reset": :test,
"test.setup": :test,
"ecto.gen.migration": :test
],
start_permanent: Mix.env() == :prod,
description: description(),
package: package(),
Expand All @@ -29,20 +35,23 @@ defmodule Kaffy.MixProject do
end

# Specifies which paths to compile per environment.
defp elixirc_paths(:test), do: ["lib", "test/fixtures"]
defp elixirc_paths(:test), do: ["lib", "test/fixtures", "test/support"]
defp elixirc_paths(_), do: ["lib"]

# Run "mix help deps" to learn about dependencies.
defp deps do
[
{:ex_machina, "~> 2.7.0", only: :test},
{:phoenix, "~> 1.7.10"},
{:phoenix_html, "~> 4.0"},
{:phoenix_html_helpers, "~> 1.0"},
{:phoenix_view, "~> 2.0.2"},
{:mock, "~> 0.3.3", only: :test},
{:ecto, "~> 3.0"},
{:ecto_sql, "~> 3.10"},
{:ex_doc, ">= 0.0.0", only: :dev, runtime: false},
{:jason, "~> 1.3", only: :test}
{:jason, "~> 1.3", only: :test},
{:postgrex, "~> 0.16", optional: true}
]
end

Expand Down Expand Up @@ -77,4 +86,11 @@ defmodule Kaffy.MixProject do
formatters: ["html"]
]
end

defp aliases do
[
"test.reset": ["ecto.drop", "test.setup"],
"test.setup": ["ecto.create", "ecto.migrate"]
]
end
end
4 changes: 4 additions & 0 deletions mix.lock
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
%{
"castore": {:hex, :castore, "1.0.5", "9eeebb394cc9a0f3ae56b813459f990abb0a3dedee1be6b27fdb50301930502f", [:mix], [], "hexpm", "8d7c597c3e4a64c395980882d4bca3cebb8d74197c590dc272cfd3b6a6310578"},
"db_connection": {:hex, :db_connection, "2.6.0", "77d835c472b5b67fc4f29556dee74bf511bbafecdcaf98c27d27fa5918152086", [:mix], [{:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "c2f992d15725e721ec7fbc1189d4ecdb8afef76648c746a8e1cad35e3b8a35f3"},
"decimal": {:hex, :decimal, "2.1.1", "5611dca5d4b2c3dd497dec8f68751f1f1a54755e8ed2a966c2633cf885973ad6", [:mix], [], "hexpm", "53cfe5f497ed0e7771ae1a475575603d77425099ba5faef9394932b35020ffcc"},
"earmark_parser": {:hex, :earmark_parser, "1.4.33", "3c3fd9673bb5dcc9edc28dd90f50c87ce506d1f71b70e3de69aa8154bc695d44", [:mix], [], "hexpm", "2d526833729b59b9fdb85785078697c72ac5e5066350663e5be6a1182da61b8f"},
"ecto": {:hex, :ecto, "3.10.3", "eb2ae2eecd210b4eb8bece1217b297ad4ff824b4384c0e3fdd28aaf96edd6135", [:mix], [{:decimal, "~> 1.6 or ~> 2.0", [hex: :decimal, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "44bec74e2364d491d70f7e42cd0d690922659d329f6465e89feb8a34e8cd3433"},
"ecto_sql": {:hex, :ecto_sql, "3.10.2", "6b98b46534b5c2f8b8b5f03f126e75e2a73c64f3c071149d32987a5378b0fdbd", [:mix], [{:db_connection, "~> 2.4.1 or ~> 2.5", [hex: :db_connection, repo: "hexpm", optional: false]}, {:ecto, "~> 3.10.0", [hex: :ecto, repo: "hexpm", optional: false]}, {:myxql, "~> 0.6.0", [hex: :myxql, repo: "hexpm", optional: true]}, {:postgrex, "~> 0.16.0 or ~> 0.17.0 or ~> 1.0", [hex: :postgrex, repo: "hexpm", optional: true]}, {:tds, "~> 2.1.1 or ~> 2.2", [hex: :tds, repo: "hexpm", optional: true]}, {:telemetry, "~> 0.4.0 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "68c018debca57cb9235e3889affdaec7a10616a4e3a80c99fa1d01fdafaa9007"},
"ex_doc": {:hex, :ex_doc, "0.30.6", "5f8b54854b240a2b55c9734c4b1d0dd7bdd41f71a095d42a70445c03cf05a281", [:mix], [{:earmark_parser, "~> 1.4.31", [hex: :earmark_parser, repo: "hexpm", optional: false]}, {:makeup_elixir, "~> 0.14", [hex: :makeup_elixir, repo: "hexpm", optional: false]}, {:makeup_erlang, "~> 0.1", [hex: :makeup_erlang, repo: "hexpm", optional: false]}], "hexpm", "bd48f2ddacf4e482c727f9293d9498e0881597eae6ddc3d9562bd7923375109f"},
"ex_machina": {:hex, :ex_machina, "2.7.0", "b792cc3127fd0680fecdb6299235b4727a4944a09ff0fa904cc639272cd92dc7", [:mix], [{:ecto, "~> 2.2 or ~> 3.0", [hex: :ecto, repo: "hexpm", optional: true]}, {:ecto_sql, "~> 3.0", [hex: :ecto_sql, repo: "hexpm", optional: true]}], "hexpm", "419aa7a39bde11894c87a615c4ecaa52d8f107bbdd81d810465186f783245bf8"},
"jason": {:hex, :jason, "1.4.1", "af1504e35f629ddcdd6addb3513c3853991f694921b1b9368b0bd32beb9f1b63", [:mix], [{:decimal, "~> 1.0 or ~> 2.0", [hex: :decimal, repo: "hexpm", optional: true]}], "hexpm", "fbb01ecdfd565b56261302f7e1fcc27c4fb8f32d56eab74db621fc154604a7a1"},
"makeup": {:hex, :makeup, "1.1.0", "6b67c8bc2882a6b6a445859952a602afc1a41c2e08379ca057c0f525366fc3ca", [:mix], [{:nimble_parsec, "~> 1.2.2 or ~> 1.3", [hex: :nimble_parsec, repo: "hexpm", optional: false]}], "hexpm", "0a45ed501f4a8897f580eabf99a2e5234ea3e75a4373c8a52824f6e873be57a6"},
"makeup_elixir": {:hex, :makeup_elixir, "0.16.1", "cc9e3ca312f1cfeccc572b37a09980287e243648108384b97ff2b76e505c3555", [:mix], [{:makeup, "~> 1.0", [hex: :makeup, repo: "hexpm", optional: false]}, {:nimble_parsec, "~> 1.2.3 or ~> 1.3", [hex: :nimble_parsec, repo: "hexpm", optional: false]}], "hexpm", "e127a341ad1b209bd80f7bd1620a15693a9908ed780c3b763bccf7d200c767c6"},
Expand All @@ -20,6 +23,7 @@
"phoenix_view": {:hex, :phoenix_view, "2.0.3", "4d32c4817fce933693741deeb99ef1392619f942633dde834a5163124813aad3", [:mix], [{:phoenix_html, "~> 2.14.2 or ~> 3.0 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}, {:phoenix_template, "~> 1.0", [hex: :phoenix_template, repo: "hexpm", optional: false]}], "hexpm", "cd34049af41be2c627df99cd4eaa71fc52a328c0c3d8e7d4aa28f880c30e7f64"},
"plug": {:hex, :plug, "1.15.3", "712976f504418f6dff0a3e554c40d705a9bcf89a7ccef92fc6a5ef8f16a30a97", [:mix], [{:mime, "~> 1.0 or ~> 2.0", [hex: :mime, repo: "hexpm", optional: false]}, {:plug_crypto, "~> 1.1.1 or ~> 1.2 or ~> 2.0", [hex: :plug_crypto, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4.3 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "cc4365a3c010a56af402e0809208873d113e9c38c401cabd88027ef4f5c01fd2"},
"plug_crypto": {:hex, :plug_crypto, "2.0.0", "77515cc10af06645abbfb5e6ad7a3e9714f805ae118fa1a70205f80d2d70fe73", [:mix], [], "hexpm", "53695bae57cc4e54566d993eb01074e4d894b65a3766f1c43e2c61a1b0f45ea9"},
"postgrex": {:hex, :postgrex, "0.17.5", "0483d054938a8dc069b21bdd636bf56c487404c241ce6c319c1f43588246b281", [:mix], [{:db_connection, "~> 2.1", [hex: :db_connection, repo: "hexpm", optional: false]}, {:decimal, "~> 1.5 or ~> 2.0", [hex: :decimal, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:table, "~> 0.1.0", [hex: :table, repo: "hexpm", optional: true]}], "hexpm", "50b8b11afbb2c4095a3ba675b4f055c416d0f3d7de6633a595fc131a828a67eb"},
"telemetry": {:hex, :telemetry, "1.2.1", "68fdfe8d8f05a8428483a97d7aab2f268aaff24b49e0f599faa091f1d4e7f61c", [:rebar3], [], "hexpm", "dad9ce9d8effc621708f99eac538ef1cbe05d6a874dd741de2e689c47feafed5"},
"websock": {:hex, :websock, "0.5.3", "2f69a6ebe810328555b6fe5c831a851f485e303a7c8ce6c5f675abeb20ebdadc", [:mix], [], "hexpm", "6105453d7fac22c712ad66fab1d45abdf049868f253cf719b625151460b8b453"},
"websock_adapter": {:hex, :websock_adapter, "0.5.5", "9dfeee8269b27e958a65b3e235b7e447769f66b5b5925385f5a569269164a210", [:mix], [{:bandit, ">= 0.6.0", [hex: :bandit, repo: "hexpm", optional: true]}, {:plug, "~> 1.14", [hex: :plug, repo: "hexpm", optional: false]}, {:plug_cowboy, "~> 2.6", [hex: :plug_cowboy, repo: "hexpm", optional: true]}, {:websock, "~> 0.5", [hex: :websock, repo: "hexpm", optional: false]}], "hexpm", "4b977ba4a01918acbf77045ff88de7f6972c2a009213c515a445c48f224ffce9"},
Expand Down
6 changes: 5 additions & 1 deletion test/fixtures/travel_schema.ex
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,11 @@ defmodule Fixtures.TravelSchema do
field(:description, :string)
field(:number_of_people, :integer)
field(:requires_passport, :boolean)
field(:travel_type, Ecto.Enum, values: [business: "business", leisure: "leisure", other: "undisclosed"])

field(:travel_type, Ecto.Enum,
values: [business: "business", leisure: "leisure", other: "undisclosed"]
)

field(:start_time, :utc_datetime)
field(:local_start_time, :naive_datetime)
field(:end_date, :date)
Expand Down
133 changes: 133 additions & 0 deletions test/kaffy/resource_query_test.exs
Original file line number Diff line number Diff line change
@@ -0,0 +1,133 @@
defmodule Kaffy.ResourceQueryTest do
use Kaffy.DataCase, async: false

alias Kaffy.ResourceQuery
alias KaffyTest.Schemas.Pet

defmodule PetAdmin do
end

setup_all do
Application.put_env(:kaffy, :ecto_repo, KaffyTest.Repo)

Application.put_env(:kaffy, :resources, fn _ ->
[
admin: [
name: "Pets",
resources: [
pets: [
schema: KaffyTest.Schemas.Pet,
admin: PetAdmin
]
]
]
]
end)
end

setup do
conn =
build_conn()
|> Plug.Test.init_test_session(%{})
|> Phoenix.Controller.fetch_flash([])
|> Map.put(:query_params, %{})

[conn: conn]
end

describe "list_resource/3" do
test "returns all resources", %{conn: conn} do
[pet1 | _pets] = insert_list(3, :pet)
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
assert {3, pets} = ResourceQuery.list_resource(conn, resource, %{})
assert Enum.any?(pets, fn %Pet{} = pet -> pet.id == pet1.id end)
end

test "returns per_page limit", %{conn: conn} do
pets = insert_list(3, :pet)
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
assert {3, [returned_pet]} = ResourceQuery.list_resource(conn, resource, %{"limit" => "1"})

pet_ids = Enum.map(pets, & &1.id)
assert Enum.member?(pet_ids, returned_pet.id)
end

test "returns pages", %{conn: conn} do
pets = insert_list(3, :pet)

resource = Kaffy.Utils.get_resource(conn, "admin", "pets")

assert {3, [returned_pet1]} =
ResourceQuery.list_resource(conn, resource, %{"limit" => "1", "page" => "1"})

assert {3, [returned_pet2]} =
ResourceQuery.list_resource(conn, resource, %{"limit" => "1", "page" => "2"})

assert {3, [returned_pet3]} =
ResourceQuery.list_resource(conn, resource, %{"limit" => "1", "page" => "3"})

pet_ids =
Enum.map(pets, & &1.id)
|> Enum.sort()

returned_pet_ids =
[returned_pet1.id, returned_pet2.id, returned_pet3.id]
|> Enum.sort()

assert returned_pet_ids == pet_ids
end

test "returns search results", %{conn: conn} do
insert_list(3, :pet)
pet = insert(:pet, name: "Fido")
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")

assert {1, [returned_pet]} =
ResourceQuery.list_resource(conn, resource, %{"search" => "Fido"})

assert returned_pet.id == pet.id
end

test "returns no results when search does not match", %{conn: conn} do
insert_list(3, :pet)
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
assert {0, []} = ResourceQuery.list_resource(conn, resource, %{"search" => "Fido"})
end

test "returns filter results", %{conn: conn} do
insert_list(3, :pet)
pet = insert(:pet, name: "Fido")
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
conn = Map.put(conn, :query_params, %{"person_id" => pet.person.id})
assert {1, [returned_pet]} = ResourceQuery.list_resource(conn, resource, %{})
assert returned_pet.id == pet.id
end

test "returns no results when filter does not match", %{conn: conn} do
insert_list(3, :pet)
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
conn = Map.put(conn, :query_params, %{"person_id" => "0"})
assert {0, []} = ResourceQuery.list_resource(conn, resource, %{})
end

test "returns ordered results", %{conn: conn} do
pets = insert_list(3, :pet)
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
conn = Map.put(conn, :query_params, %{"_of" => "id", "_ow" => "asc"})
assert {3, returned_pets} = ResourceQuery.list_resource(conn, resource, %{})
returned_pet_ids = Enum.map(returned_pets, & &1.id)
sorted_pet_ids = Enum.sort(Enum.map(pets, & &1.id))
assert returned_pet_ids == sorted_pet_ids
end

test "returns ordered results descending", %{conn: conn} do
pets = insert_list(3, :pet)
resource = Kaffy.Utils.get_resource(conn, "admin", "pets")
conn = Map.put(conn, :query_params, %{"_of" => "id", "_ow" => "desc"})
assert {3, returned_pets} = ResourceQuery.list_resource(conn, resource, %{})
returned_pet_ids = Enum.map(returned_pets, & &1.id)
sorted_pet_ids = Enum.reverse(Enum.sort(Enum.map(pets, & &1.id)))
assert returned_pet_ids == sorted_pet_ids
end
end
end
27 changes: 19 additions & 8 deletions test/resource_admin_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,10 @@ defmodule Kaffy.ResourceAdminTest do
end

def deserialize_id(_schema, serialized_id) do
{person_id, pet_id} = serialized_id
|> Base.url_decode64!(padding: false)
|> :erlang.binary_to_term()
{person_id, pet_id} =
serialized_id
|> Base.url_decode64!(padding: false)
|> :erlang.binary_to_term()

[person_id: person_id, pet_id: pet_id]
end
Expand Down Expand Up @@ -75,11 +76,17 @@ defmodule Kaffy.ResourceAdminTest do
end

test "serialize composite id" do
assert ResourceAdmin.serialize_id([schema: Owner, admin: OwnerAdmin], %{person_id: 1, pet_id: 2}) == "1:2"
assert ResourceAdmin.serialize_id([schema: Owner, admin: OwnerAdmin], %{
person_id: 1,
pet_id: 2
}) == "1:2"
end

test "custom serialization of composite key" do
assert ResourceAdmin.serialize_id([schema: Owner, admin: OwnerETFAdmin], %{person_id: 1, pet_id: 2}) == "g2gCYQFhAg"
assert ResourceAdmin.serialize_id([schema: Owner, admin: OwnerETFAdmin], %{
person_id: 1,
pet_id: 2
}) == "g2gCYQFhAg"
end
end

Expand All @@ -89,14 +96,18 @@ defmodule Kaffy.ResourceAdminTest do
end

test "deserialize composite id" do
assert ResourceAdmin.deserialize_id([schema: Owner, admin: OwnerAdmin], "1:2") == [person_id: "1", pet_id: "2"]
assert ResourceAdmin.deserialize_id([schema: Owner, admin: OwnerAdmin], "1:2") == [
person_id: "1",
pet_id: "2"
]
end

test "custom deserialization of composite key" do
assert ResourceAdmin.deserialize_id([schema: Owner, admin: OwnerETFAdmin], "g2gCYQFhAg") == [person_id: 1, pet_id: 2]
assert ResourceAdmin.deserialize_id([schema: Owner, admin: OwnerETFAdmin], "g2gCYQFhAg") ==
[person_id: 1, pet_id: 2]
end
end

describe "index_description/1" do
test "nil if index_description is not defined as function in admin" do
refute ResourceAdmin.index_description(schema: Nested.Node, admin: NestedNodeAdmin)
Expand Down
Loading
Loading