diff --git a/.credo.exs b/.credo.exs index 4453d21..564fbe7 100644 --- a/.credo.exs +++ b/.credo.exs @@ -107,7 +107,7 @@ alias Credo.Check {Check.Readability.SinglePipe, []}, {Check.Readability.StrictModuleLayout, []}, {Check.Readability.WithCustomTaggedTuple, []}, - {Check.Refactor.ABCSize, [max_size: 60]}, + {Check.Refactor.ABCSize, [max_size: 80]}, {Check.Refactor.DoubleBooleanNegation, []}, {Check.Refactor.FilterReject, []}, {Check.Refactor.MapMap, []}, diff --git a/lib/endo/adapters/postgres.ex b/lib/endo/adapters/postgres.ex index 6dc6277..988f241 100644 --- a/lib/endo/adapters/postgres.ex +++ b/lib/endo/adapters/postgres.ex @@ -23,12 +23,13 @@ defmodule Endo.Adapters.Postgres do @spec list_tables(repo :: module(), opts :: Keyword.t()) :: [Table.t()] def list_tables(repo, opts \\ []) when is_atom(repo) do + opts = Keyword.put_new(opts, :prefix, Endo.table_schema()) preloads = [:columns, table_constraints: [:key_column_usage, :constraint_column_usage]] derive_preloads = fn %Table{table_name: name} = table -> indexes = PgClass.query(collate_indexes: true, relname: name) metadata = PgClass.query(relname: name, relkind: ~w(r t m f p)) - size = Size.query(relname: name) + size = Size.query(relname: name, prefix: opts[:prefix]) %Table{ table diff --git a/lib/endo/adapters/postgres/size.ex b/lib/endo/adapters/postgres/size.ex index d8e95f2..35fbd74 100644 --- a/lib/endo/adapters/postgres/size.ex +++ b/lib/endo/adapters/postgres/size.ex @@ -3,8 +3,10 @@ defmodule Endo.Adapters.Postgres.Size do import Ecto.Query - @spec query([{:relname, String.t()}]) :: Ecto.Queryable.t() - def query(relname: relname) do + @spec query([{:relname, String.t()}, {:prefix, String.t()}]) :: Ecto.Queryable.t() + def query(opts) do + relname = Enum.join([opts[:prefix], opts[:relname]], ".") + select( with_cte("virtual_table", "virtual_table", as: diff --git a/lib/endo/adapters/postgres/table.ex b/lib/endo/adapters/postgres/table.ex index 20de6ed..c386b49 100644 --- a/lib/endo/adapters/postgres/table.ex +++ b/lib/endo/adapters/postgres/table.ex @@ -58,9 +58,7 @@ defmodule Endo.Adapters.Postgres.Table do @impl Endo.Queryable def query(base_query \\ base_query(), filters) do - filters - |> Keyword.put_new(:prefix, Endo.table_schema()) - |> Enum.reduce(base_query, fn + Enum.reduce(filters, base_query, fn {:prefix, prefix}, query when is_binary(prefix) -> from(x in query, where: x.table_schema == ^prefix) diff --git a/lib/endo/queryable.ex b/lib/endo/queryable.ex index 4a40625..24a01f7 100644 --- a/lib/endo/queryable.ex +++ b/lib/endo/queryable.ex @@ -34,6 +34,10 @@ defmodule Endo.Queryable do @callback query(base_query :: Ecto.Queryable.t(), Keyword.t()) :: Ecto.Queryable.t() @spec apply_filter(Ecto.Queryable.t(), field :: atom(), value :: any()) :: Ecto.Queryable.t() + def apply_filter(query, :prefix, value) do + from(x in query, prefix: ^value) + end + def apply_filter(query, :preload, value) do from(x in query, preload: ^value) end diff --git a/priv/repo/migrations/20221221123643_bootstrap_testing_env.exs b/priv/repo/migrations/20221221123643_bootstrap_testing_env.exs index 79179b6..1e90e4a 100644 --- a/priv/repo/migrations/20221221123643_bootstrap_testing_env.exs +++ b/priv/repo/migrations/20221221123643_bootstrap_testing_env.exs @@ -5,6 +5,20 @@ defmodule Test.Postgres.Repo.Migrations.BootstrapTestingEnv do create_accounts() create_repos() create_orgs() + create_prefix_table() + end + + def create_prefix_table do + execute("CREATE SCHEMA debug") + + flush() + + create table(:events, prefix: "debug") do + add(:type, :string, null: false) + add(:data, :map, null: false) + + timestamps() + end end defp create_accounts do diff --git a/test/endo_test.exs b/test/endo_test.exs index f57a385..030eb2f 100644 --- a/test/endo_test.exs +++ b/test/endo_test.exs @@ -69,6 +69,19 @@ defmodule EndoTest do test "given invalid table name, but valid repo, returns nil" do assert is_nil(Endo.get_table(Test.Postgres.Repo, "passports")) end + + test "returns nothing when querying table belonging to non-default prefix when not specified" do + assert is_nil(Endo.get_table(Test.Postgres.Repo, "events")) + end + + test "returns nothing when querying table belonging to incorrectly specified prefix" do + assert is_nil(Endo.get_table(Test.Postgres.Repo, "events", prefix: "something_random")) + end + + test "returns table belonging to non-default prefix if specified correctly" do + assert %Endo.Table{name: "events"} = + Endo.get_table(Test.Postgres.Repo, "events", prefix: "debug") + end end describe "list_tables/2 (Postgres)" do