Skip to content

Commit

Permalink
Merge pull request #54 from dwyl/query-all
Browse files Browse the repository at this point in the history
Query all
  • Loading branch information
Danwhy authored Mar 12, 2019
2 parents a057334 + d9eb8b9 commit fd63ef5
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 28 deletions.
58 changes: 57 additions & 1 deletion lib/alog/connection.ex
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,63 @@ defmodule Alog.Connection do
defdelegate to_constraints(error_struct), to: EAPC

@impl true
defdelegate all(query), to: EAPC
def all(query) do
iodata_query = EAPC.all(query)

query = iodata_query
|> IO.iodata_to_binary()
|> alogify_all_query()

query
end

defp alogify_all_query(query) do
query_data = get_query_data(query)
# if all query is called during migration, some column used in the
# alogify version might not be yet defined.
# Return the "normal" query
if (query_data["table_name"] == "\"schema_migrations\"") do
query
else
subquery = IO.iodata_to_binary(
[ "SELECT DISTINCT ON (#{query_data["table_as"]}.\"entry_id\" ) ",
query_data["subquery_fields"],
get_deleted_field(query_data),
" FROM ",
query_data["table_name"], " AS ", query_data["table_as"],
query_data["rest_query"],
" ORDER BY #{query_data["table_as"]}.\"entry_id\", #{query_data["table_as"]}.\"inserted_at\" DESC"
]
)

IO.iodata_to_binary(
["SELECT ", query_data["field_names"], " FROM (", subquery, ") AS alogsubquery WHERE (NOT alogsubquery.\"deleted\")"]
)
end
end

defp get_query_data(query) do
data = Regex.named_captures(~r/(\bSELECT\b)\s(?<fields>.*)\sFROM\s(?<table_name>.*)\sas\s(?<table_as>.*)(?<rest_query>.*)/i, query)
data = Map.put(data, "field_names", Regex.replace(~r/#{data["table_as"]}/, data["fields"], "alogsubquery"))

subquery_fields = data["fields"]
|> String.split(",")
|> Enum.map(fn f ->
field_name = Regex.replace(~r/#{data["table_as"]}./, f, "")
f <> " AS #{field_name}"
end)
|> Enum.join(", ")

Map.put(data, "subquery_fields", subquery_fields)
end

defp get_deleted_field(query_data) do
if String.contains?(query_data["subquery_fields"], "#{query_data["table_as"]}.\"deleted\"") do
""
else
", #{query_data["table_as"]}.\"deleted\" AS \"deleted\""
end
end

@impl true
defdelegate update_all(query, prefix \\ nil), to: EAPC
Expand Down
37 changes: 10 additions & 27 deletions test/all_test.exs
Original file line number Diff line number Diff line change
@@ -1,31 +1,14 @@
defmodule AlogTest.AllTest do
use Alog.TestApp.DataCase

# alias Alog.TestApp.{User, Helpers}
#
# describe "all/0:" do
# test "succeeds" do
# {:ok, _} = %User{} |> User.changeset(Helpers.user_1_params()) |> User.insert()
# {:ok, _} = %User{} |> User.changeset(Helpers.user_2_params()) |> User.insert()
#
# assert length(User.all()) == 2
# end
#
# test "does not include old items" do
# {:ok, user} = %User{} |> User.changeset(Helpers.user_1_params()) |> User.insert()
# {:ok, _} = %User{} |> User.changeset(Helpers.user_2_params()) |> User.insert()
# {:ok, _} = user |> User.changeset(%{postcode: "W2 3EC"}) |> User.update()
#
# assert length(User.all()) == 2
# end
#
# test "all return inserted_at original value" do
# {:ok, user} = %User{} |> User.changeset(Helpers.user_3_params()) |> User.insert()
# {:ok, user_updated} = user |> User.changeset(%{postcode: "W2 3EC"}) |> User.update()
#
# [user_all] = User.all()
# assert user_all.inserted_at == user.inserted_at
# assert user_all.postcode == user_updated.postcode
# end
# end
alias Alog.TestApp.{Comment}

describe "all/0:" do
test "succeeds" do
{:ok, _comment} = %Comment{comment: "Hello Rob"} |> Repo.insert()
{:ok, _} = %Comment{comment: "Hello Dan"} |> Repo.insert()

assert length(Repo.all(Comment)) == 2
end
end
end

0 comments on commit fd63ef5

Please sign in to comment.