Browse Source

Feature: Mobile - Add secondary organization access to GraphQL UserType.

Martin Gruner 2 years ago
parent
commit
045447edf4

+ 30 - 0
app/frontend/shared/graphql/types.ts

@@ -441,6 +441,26 @@ export type OrganizationMembersArgs = {
   last?: InputMaybe<Scalars['Int']>;
 };
 
+/** The connection type for Organization. */
+export type OrganizationConnection = {
+  __typename?: 'OrganizationConnection';
+  /** A list of edges. */
+  edges: Array<OrganizationEdge>;
+  /** Information to aid in pagination. */
+  pageInfo: PageInfo;
+  /** Indicates the total number of available records. */
+  totalCount: Scalars['Int'];
+};
+
+/** An edge in a connection. */
+export type OrganizationEdge = {
+  __typename?: 'OrganizationEdge';
+  /** A cursor for use in pagination. */
+  cursor: Scalars['String'];
+  /** The item at the end of the edge. */
+  node: Organization;
+};
+
 /** The organization insert/update fields. */
 export type OrganizationInput = {
   /** The organization active flag */
@@ -1014,6 +1034,7 @@ export type User = ObjectAttributeValueInterface & {
   permissions?: Maybe<UserPermission>;
   phone?: Maybe<Scalars['String']>;
   preferences?: Maybe<Scalars['JSON']>;
+  secondaryOrganizations?: Maybe<OrganizationConnection>;
   ticketsCount?: Maybe<TicketCount>;
   /** Last update date/time of the record */
   updatedAt: Scalars['ISO8601DateTime'];
@@ -1024,6 +1045,15 @@ export type User = ObjectAttributeValueInterface & {
   web?: Maybe<Scalars['String']>;
 };
 
+
+/** Users (admins, agents and customers) */
+export type UserSecondaryOrganizationsArgs = {
+  after?: InputMaybe<Scalars['String']>;
+  before?: InputMaybe<Scalars['String']>;
+  first?: InputMaybe<Scalars['Int']>;
+  last?: InputMaybe<Scalars['Int']>;
+};
+
 /** Autogenerated return type of UserAdd */
 export type UserAddPayload = {
   __typename?: 'UserAddPayload';

+ 6 - 0
app/graphql/gql/types/user_type.rb

@@ -20,6 +20,8 @@ module Gql::Types
     scoped_fields do
       belongs_to :organization, Gql::Types::OrganizationType
 
+      field :secondary_organizations, Gql::Types::OrganizationType.connection_type
+
       field :firstname, String
       field :lastname, String
       field :fullname, String
@@ -51,5 +53,9 @@ module Gql::Types
     # field :city, String
     # field :country, String
     # field :address, String
+
+    def secondary_organizations
+      @object.organizations
+    end
   end
 end

+ 12 - 3
spec/graphql/gql/queries/current_user_spec.rb

@@ -5,8 +5,9 @@ require 'rails_helper'
 RSpec.describe Gql::Queries::CurrentUser, type: :graphql do
 
   context 'when fetching user information' do
-    let(:organization) { create(:organization) }
-    let(:agent)        { create(:agent, department: 'TestDepartment', organization: organization) }
+    let(:organization)   { create(:organization) }
+    let(:secondary_orgs) { create_list(:organization, 2) }
+    let(:agent)          { create(:agent, department: 'TestDepartment', organization: organization, organizations: secondary_orgs) }
     let(:query) do
       <<~QUERY
         query currentUser {
@@ -24,6 +25,13 @@ RSpec.describe Gql::Queries::CurrentUser, type: :graphql do
             organization {
               name
             }
+            secondaryOrganizations {
+              edges {
+                node {
+                  name
+                }
+              }
+            }
             permissions {
               names
             }
@@ -46,8 +54,9 @@ RSpec.describe Gql::Queries::CurrentUser, type: :graphql do
         expect(oas.find { |oa| oa['attribute']['name'].eql?('department') }['value']).to eq('TestDepartment')
       end
 
-      it 'has data for Organization' do
+      it 'has data for primary and secondary organizations', :aggregate_failures do
         expect(gql.result.data['organization']).to include('name' => organization.name)
+        expect(gql.result.nodes('secondaryOrganizations')).to eq(secondary_orgs.map { |o| { 'name' => o.name } })
       end
 
       it 'has permission data' do

+ 8 - 3
spec/support/graphql.rb

@@ -114,11 +114,16 @@ module ZammadSpecSupportGraphql
       #
       #   expect(gql.response.nodes.first).to include(...)
       #
-      def nodes
+      # Also can operate on a subentry in the hash rather than the top level.
+      #
+      #   expect(gql.response.nodes('first_level', 'second_level').first).to include(...)
+      #
+      def nodes(*subkeys)
+        content = data.dig(*subkeys, 'edges')
         assert('GraphQL result contains node entries') do
-          !data['edges'].nil?
+          !content.nil?
         end
-        data['edges'].map { |edge| edge['node'] }
+        content.map { |edge| edge['node'] }
       end
 
       #