zf

zenflows testing
git clone https://s.sonu.ch/~srfsh/zf.git
Log | Files | Refs | Submodules | README | LICENSE

commit d1417e74e07fe90116885c594ba96db78f8e360f
parent 1ac24e4737c38cb9aa34c21607193a3661c60dd0
Author: srfsh <dev@srf.sh>
Date:   Mon, 22 Aug 2022 19:54:08 +0300

Zenflows{Test,}.VF.AgentRelationship: add paging support and small improvements

Diffstat:
Msrc/zenflows/vf/agent_relationship/domain.ex | 58+++++++++++++++++++++++++++++++---------------------------
Msrc/zenflows/vf/agent_relationship/resolv.ex | 41+++++++++++++++++++++++------------------
Msrc/zenflows/vf/agent_relationship/type.ex | 49++++++++++++++++++++++++++++++++++---------------
Mtest/vf/agent_relationship/domain.test.exs | 45+++++++++++++++++++++++++++------------------
Mtest/vf/agent_relationship/type.test.exs | 122++++++++++++++++++++++++++++++++++++-------------------------------------------
5 files changed, 171 insertions(+), 144 deletions(-)

diff --git a/src/zenflows/vf/agent_relationship/domain.ex b/src/zenflows/vf/agent_relationship/domain.ex @@ -20,55 +20,71 @@ defmodule Zenflows.VF.AgentRelationship.Domain do alias Ecto.Multi alias Zenflows.DB.Repo +alias Zenflows.GQL.Paging alias Zenflows.VF.AgentRelationship @typep repo() :: Ecto.Repo.t() @typep chgset() :: Ecto.Changeset.t() -@typep changes() :: Ecto.Multi.changes() @typep id() :: Zenflows.DB.Schema.id() @typep params() :: Zenflows.DB.Schema.params() -@spec by_id(repo(), id()) :: AgentRelationship.t() | nil -def by_id(repo \\ Repo, id) do - repo.get(AgentRelationship, id) +@spec one(repo(), id() | map() | Keyword.t()) + :: {:ok, AgentRelationship.t()} | {:error, String.t()} +def one(repo \\ Repo, _) +def one(repo, id) when is_binary(id), do: one(repo, id: id) +def one(repo, clauses) do + case repo.get_by(AgentRelationship, clauses) do + nil -> {:error, "not found"} + found -> {:ok, found} + end +end + +@spec all(Paging.params()) :: Paging.result(AgentRelationship.t()) +def all(params) do + Paging.page(AgentRelationship, params) end @spec create(params()) :: {:ok, AgentRelationship.t()} | {:error, chgset()} def create(params) do Multi.new() - |> Multi.insert(:rel, AgentRelationship.chgset(params)) + |> Multi.insert(:insert, AgentRelationship.chgset(params)) |> Repo.transaction() |> case do - {:ok, %{rel: rel}} -> {:ok, rel} + {:ok, %{insert: ar}} -> {:ok, ar} {:error, _, cset, _} -> {:error, cset} end end -@spec update(id(), params()) :: {:ok, AgentRelationship.t()} | {:error, chgset()} +@spec update(id(), params()) + :: {:ok, AgentRelationship.t()} | {:error, String.t() | chgset()} def update(id, params) do Multi.new() - |> Multi.run(:get, multi_get(id)) - |> Multi.update(:update, &AgentRelationship.chgset(&1.get, params)) + |> Multi.put(:id, id) + |> Multi.run(:one, &one/2) + |> Multi.update(:update, &AgentRelationship.chgset(&1.one, params)) |> Repo.transaction() |> case do - {:ok, %{update: rel}} -> {:ok, rel} + {:ok, %{update: ar}} -> {:ok, ar} {:error, _, msg_or_cset, _} -> {:error, msg_or_cset} end end -@spec delete(id()) :: {:ok, AgentRelationship.t()} | {:error, chgset()} +@spec delete(id()) + :: {:ok, AgentRelationship.t()} | {:error, String.t() | chgset()} def delete(id) do Multi.new() - |> Multi.run(:get, multi_get(id)) - |> Multi.delete(:delete, &(&1.get)) + |> Multi.put(:id, id) + |> Multi.run(:one, &one/2) + |> Multi.delete(:delete, &(&1.one)) |> Repo.transaction() |> case do - {:ok, %{delete: rel}} -> {:ok, rel} + {:ok, %{delete: ar}} -> {:ok, ar} {:error, _, msg_or_cset, _} -> {:error, msg_or_cset} end end -@spec preload(AgentRelationship.t(), :subject | :object | :relationship) :: AgentRelationship.t() +@spec preload(AgentRelationship.t(), :subject | :object | :relationship) + :: AgentRelationship.t() def preload(rel, :subject) do Repo.preload(rel, :subject) end @@ -80,16 +96,4 @@ end def preload(rel, :relationship) do Repo.preload(rel, :relationship) end - -# Returns an AgentRelationship in ok-err tuple from given ID. Used inside -# Ecto.Multi.run/5 to get a record in transaction. -@spec multi_get(id()) :: (repo(), changes() -> {:ok, AgentRelationship.t()} | {:error, String.t()}) -defp multi_get(id) do - fn repo, _ -> - case by_id(repo, id) do - nil -> {:error, "not found"} - rel -> {:ok, rel} - end - end -end end diff --git a/src/zenflows/vf/agent_relationship/resolv.ex b/src/zenflows/vf/agent_relationship/resolv.ex @@ -20,40 +20,45 @@ defmodule Zenflows.VF.AgentRelationship.Resolv do alias Zenflows.VF.{AgentRelationship, AgentRelationship.Domain} -def subject(%AgentRelationship{} = rel, _params, _info) do - rel = Domain.preload(rel, :subject) - {:ok, rel.subject} -end - -def object(%AgentRelationship{} = rel, _params, _info) do - rel = Domain.preload(rel, :object) - {:ok, rel.object} +def agent_relationship(params, _) do + Domain.one(params) end -def relationship(%AgentRelationship{} = rel, _params, _info) do - rel = Domain.preload(rel, :relationship) - {:ok, rel.relationship} -end - -def agent_relationship(%{id: id}, _info) do - {:ok, Domain.by_id(id)} +def agent_relationships(params, _) do + Domain.all(params) end -def create_agent_relationship(%{relationship: params}, _info) do +def create_agent_relationship(%{relationship: params}, _) do with {:ok, rel} <- Domain.create(params) do {:ok, %{agent_relationship: rel}} end end -def update_agent_relationship(%{relationship: %{id: id} = params}, _info) do +def update_agent_relationship(%{relationship: %{id: id} = params}, _) do with {:ok, rel} <- Domain.update(id, params) do {:ok, %{agent_relationship: rel}} end end -def delete_agent_relationship(%{id: id}, _info) do +def delete_agent_relationship(%{id: id}, _) do with {:ok, _rel} <- Domain.delete(id) do {:ok, true} end end + +def subject(%AgentRelationship{} = rel, _, _) do + rel = Domain.preload(rel, :subject) + {:ok, rel.subject} +end + +def object(%AgentRelationship{} = rel, _, _) do + rel = Domain.preload(rel, :object) + {:ok, rel.object} +end + +def relationship(%AgentRelationship{} = rel, _, _) do + rel = Domain.preload(rel, :relationship) + {:ok, rel.relationship} +end + end diff --git a/src/zenflows/vf/agent_relationship/type.ex b/src/zenflows/vf/agent_relationship/type.ex @@ -26,11 +26,14 @@ alias Zenflows.VF.AgentRelationship.Resolv The subject of a relationship between two agents. For example, if Mary is a member of a group, then Mary is the subject. """ +@subject_id "(`Agent`) #{@subject}" @object """ The object of a relationship between two agents. For example, if Mary is a member of a group, then the group is the object. """ +@object_id "(`Agent`) #{@object}" @relationship "A kind of relationship that exists between two agents." +@relationship_id "(`AgentRelationshipRole`) #{@relationship}" #@in_scope_of """ #Grouping around something to create a boundary or context, used for #documenting, accounting, planning. @@ -61,18 +64,14 @@ object :agent_relationship do field :note, :string end -object :agent_relationship_response do - field :agent_relationship, non_null(:agent_relationship) -end - input_object :agent_relationship_create_params do - @desc "(`Agent`) " <> @subject + @desc @subject_id field :subject_id, non_null(:id), name: "subject" - @desc "(`Agent`) " <> @object + @desc @object_id field :object_id, non_null(:id), name: "object" - @desc "(`AgentRelationshipRole`) " <> @relationship + @desc @relationship_id field :relationship_id, non_null(:id), name: "relationship" #@desc @in_scope_of @@ -85,13 +84,13 @@ end input_object :agent_relationship_update_params do field :id, non_null(:id) - @desc "(`Agent`) " <> @subject + @desc @subject_id field :subject_id, :id, name: "subject" - @desc "(`Agent`) " <> @object + @desc @object_id field :object_id, :id, name: "object" - @desc "(`AgentRelationshipRole`) " <> @relationship + @desc @relationship_id field :relationship_id, :id, name: "relationship" #@desc @in_scope_of @@ -101,6 +100,20 @@ input_object :agent_relationship_update_params do field :note, :string end +object :agent_relationship_response do + field :agent_relationship, non_null(:agent_relationship) +end + +object :agent_relationship_edge do + field :cursor, non_null(:id) + field :node, non_null(:agent_relationship) +end + +object :agent_relationship_connection do + field :page_info, non_null(:page_info) + field :edges, non_null(list_of(non_null(:agent_relationship_edge))) +end + object :query_agent_relationship do @desc "Retrieve details of an agent relationship by its ID." field :agent_relationship, :agent_relationship do @@ -108,11 +121,17 @@ object :query_agent_relationship do resolve &Resolv.agent_relationship/2 end - #@desc """ - #Retrieve details of all the relationships between all agents - #registered in this collaboration space. - #""" - #agentRelationships(start: ID, limit: Int): [AgentRelationship!] + @desc """ + Retrieve details of all the relationships between all agents + registered in this collaboration space. + """ + field :agent_relationships, :agent_relationship_connection do + arg :first, :integer + arg :after, :id + arg :last, :integer + arg :before, :id + resolve &Resolv.agent_relationships/2 + end end object :mutation_agent_relationship do diff --git a/test/vf/agent_relationship/domain.test.exs b/test/vf/agent_relationship/domain.test.exs @@ -30,42 +30,45 @@ setup do # in_scope_of: note: Factory.uniq("note"), }, - agent_relationship: Factory.insert!(:agent_relationship), + inserted: Factory.insert!(:agent_relationship), } end -test "by_id/1 returns an AgentRelationship", %{agent_relationship: rel} do - assert %AgentRelationship{} = Domain.by_id(rel.id) +describe "one/1" do + test "with good id: finds the AgentRelationship", %{inserted: %{id: id}} do + assert {:ok, %AgentRelationship{}} = Domain.one(id) + end + + test "with bad id: doesn't find the AgentRelationship"do + assert {:error, "not found"} = Domain.one(Factory.id()) + end end describe "create/1" do - test "creates an AgentRelationship with valid params", %{params: params} do - assert {:ok, %AgentRelationship{} = rel} = Domain.create(params) - - assert rel.subject_id == params.subject_id - assert rel.object_id == params.object_id - assert rel.relationship_id == params.relationship_id - assert rel.note == params.note + test "with good params: creates an AgentRelationship", %{params: params} do + assert {:ok, %AgentRelationship{} = new} = Domain.create(params) + assert new.subject_id == params.subject_id + assert new.object_id == params.object_id + assert new.relationship_id == params.relationship_id + assert new.note == params.note end - test "doesn't create a AgentRelationship with invalid params" do + test "with bad params: doesn't create an AgentRelationship" do assert {:error, %Changeset{}} = Domain.create(%{}) end end describe "update/2" do - test "updates an AgentRelationship with valid params", %{params: params, agent_relationship: old} do + test "with good params: updates the AgentRelationship", %{params: params, inserted: old} do assert {:ok, %AgentRelationship{} = new} = Domain.update(old.id, params) - assert new.subject_id == params.subject_id assert new.object_id == params.object_id assert new.relationship_id == params.relationship_id assert new.note == params.note end - test "doesn't update a AgentRelationship", %{agent_relationship: old} do + test "with bad params: doesn't update the AgentRelationship", %{inserted: old} do assert {:ok, %AgentRelationship{} = new} = Domain.update(old.id, %{}) - assert new.subject_id == old.subject_id assert new.object_id == old.object_id assert new.relationship_id == old.relationship_id @@ -73,8 +76,14 @@ describe "update/2" do end end -test "delete/1 deletes an AgentRelationship", %{agent_relationship: %{id: id}} do - assert {:ok, %AgentRelationship{id: ^id}} = Domain.delete(id) - assert Domain.by_id(id) == nil +describe "delete/1" do + test "with good id: deletes the AgentRelationship", %{inserted: %{id: id}} do + assert {:ok, %AgentRelationship{id: ^id}} = Domain.delete(id) + assert {:error, "not found"} = Domain.one(id) + end + + test "with bad id: doesn't delete the AgentRelationship" do + assert {:error, "not found"} = Domain.delete(Factory.id()) + end end end diff --git a/test/vf/agent_relationship/type.test.exs b/test/vf/agent_relationship/type.test.exs @@ -21,98 +21,88 @@ use ZenflowsTest.Help.AbsinCase, async: true setup do %{ params: %{ - subject_id: Factory.insert!(:agent).id, - object_id: Factory.insert!(:agent).id, - relationship_id: Factory.insert!(:agent_relationship_role).id, - # in_scope_of: - note: Factory.uniq("note"), + "subject" => Factory.insert!(:agent).id, + "object" => Factory.insert!(:agent).id, + "relationship" => Factory.insert!(:agent_relationship_role).id, + # inScopeOf: + "note" => Factory.uniq("note"), }, - agent_relationship: Factory.insert!(:agent_relationship), + inserted: Factory.insert!(:agent_relationship), } end +@frag """ +fragment agentRelationship on AgentRelationship { + id + subject { id } + object { id } + relationship { id } + note +} +""" + describe "Query" do - test "agentRelationship()", %{agent_relationship: rel} do + test "agentRelationship", %{inserted: new} do assert %{data: %{"agentRelationship" => data}} = - query!(""" - agentRelationship(id: "#{rel.id}") { - id - subject { id } - object { id } - relationship { - id - } - note + run!(""" + #{@frag} + query ($id: ID!) { + agentRelationship(id: $id) {...agentRelationship} } - """) + """, vars: %{"id" => new.id}) - assert data["id"] == rel.id - assert data["subject"]["id"] == rel.subject_id - assert data["object"]["id"] == rel.object_id - assert data["relationship"]["id"] == rel.relationship_id - assert data["note"] == rel.note + assert data["id"] == new.id + assert data["subject"]["id"] == new.subject_id + assert data["object"]["id"] == new.object_id + assert data["relationship"]["id"] == new.relationship_id + assert data["note"] == new.note end end describe "Mutation" do - test "createAgentRelationship()", %{params: params} do + test "createAgentRelationship", %{params: params} do assert %{data: %{"createAgentRelationship" => %{"agentRelationship" => data}}} = - mutation!(""" - createAgentRelationship(relationship: { - subject: "#{params.subject_id}" - object: "#{params.object_id}" - relationship: "#{params.relationship_id}" - note: "#{params.note}" - }) { - agentRelationship { - id - subject { id } - object { id } - relationship { id } - note + run!(""" + #{@frag} + mutation ($relationship: AgentRelationshipCreateParams!) { + createAgentRelationship(relationship: $relationship) { + agentRelationship {...agentRelationship} } } - """) + """, vars: %{"relationship" => params}) assert {:ok, _} = Zenflows.DB.ID.cast(data["id"]) - assert data["subject"]["id"] == params.subject_id - assert data["object"]["id"] == params.object_id - assert data["relationship"]["id"] == params.relationship_id - assert data["note"] == params.note + assert data["subject"]["id"] == params["subject"] + assert data["object"]["id"] == params["object"] + assert data["relationship"]["id"] == params["relationship"] + assert data["note"] == params["note"] end - test "updateAgentRelationship()", %{params: params, agent_relationship: rel} do + test "updateAgentRelationship", %{params: params, inserted: old} do assert %{data: %{"updateAgentRelationship" => %{"agentRelationship" => data}}} = - mutation!(""" - updateAgentRelationship(relationship: { - id: "#{rel.id}" - subject: "#{params.subject_id}" - object: "#{params.object_id}" - relationship: "#{params.relationship_id}" - note: "#{params.note}" - }) { - agentRelationship { - id - subject { id } - object { id } - relationship { id } - note + run!(""" + #{@frag} + mutation ($relationship: AgentRelationshipUpdateParams!) { + updateAgentRelationship(relationship: $relationship) { + agentRelationship {...agentRelationship} } } - """) + """, vars: %{"relationship" => Map.put(params, "id", old.id)}) - assert data["id"] == rel.id - assert data["subject"]["id"] == params.subject_id - assert data["object"]["id"] == params.object_id - assert data["relationship"]["id"] == params.relationship_id - assert data["note"] == params.note + assert data["id"] == old.id + assert data["subject"]["id"] == params["subject"] + assert data["object"]["id"] == params["object"] + assert data["relationship"]["id"] == params["relationship"] + assert data["note"] == params["note"] end - test "deleteAgentRelationship()", %{agent_relationship: %{id: id}} do + test "deleteAgentRelationship", %{inserted: %{id: id}} do assert %{data: %{"deleteAgentRelationship" => true}} = - mutation!(""" - deleteAgentRelationship(id: "#{id}") - """) + run!(""" + mutation ($id: ID!) { + deleteAgentRelationship(id: $id) + } + """, vars: %{"id" => id}) end end end