From 89ce49a58678ad4fccb3fdd6e5473515c334bd4e Mon Sep 17 00:00:00 2001 From: Riku Rouvila Date: Mon, 25 Nov 2024 11:00:25 +0200 Subject: [PATCH] Events v2: Skeleton GraphQL resolvers for basic operations (#8033) Co-authored-by: Markus --- .github/workflows/lint-and-test.yml | 41 +- docker-compose.yml | 13 + packages/client/Dockerfile | 4 + packages/client/Dockerfile.dockerignore | 3 +- packages/client/package.json | 1 + packages/commons/src/authentication.ts | 5 + packages/commons/src/events/Action.ts | 33 +- packages/commons/src/events/Event.ts | 20 +- packages/events/src/index.test.ts | 45 +- packages/events/src/index.ts | 26 +- packages/events/src/router.ts | 48 +- packages/events/src/service/events.ts | 27 +- packages/events/tsconfig.json | 4 +- packages/gateway/Dockerfile | 3 + packages/gateway/Dockerfile.dockerignore | 1 + packages/gateway/package.json | 5 +- packages/gateway/src/environment.ts | 1 + .../bookmarkAdvancedSearch/schema.graphql | 4 +- packages/gateway/src/graphql/common.graphql | 2 +- packages/gateway/src/graphql/config.ts | 4 + packages/gateway/src/graphql/index.graphql | 2 + packages/gateway/src/graphql/schema.d.ts | 672 +++++++++++++++++- packages/gateway/src/graphql/schema.graphql | 136 +++- packages/gateway/src/v2-events/.eslintrc.js | 7 +- .../src/v2-events/events/root-resolvers.ts | 70 ++ .../src/v2-events/events/schema.graphql | 149 ++++ .../src/v2-events/events/type-resolvers.ts | 29 + packages/gateway/tsconfig.json | 3 +- yarn.lock | 5 + 29 files changed, 1256 insertions(+), 107 deletions(-) create mode 100644 packages/gateway/src/v2-events/events/root-resolvers.ts create mode 100644 packages/gateway/src/v2-events/events/schema.graphql create mode 100644 packages/gateway/src/v2-events/events/type-resolvers.ts diff --git a/.github/workflows/lint-and-test.yml b/.github/workflows/lint-and-test.yml index 8eaea31a5c9..4b538231ad9 100644 --- a/.github/workflows/lint-and-test.yml +++ b/.github/workflows/lint-and-test.yml @@ -85,17 +85,36 @@ jobs: with: node-version-file: .nvmrc + - name: Extract dependencies for ${{ matrix.package }} + if: steps.check-scripts.outputs.skip != 'true' + id: extract-dependencies + run: | + DEPENDENCIES=$(node -e " + const { execSync } = require('child_process'); + const output = execSync('yarn --silent workspaces info', { encoding: 'utf-8' }); + const json = JSON.parse(output.replaceAll('@opencrvs', 'packages')); + + const getDependencies = (pkg) => + json[pkg].workspaceDependencies.concat( + json[pkg].workspaceDependencies.flatMap(getDependencies) + ); + + console.log( + getDependencies('${{ matrix.package }}').join(' ') + ); + ") + echo "DEPENDENCIES=${DEPENDENCIES}" >> $GITHUB_ENV + echo "Found dependencies: $DEPENDENCIES" + - name: Remove other package directories if: steps.check-scripts.outputs.skip != 'true' run: | for dir in packages/*; do - if [ "$dir" != "${{ matrix.package }}" ] && [ "$dir" != "packages/commons" ] && [ "$dir" != "packages/components" ]; then - if [ "${{ matrix.package }}" == "packages/client" ] && [ "$dir" == "packages/gateway" ] ; then - echo "Skipping $dir" - else - echo "Removing $dir" - rm -rf "$dir" - fi + if echo "${{ matrix.package }} $DEPENDENCIES" | grep -q -w "$dir"; then + echo "Skipping $dir" + else + echo "Removing $dir" + rm -rf "$dir" fi done @@ -119,15 +138,13 @@ jobs: # TODO: Move out of the matrix to be built once and shared - name: Build common package - if: steps.check-scripts.outputs.skip != 'true' + if: steps.check-scripts.outputs.skip != 'true' && contains(env.DEPENDENCIES, 'packages/commons') run: cd packages/commons && yarn build - name: Build components client and login - if: steps.check-scripts.outputs.skip != 'true' + if: steps.check-scripts.outputs.skip != 'true' && contains(env.DEPENDENCIES, 'packages/components') run: | - if [[ "${{ matrix.package }}" == "packages/client" || "${{ matrix.package }}" == "packages/login" ]]; then - cd packages/components && yarn build - fi + cd packages/components && yarn build # TODO: should run parallel to unit tests as can take as much as unit tests - name: Run linting diff --git a/docker-compose.yml b/docker-compose.yml index 8e4773ce027..9920f4f68f2 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -73,6 +73,7 @@ services: - CONFIG_SMS_CODE_EXPIRY_SECONDS=600 - CONFIG_TOKEN_EXPIRY_SECONDS=604800 - NODE_ENV=development + - EVENTS_URL=http://events:5555/ - FHIR_URL=http://hearth:3447/fhir - USER_MANAGEMENT_URL=http://user-mgnt:3030/ - SEARCH_URL=http://search:9090/ @@ -86,6 +87,18 @@ services: - CHECK_INVALID_TOKEN=true - MINIO_BUCKET=ocrvs - DOCUMENTS_URL=http://documents:9050 + events: + image: opencrvs/ocrvs-events:${VERSION} + #platform: linux/amd64 + build: + context: . + dockerfile: ./packages/events/Dockerfile + restart: unless-stopped + depends_on: + - base + environment: + - MONGO_URL=mongodb://mongo1/events + # User facing services workflow: image: opencrvs/ocrvs-workflow:${VERSION} diff --git a/packages/client/Dockerfile b/packages/client/Dockerfile index d63d27950ec..205042cb324 100644 --- a/packages/client/Dockerfile +++ b/packages/client/Dockerfile @@ -3,8 +3,12 @@ FROM opencrvs/ocrvs-base:${BRANCH} USER node +COPY --chown=node:node packages/gateway /app/packages/gateway +COPY --chown=node:node packages/events /app/packages/events + WORKDIR /app/packages/components COPY --chown=node:node packages/components /app/packages/components + RUN yarn install --frozen-lockfile && yarn build ENV CONTENT_SECURITY_POLICY_WILDCARD "{{CONTENT_SECURITY_POLICY_WILDCARD}}" ENV COUNTRY_CONFIG_URL_INTERNAL "{{COUNTRY_CONFIG_URL_INTERNAL}}" diff --git a/packages/client/Dockerfile.dockerignore b/packages/client/Dockerfile.dockerignore index 042ff4d295a..2e4079799a3 100644 --- a/packages/client/Dockerfile.dockerignore +++ b/packages/client/Dockerfile.dockerignore @@ -20,4 +20,5 @@ packages/* !packages/commons !packages/components !packages/client -!packages/gateway \ No newline at end of file +!packages/gateway +!packages/events \ No newline at end of file diff --git a/packages/client/package.json b/packages/client/package.json index e0be658b4ec..db986d963e9 100644 --- a/packages/client/package.json +++ b/packages/client/package.json @@ -108,6 +108,7 @@ "xregexp": "^4.2.0" }, "devDependencies": { + "@opencrvs/gateway": "^1.5.0", "@graphql-codegen/add": "^5.0.0", "@graphql-codegen/cli": "^5.0.0", "@graphql-codegen/introspection": "^3.0.0", diff --git a/packages/commons/src/authentication.ts b/packages/commons/src/authentication.ts index 1dd7514a79e..65d5b2c618a 100644 --- a/packages/commons/src/authentication.ts +++ b/packages/commons/src/authentication.ts @@ -113,3 +113,8 @@ export const getTokenPayload = (token: string): ITokenPayload => { } return decoded } + +export const getUserId = (token: string): string => { + const tokenPayload = getTokenPayload(token.split(' ')[1]) + return tokenPayload.sub +} diff --git a/packages/commons/src/events/Action.ts b/packages/commons/src/events/Action.ts index 15902b29b43..c9007ad9903 100644 --- a/packages/commons/src/events/Action.ts +++ b/packages/commons/src/events/Action.ts @@ -42,7 +42,6 @@ export const ActionConfig = z.object({ }) export const ActionInputBase = z.object({ - type: z.enum(actionTypes as NonEmptyArray), fields: z.array( z.object({ id: z.string(), @@ -62,18 +61,28 @@ export const ActionInputBase = z.object({ ) }) -export const ActionInput = z.union([ - ActionInputBase.extend({ - type: z.enum([ActionType.CREATE]) - }), - ActionInputBase.extend({ - type: z.enum([ActionType.REGISTER]), - identifiers: z.object({ - trackingId: z.string(), - registrationNumber: z.string() - }) +export const CreateActionInput = ActionInputBase.extend({}) +export const NotifyActionInput = ActionInputBase.extend({}) +export const DeclareActionInput = ActionInputBase.extend({}) +export const RegisterActionInput = ActionInputBase.extend({ + identifiers: z.object({ + trackingId: z.string(), + registrationNumber: z.string() }) -]) +}) + +export const ActionInput = z + .union([ + CreateActionInput.extend({ type: z.enum([ActionType.CREATE]) }), + NotifyActionInput.extend({ type: z.enum([ActionType.NOTIFY]) }), + DeclareActionInput.extend({ type: z.enum([ActionType.DECLARE]) }), + RegisterActionInput.extend({ type: z.enum([ActionType.REGISTER]) }) + ]) + .and( + z.object({ + createdBy: z.string() + }) + ) export type ActionInput = z.infer diff --git a/packages/commons/src/events/Event.ts b/packages/commons/src/events/Event.ts index 078e61a117f..61f25f085f1 100644 --- a/packages/commons/src/events/Event.ts +++ b/packages/commons/src/events/Event.ts @@ -16,25 +16,7 @@ import { Label, Summary } from './utils' * A subset of an event. Describes fields that can be sent to the system with the intention of either creating or mutating a an event */ export const EventInput = z.object({ - type: z.string(), - fields: z.array( - z.object({ - id: z.string(), - value: z.union([ - z.string(), - z.number(), - z.array( - // @TODO: Check if we could make this stricter - z.object({ - optionValues: z.array(z.string()), - type: z.string(), - data: z.string(), - fileSize: z.number() - }) - ) - ]) - }) - ) + type: z.string() }) export type EventInput = z.infer diff --git a/packages/events/src/index.test.ts b/packages/events/src/index.test.ts index b4404f50cd3..c03357322c9 100644 --- a/packages/events/src/index.test.ts +++ b/packages/events/src/index.test.ts @@ -11,11 +11,10 @@ import { vi } from 'vitest' import { appRouter, t } from './router' import { - setupServer, getClient, - resetServer + resetServer, + setupServer } from './storage/__mocks__/mongodb' -import { ActionType } from '@opencrvs/commons' const { createCallerFactory } = t @@ -31,7 +30,9 @@ afterEach(async () => { function createClient() { const createCaller = createCallerFactory(appRouter) - const caller = createCaller({}) + const caller = createCaller({ + user: { id: '1' } + }) return caller } @@ -39,7 +40,7 @@ const client = createClient() test('event can be created and fetched', async () => { const event = await client.event.create({ transactionId: '1', - event: { type: 'birth', fields: [] } + event: { type: 'birth' } }) const fetchedEvent = await client.event.get(event.id) @@ -52,12 +53,12 @@ test('creating an event is an idempotent operation', async () => { await client.event.create({ transactionId: '1', - event: { type: 'birth', fields: [] } + event: { type: 'birth' } }) await client.event.create({ transactionId: '1', - event: { type: 'birth', fields: [] } + event: { type: 'birth' } }) expect(await db.collection('events').find().toArray()).toHaveLength(1) @@ -66,13 +67,12 @@ test('creating an event is an idempotent operation', async () => { test('stored events can be modified', async () => { const originalEvent = await client.event.create({ transactionId: '1', - event: { type: 'birth', fields: [] } + event: { type: 'birth' } }) const event = await client.event.patch({ id: originalEvent.id, - type: 'death', - fields: [] + type: 'death' }) expect(event.updatedAt).not.toBe(originalEvent.updatedAt) @@ -82,28 +82,19 @@ test('stored events can be modified', async () => { test('actions can be added to created events', async () => { const originalEvent = await client.event.create({ transactionId: '1', - event: { type: 'birth', fields: [] } + event: { type: 'birth' } }) - const event = await client.event.actions.create({ + const event = await client.event.actions.declare({ eventId: originalEvent.id, + transactionId: '2', action: { - type: ActionType.REGISTER, - fields: [], - identifiers: { - trackingId: '123', - registrationNumber: '456' - } + fields: [] } }) - expect(event.actions).toContainEqual( - expect.objectContaining({ - type: ActionType.REGISTER, - identifiers: { - trackingId: '123', - registrationNumber: '456' - } - }) - ) + expect(event.actions).toEqual([ + expect.objectContaining({ type: 'CREATE' }), + expect.objectContaining({ type: 'DECLARE' }) + ]) }) diff --git a/packages/events/src/index.ts b/packages/events/src/index.ts index 94bcad50752..0d949daddad 100644 --- a/packages/events/src/index.ts +++ b/packages/events/src/index.ts @@ -17,9 +17,33 @@ require('app-module-path').addPath(require('path').join(__dirname, '../')) import { appRouter } from './router' import { createHTTPServer } from '@trpc/server/adapters/standalone' +import { getUserId } from '@opencrvs/commons/authentication' +import { TRPCError } from '@trpc/server' const server = createHTTPServer({ - router: appRouter + router: appRouter, + createContext: function createContext(opts) { + const token = opts.req.headers.authorization + if (!token) { + throw new TRPCError({ + code: 'UNAUTHORIZED' + }) + } + + const userId = getUserId(token) + + if (!userId) { + throw new TRPCError({ + code: 'UNAUTHORIZED' + }) + } + + return { + user: { + id: userId + } + } + } }) server.listen(5555) diff --git a/packages/events/src/router.ts b/packages/events/src/router.ts index 2333c7891e6..a333af857d5 100644 --- a/packages/events/src/router.ts +++ b/packages/events/src/router.ts @@ -9,6 +9,11 @@ * Copyright (C) The OpenCRVS Authors located at https://github.com/opencrvs/opencrvs-core/blob/master/AUTHORS. */ +import { + DeclareActionInput, + EventInput, + NotifyActionInput +} from '@opencrvs/commons' import { initTRPC } from '@trpc/server' import superjson from 'superjson' import { z } from 'zod' @@ -20,9 +25,16 @@ import { getEventById, patchEvent } from './service/events' -import { ActionInput, EventInput } from '@opencrvs/commons' -export const t = initTRPC.create({ +const ContextSchema = z.object({ + user: z.object({ + id: z.string() + }) +}) + +type Context = z.infer + +export const t = initTRPC.context().create({ transformer: superjson }) @@ -44,7 +56,11 @@ export const appRouter = router({ }) ) .mutation(async (options) => { - return createEvent(options.input.event, options.input.transactionId) + return createEvent( + options.input.event, + options.ctx.user.id, + options.input.transactionId + ) }), patch: publicProcedure.input(EventInputWithId).mutation(async (options) => { return patchEvent(options.input) @@ -53,15 +69,35 @@ export const appRouter = router({ return getEventById(input) }), actions: router({ - create: publicProcedure + notify: publicProcedure + .input( + z.object({ + eventId: z.string(), + transactionId: z.string(), + action: NotifyActionInput + }) + ) + .mutation(async (options) => { + return addAction(options.input.eventId, { + ...options.input.action, + type: 'NOTIFY', + createdBy: options.ctx.user.id + }) + }), + declare: publicProcedure .input( z.object({ eventId: z.string(), - action: ActionInput + transactionId: z.string(), + action: DeclareActionInput }) ) .mutation(async (options) => { - return addAction(options.input.eventId, options.input.action) + return addAction(options.input.eventId, { + ...options.input.action, + type: 'DECLARE', + createdBy: options.ctx.user.id + }) }) }) }) diff --git a/packages/events/src/service/events.ts b/packages/events/src/service/events.ts index 44c67083321..5bed77aeb73 100644 --- a/packages/events/src/service/events.ts +++ b/packages/events/src/service/events.ts @@ -19,10 +19,6 @@ import { } from '@opencrvs/commons' import { z } from 'zod' -export const EventInputWithId = EventInput.extend({ - id: z.string() -}) - const EventWithTransactionId = Event.extend({ transactionId: z.string() }) @@ -55,6 +51,7 @@ export async function getEventById(id: string) { export async function createEvent( eventInput: z.infer, + createdBy: string, transactionId: string ): Promise { const existingEvent = await getEventByTransactionId(transactionId) @@ -79,7 +76,7 @@ export async function createEvent( { type: ActionType.CREATE, createdAt: now, - createdBy: '123-123-123', + createdBy, fields: [] } ] @@ -90,11 +87,9 @@ export async function createEvent( export async function addAction(eventId: string, action: ActionInput) { const db = await getClient() - const collection = db.collection('events') - const now = new Date() - await collection.updateOne( + await db.collection('events').updateOne( { id: eventId }, @@ -102,8 +97,7 @@ export async function addAction(eventId: string, action: ActionInput) { $push: { actions: { ...action, - createdAt: now, - createdBy: '123-123-123' + createdAt: now } } } @@ -112,9 +106,13 @@ export async function addAction(eventId: string, action: ActionInput) { return getEventById(eventId) } -export async function patchEvent( - event: z.infer -): Promise { +export const EventInputWithId = EventInput.extend({ + id: z.string() +}) + +export type EventInputWithId = z.infer + +export async function patchEvent(event: EventInputWithId): Promise { const existingEvent = await getEventById(event.id) if (!existingEvent) { @@ -122,8 +120,7 @@ export async function patchEvent( } const db = await getClient() - const collection = - db.collection>('events') + const collection = db.collection('events') const now = new Date() diff --git a/packages/events/tsconfig.json b/packages/events/tsconfig.json index b2b2050756c..2c51ebffab2 100644 --- a/packages/events/tsconfig.json +++ b/packages/events/tsconfig.json @@ -4,12 +4,12 @@ "strict": true, "paths": { "@events/*": ["./*"] }, "target": "es6", - "module": "commonjs", + "module": "node16", "outDir": "build/dist", "sourceMap": true, "allowSyntheticDefaultImports": true, "skipLibCheck": true, - "moduleResolution": "node", + "moduleResolution": "node16", "rootDir": ".", "lib": ["esnext.asynciterable", "es6", "es2017"], "forceConsistentCasingInFileNames": true, diff --git a/packages/gateway/Dockerfile b/packages/gateway/Dockerfile index 13be00a9988..0e47393ac9a 100644 --- a/packages/gateway/Dockerfile +++ b/packages/gateway/Dockerfile @@ -3,8 +3,11 @@ FROM opencrvs/ocrvs-base:${BRANCH} USER node +COPY --chown=node:node packages/events /app/packages/events + WORKDIR /app/packages/gateway COPY --chown=node:node packages/gateway/*.json /app/packages/gateway/ + RUN yarn install --frozen-lockfile COPY --chown=node:node packages/gateway /app/packages/gateway RUN yarn build diff --git a/packages/gateway/Dockerfile.dockerignore b/packages/gateway/Dockerfile.dockerignore index 5eca91c5874..15e78bf74a7 100644 --- a/packages/gateway/Dockerfile.dockerignore +++ b/packages/gateway/Dockerfile.dockerignore @@ -19,3 +19,4 @@ grafana packages/ !packages/commons !packages/gateway +!packages/events diff --git a/packages/gateway/package.json b/packages/gateway/package.json index 436bc09ea8c..45cd3e76548 100644 --- a/packages/gateway/package.json +++ b/packages/gateway/package.json @@ -27,12 +27,15 @@ "@graphql-tools/utils": "^9.2.1", "@hapi/h2o2": "^9.1.0", "@hapi/hapi": "^20.0.1", - "@opencrvs/commons": "^1.3.0", + "@opencrvs/events": "^1.5.0", + "@opencrvs/commons": "^1.5.0", + "@trpc/client": "^11.0.0-rc.532", "@types/archiver": "^3.0.0", "@types/flat": "^0.0.28", "@types/uuid-validate": "^0.0.3", "apollo-datasource-rest": "^3.7.0", "apollo-server-hapi": "^3.5.0", + "superjson": "1.9.0-0", "app-module-path": "^2.2.0", "archiver": "^3.1.1", "bunyan": "^1.8.12", diff --git a/packages/gateway/src/environment.ts b/packages/gateway/src/environment.ts index 7fdc7179d83..d8030ffdc12 100644 --- a/packages/gateway/src/environment.ts +++ b/packages/gateway/src/environment.ts @@ -29,6 +29,7 @@ export const env = cleanEnv(process.env, { APPLICATION_CONFIG_URL: url({ devDefault: 'http://localhost:2021/' }), NOTIFICATION_URL: url({ devDefault: 'http://localhost:2020/' }), WORKFLOW_URL: url({ devDefault: 'http://localhost:5050/' }), + EVENTS_URL: url({ devDefault: 'http://localhost:5555/' }), COUNTRY_CONFIG_URL: url({ devDefault: 'http://localhost:3040' }), DOCUMENTS_URL: url({ devDefault: 'http://localhost:9050' }), DISABLE_RATE_LIMIT: bool({ diff --git a/packages/gateway/src/features/bookmarkAdvancedSearch/schema.graphql b/packages/gateway/src/features/bookmarkAdvancedSearch/schema.graphql index 3e02a0ee849..3a7e5b66c95 100644 --- a/packages/gateway/src/features/bookmarkAdvancedSearch/schema.graphql +++ b/packages/gateway/src/features/bookmarkAdvancedSearch/schema.graphql @@ -14,7 +14,7 @@ type BookmarkedSeachItem { } type AdvancedSeachParameters { - event: Event + event: EventType name: String registrationStatuses: [String] dateOfEvent: String @@ -80,7 +80,7 @@ input BookmarkSearchInput { } input AdvancedSearchParametersInput { - event: Event + event: EventType name: String registrationStatuses: [String] dateOfEvent: String diff --git a/packages/gateway/src/graphql/common.graphql b/packages/gateway/src/graphql/common.graphql index 7b8c4810f25..d0231b09781 100644 --- a/packages/gateway/src/graphql/common.graphql +++ b/packages/gateway/src/graphql/common.graphql @@ -31,7 +31,7 @@ type HumanName { # -> HumanName # Although the recommended way is use ALL_CAPS but keeping it lowercase # makes it a lot more easier to use in client -enum Event { +enum EventType { birth death marriage diff --git a/packages/gateway/src/graphql/config.ts b/packages/gateway/src/graphql/config.ts index c0d94db2c87..702884cb91e 100644 --- a/packages/gateway/src/graphql/config.ts +++ b/packages/gateway/src/graphql/config.ts @@ -17,6 +17,8 @@ import { GraphQLError } from 'graphql' +import { resolvers as eventsV2Resolvers } from '@gateway/v2-events/events/root-resolvers' +import { eventResolvers as eventsV2TypeResolvers } from '@gateway/v2-events/events/type-resolvers' import { resolvers as locationRootResolvers } from '@gateway/features/location/root-resolvers' import { resolvers as metricsRootResolvers } from '@gateway/features/metrics/root-resolvers' import { resolvers as integrationResolver } from '@gateway/features/systems/root-resolvers' @@ -67,6 +69,8 @@ interface IStringIndexSignatureInterface { type StringIndexed = T & IStringIndexSignatureInterface export const resolvers: StringIndexed = merge( + eventsV2Resolvers, + eventsV2TypeResolvers, notificationRootResolvers as IResolvers, registrationRootResolvers as IResolvers, locationRootResolvers as IResolvers, diff --git a/packages/gateway/src/graphql/index.graphql b/packages/gateway/src/graphql/index.graphql index f9f8634bfd4..4b9c623f486 100644 --- a/packages/gateway/src/graphql/index.graphql +++ b/packages/gateway/src/graphql/index.graphql @@ -19,6 +19,8 @@ # import Mutation.* from '../features/systems/schema.graphql' # import Query.* from '../features/systems/schema.graphql' # import Mutation from '../features/bookmarkAdvancedSearch/schema.graphql' +# import Mutation.* from '../v2-events/events/schema.graphql' +# import Query.* from '../v2-events/events/schema.graphql' # import * from 'common.graphql' # TODO diff --git a/packages/gateway/src/graphql/schema.d.ts b/packages/gateway/src/graphql/schema.d.ts index 36e768d82eb..a583dfaf43c 100644 --- a/packages/gateway/src/graphql/schema.d.ts +++ b/packages/gateway/src/graphql/schema.d.ts @@ -50,6 +50,7 @@ export interface GQLQuery { getEventsWithProgress?: GQLEventProgressResultSet getSystemRoles?: Array fetchSystem?: GQLSystem + getEvent: GQLEvent } export interface GQLMutation { @@ -106,6 +107,18 @@ export interface GQLMutation { deleteSystem?: GQLSystem bookmarkAdvancedSearch?: GQLBookMarkedSearches removeBookmarkedAdvancedSearch?: GQLBookMarkedSearches + createEvent: GQLEvent + notifyEvent: GQLEvent + declareEvent: GQLEvent + registerEvent: GQLEvent + certifyEvent: GQLEvent + issueEvent: GQLEvent + revokeEvent: GQLEvent + reinstateEvent: GQLEvent + revokeCorrectionEvent: GQLEvent + requestCorrectionEvent: GQLEvent + approveCorrectionEvent: GQLEvent + rejectCorrectionEvent: GQLEvent } export interface GQLDummy { @@ -378,7 +391,7 @@ export interface GQLEventSearchResultSet { } export interface GQLAdvancedSearchParametersInput { - event?: GQLEvent + event?: GQLEventType name?: string registrationStatuses?: Array dateOfEvent?: string @@ -490,6 +503,14 @@ export interface GQLSystem { settings?: GQLSystemSettings } +export interface GQLEvent { + type: string + id: string + createdAt: GQLDateTime + updatedAt: GQLDateTime + actions: Array +} + export interface GQLCorrectionInput { requester: string requesterOther?: string @@ -662,6 +683,54 @@ export interface GQLRemoveBookmarkedSeachInput { searchId: string } +export interface GQLEventInput { + type: string +} + +export interface GQLNotifyActionInput { + fields: Array +} + +export interface GQLDeclareActionInput { + fields: Array +} + +export interface GQLRegisterActionInput { + fields: Array +} + +export interface GQLCertifyActionInput { + fields: Array +} + +export interface GQLIssueActionInput { + fields: Array +} + +export interface GQLRevokeActionInput { + fields: Array +} + +export interface GQLReinstateActionInput { + fields: Array +} + +export interface GQLRevokeCorrectionActionInput { + fields: Array +} + +export interface GQLRequestCorrectionActionInput { + fields: Array +} + +export interface GQLApproveCorrectionActionInput { + fields: Array +} + +export interface GQLRejectCorrectionActionInput { + fields: Array +} + export type GQLMap = any export interface GQLRegistration { @@ -979,7 +1048,7 @@ export interface GQLEventSearchSetNameMap { MarriageEventSearchSet: GQLMarriageEventSearchSet } -export const enum GQLEvent { +export const enum GQLEventType { birth = 'birth', death = 'death', marriage = 'marriage' @@ -1022,6 +1091,29 @@ export interface GQLSystemSettings { openIdProviderClaims?: string } +export type GQLDateTime = any + +export type GQLAction = + | GQLCreateAction + | GQLRegisterAction + | GQLNotifyAction + | GQLDeclareAction + +/** Use this to resolve union type Action */ +export type GQLPossibleActionTypeNames = + | 'CreateAction' + | 'RegisterAction' + | 'NotifyAction' + | 'DeclareAction' + +export interface GQLActionNameMap { + Action: GQLAction + CreateAction: GQLCreateAction + RegisterAction: GQLRegisterAction + NotifyAction: GQLNotifyAction + DeclareAction: GQLDeclareAction +} + export interface GQLAttachmentInput { _fhirID?: string contentType?: string @@ -1218,6 +1310,11 @@ export interface GQLWebhookInput { permissions: Array } +export interface GQLFieldInput { + id: string + value: GQLFieldValue +} + export interface GQLAssignmentData { practitionerId?: string firstName?: string @@ -1310,7 +1407,7 @@ export interface GQLRoleLabel { } export interface GQLAdvancedSeachParameters { - event?: GQLEvent + event?: GQLEventType name?: string registrationStatuses?: Array dateOfEvent?: string @@ -1500,6 +1597,36 @@ export interface GQLWebhookPermission { permissions: Array } +export interface GQLCreateAction { + type: string + createdAt: GQLDateTime + createdBy: string + fields: Array +} + +export interface GQLRegisterAction { + type: string + createdAt: GQLDateTime + createdBy: string + fields: Array + identifiers: GQLIdentifiers +} + +export interface GQLNotifyAction { + type: string + createdAt: GQLDateTime + createdBy: string + fields: Array +} + +export interface GQLDeclareAction { + type: string + createdAt: GQLDateTime + createdBy: string + fields: Array + identifiers: GQLIdentifiers +} + export const enum GQLAttachmentInputStatus { approved = 'approved', validated = 'validated', @@ -1621,6 +1748,16 @@ export interface GQLAdditionalIdWithCompositionId { trackingId: string } +export interface GQLField { + id: string + value: GQLFieldValue +} + +export interface GQLIdentifiers { + trackingId: string + registrationNumber: string +} + export const enum GQLTelecomSystem { other = 'other', phone = 'phone', @@ -1721,6 +1858,7 @@ export interface GQLResolver { EventProgressResultSet?: GQLEventProgressResultSetTypeResolver SystemRole?: GQLSystemRoleTypeResolver System?: GQLSystemTypeResolver + Event?: GQLEventTypeResolver CreatedIds?: GQLCreatedIdsTypeResolver Reinstated?: GQLReinstatedTypeResolver Avatar?: GQLAvatarTypeResolver @@ -1764,6 +1902,11 @@ export interface GQLResolver { EventProgressSet?: GQLEventProgressSetTypeResolver SystemSettings?: GQLSystemSettingsTypeResolver + DateTime?: GraphQLScalarType + Action?: { + __resolveType: GQLActionTypeResolver + } + AssignmentData?: GQLAssignmentDataTypeResolver RegWorkflow?: GQLRegWorkflowTypeResolver Certificate?: GQLCertificateTypeResolver @@ -1787,12 +1930,18 @@ export interface GQLResolver { MarriageEventSearchSet?: GQLMarriageEventSearchSetTypeResolver EventProgressData?: GQLEventProgressDataTypeResolver WebhookPermission?: GQLWebhookPermissionTypeResolver + CreateAction?: GQLCreateActionTypeResolver + RegisterAction?: GQLRegisterActionTypeResolver + NotifyAction?: GQLNotifyActionTypeResolver + DeclareAction?: GQLDeclareActionTypeResolver FieldValue?: GraphQLScalarType AuditLogItemBase?: { __resolveType: GQLAuditLogItemBaseTypeResolver } AdditionalIdWithCompositionId?: GQLAdditionalIdWithCompositionIdTypeResolver + Field?: GQLFieldTypeResolver + Identifiers?: GQLIdentifiersTypeResolver } export interface GQLQueryTypeResolver { sendNotificationToAllUsers?: QueryToSendNotificationToAllUsersResolver @@ -1832,6 +1981,7 @@ export interface GQLQueryTypeResolver { getEventsWithProgress?: QueryToGetEventsWithProgressResolver getSystemRoles?: QueryToGetSystemRolesResolver fetchSystem?: QueryToFetchSystemResolver + getEvent?: QueryToGetEventResolver } export interface QueryToSendNotificationToAllUsersArgs { @@ -2433,6 +2583,18 @@ export interface QueryToFetchSystemResolver { ): TResult } +export interface QueryToGetEventArgs { + eventId: string +} +export interface QueryToGetEventResolver { + ( + parent: TParent, + args: QueryToGetEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + export interface GQLMutationTypeResolver { requestRegistrationCorrection?: MutationToRequestRegistrationCorrectionResolver rejectRegistrationCorrection?: MutationToRejectRegistrationCorrectionResolver @@ -2487,6 +2649,18 @@ export interface GQLMutationTypeResolver { deleteSystem?: MutationToDeleteSystemResolver bookmarkAdvancedSearch?: MutationToBookmarkAdvancedSearchResolver removeBookmarkedAdvancedSearch?: MutationToRemoveBookmarkedAdvancedSearchResolver + createEvent?: MutationToCreateEventResolver + notifyEvent?: MutationToNotifyEventResolver + declareEvent?: MutationToDeclareEventResolver + registerEvent?: MutationToRegisterEventResolver + certifyEvent?: MutationToCertifyEventResolver + issueEvent?: MutationToIssueEventResolver + revokeEvent?: MutationToRevokeEventResolver + reinstateEvent?: MutationToReinstateEventResolver + revokeCorrectionEvent?: MutationToRevokeCorrectionEventResolver + requestCorrectionEvent?: MutationToRequestCorrectionEventResolver + approveCorrectionEvent?: MutationToApproveCorrectionEventResolver + rejectCorrectionEvent?: MutationToRejectCorrectionEventResolver } export interface MutationToRequestRegistrationCorrectionArgs { @@ -3307,6 +3481,176 @@ export interface MutationToRemoveBookmarkedAdvancedSearchResolver< ): TResult } +export interface MutationToCreateEventArgs { + event: GQLEventInput +} +export interface MutationToCreateEventResolver { + ( + parent: TParent, + args: MutationToCreateEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToNotifyEventArgs { + eventId: string + input: GQLNotifyActionInput +} +export interface MutationToNotifyEventResolver { + ( + parent: TParent, + args: MutationToNotifyEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToDeclareEventArgs { + eventId: string + input: GQLDeclareActionInput +} +export interface MutationToDeclareEventResolver { + ( + parent: TParent, + args: MutationToDeclareEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToRegisterEventArgs { + eventId: string + input: GQLRegisterActionInput +} +export interface MutationToRegisterEventResolver { + ( + parent: TParent, + args: MutationToRegisterEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToCertifyEventArgs { + eventId: string + input: GQLCertifyActionInput +} +export interface MutationToCertifyEventResolver { + ( + parent: TParent, + args: MutationToCertifyEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToIssueEventArgs { + eventId: string + input: GQLIssueActionInput +} +export interface MutationToIssueEventResolver { + ( + parent: TParent, + args: MutationToIssueEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToRevokeEventArgs { + eventId: string + input: GQLRevokeActionInput +} +export interface MutationToRevokeEventResolver { + ( + parent: TParent, + args: MutationToRevokeEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToReinstateEventArgs { + eventId: string + input: GQLReinstateActionInput +} +export interface MutationToReinstateEventResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: MutationToReinstateEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToRevokeCorrectionEventArgs { + eventId: string + input: GQLRevokeCorrectionActionInput +} +export interface MutationToRevokeCorrectionEventResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: MutationToRevokeCorrectionEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToRequestCorrectionEventArgs { + eventId: string + input: GQLRequestCorrectionActionInput +} +export interface MutationToRequestCorrectionEventResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: MutationToRequestCorrectionEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToApproveCorrectionEventArgs { + eventId: string + input: GQLApproveCorrectionActionInput +} +export interface MutationToApproveCorrectionEventResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: MutationToApproveCorrectionEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface MutationToRejectCorrectionEventArgs { + eventId: string + input: GQLRejectCorrectionActionInput +} +export interface MutationToRejectCorrectionEventResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: MutationToRejectCorrectionEventArgs, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + export interface GQLDummyTypeResolver { dummy?: DummyToDummyResolver } @@ -5283,6 +5627,59 @@ export interface SystemToSettingsResolver { ): TResult } +export interface GQLEventTypeResolver { + type?: EventToTypeResolver + id?: EventToIdResolver + createdAt?: EventToCreatedAtResolver + updatedAt?: EventToUpdatedAtResolver + actions?: EventToActionsResolver +} + +export interface EventToTypeResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface EventToIdResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface EventToCreatedAtResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface EventToUpdatedAtResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface EventToActionsResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + export interface GQLCreatedIdsTypeResolver { compositionId?: CreatedIdsToCompositionIdResolver trackingId?: CreatedIdsToTrackingIdResolver @@ -7783,6 +8180,16 @@ export interface SystemSettingsToOpenIdProviderClaimsResolver< ): TResult } +export interface GQLActionTypeResolver { + (parent: TParent, context: Context, info: GraphQLResolveInfo): + | 'CreateAction' + | 'RegisterAction' + | 'NotifyAction' + | 'DeclareAction' + | Promise< + 'CreateAction' | 'RegisterAction' | 'NotifyAction' | 'DeclareAction' + > +} export interface GQLAssignmentDataTypeResolver { practitionerId?: AssignmentDataToPractitionerIdResolver firstName?: AssignmentDataToFirstNameResolver @@ -10223,6 +10630,216 @@ export interface WebhookPermissionToPermissionsResolver< ): TResult } +export interface GQLCreateActionTypeResolver { + type?: CreateActionToTypeResolver + createdAt?: CreateActionToCreatedAtResolver + createdBy?: CreateActionToCreatedByResolver + fields?: CreateActionToFieldsResolver +} + +export interface CreateActionToTypeResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface CreateActionToCreatedAtResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface CreateActionToCreatedByResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface CreateActionToFieldsResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface GQLRegisterActionTypeResolver { + type?: RegisterActionToTypeResolver + createdAt?: RegisterActionToCreatedAtResolver + createdBy?: RegisterActionToCreatedByResolver + fields?: RegisterActionToFieldsResolver + identifiers?: RegisterActionToIdentifiersResolver +} + +export interface RegisterActionToTypeResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface RegisterActionToCreatedAtResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface RegisterActionToCreatedByResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface RegisterActionToFieldsResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface RegisterActionToIdentifiersResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface GQLNotifyActionTypeResolver { + type?: NotifyActionToTypeResolver + createdAt?: NotifyActionToCreatedAtResolver + createdBy?: NotifyActionToCreatedByResolver + fields?: NotifyActionToFieldsResolver +} + +export interface NotifyActionToTypeResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface NotifyActionToCreatedAtResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface NotifyActionToCreatedByResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface NotifyActionToFieldsResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface GQLDeclareActionTypeResolver { + type?: DeclareActionToTypeResolver + createdAt?: DeclareActionToCreatedAtResolver + createdBy?: DeclareActionToCreatedByResolver + fields?: DeclareActionToFieldsResolver + identifiers?: DeclareActionToIdentifiersResolver +} + +export interface DeclareActionToTypeResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface DeclareActionToCreatedAtResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface DeclareActionToCreatedByResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface DeclareActionToFieldsResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface DeclareActionToIdentifiersResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + export interface GQLAuditLogItemBaseTypeResolver { (parent: TParent, context: Context, info: GraphQLResolveInfo): | 'UserAuditLogItemWithComposition' @@ -10257,3 +10874,52 @@ export interface AdditionalIdWithCompositionIdToTrackingIdResolver< info: GraphQLResolveInfo ): TResult } + +export interface GQLFieldTypeResolver { + id?: FieldToIdResolver + value?: FieldToValueResolver +} + +export interface FieldToIdResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface FieldToValueResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface GQLIdentifiersTypeResolver { + trackingId?: IdentifiersToTrackingIdResolver + registrationNumber?: IdentifiersToRegistrationNumberResolver +} + +export interface IdentifiersToTrackingIdResolver { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} + +export interface IdentifiersToRegistrationNumberResolver< + TParent = any, + TResult = any +> { + ( + parent: TParent, + args: {}, + context: Context, + info: GraphQLResolveInfo + ): TResult +} diff --git a/packages/gateway/src/graphql/schema.graphql b/packages/gateway/src/graphql/schema.graphql index 6aaf55c669e..15f047f2bd5 100644 --- a/packages/gateway/src/graphql/schema.graphql +++ b/packages/gateway/src/graphql/schema.graphql @@ -147,6 +147,7 @@ type Query { sortOrder: String ): [SystemRole!] fetchSystem(clientId: ID!): System + getEvent(eventId: ID!): Event! } type Mutation { @@ -264,6 +265,30 @@ type Mutation { removeBookmarkedAdvancedSearch( removeBookmarkedSearchInput: RemoveBookmarkedSeachInput! ): BookMarkedSearches + createEvent(event: EventInput!): Event! + notifyEvent(eventId: ID!, input: NotifyActionInput!): Event! + declareEvent(eventId: ID!, input: DeclareActionInput!): Event! + registerEvent(eventId: ID!, input: RegisterActionInput!): Event! + certifyEvent(eventId: ID!, input: CertifyActionInput!): Event! + issueEvent(eventId: ID!, input: IssueActionInput!): Event! + revokeEvent(eventId: ID!, input: RevokeActionInput!): Event! + reinstateEvent(eventId: ID!, input: ReinstateActionInput!): Event! + revokeCorrectionEvent( + eventId: ID! + input: RevokeCorrectionActionInput! + ): Event! + requestCorrectionEvent( + eventId: ID! + input: RequestCorrectionActionInput! + ): Event! + approveCorrectionEvent( + eventId: ID! + input: ApproveCorrectionActionInput! + ): Event! + rejectCorrectionEvent( + eventId: ID! + input: RejectCorrectionActionInput! + ): Event! } type Dummy { @@ -499,7 +524,7 @@ type EventSearchResultSet { } input AdvancedSearchParametersInput { - event: Event + event: EventType name: String registrationStatuses: [String] dateOfEvent: String @@ -611,6 +636,14 @@ type System { settings: SystemSettings } +type Event { + type: String! + id: String! + createdAt: DateTime! + updatedAt: DateTime! + actions: [Action!]! +} + input CorrectionInput { requester: String! requesterOther: String @@ -783,6 +816,54 @@ input RemoveBookmarkedSeachInput { searchId: String! } +input EventInput { + type: String! +} + +input NotifyActionInput { + fields: [FieldInput!]! +} + +input DeclareActionInput { + fields: [FieldInput!]! +} + +input RegisterActionInput { + fields: [FieldInput!]! +} + +input CertifyActionInput { + fields: [FieldInput!]! +} + +input IssueActionInput { + fields: [FieldInput!]! +} + +input RevokeActionInput { + fields: [FieldInput!]! +} + +input ReinstateActionInput { + fields: [FieldInput!]! +} + +input RevokeCorrectionActionInput { + fields: [FieldInput!]! +} + +input RequestCorrectionActionInput { + fields: [FieldInput!]! +} + +input ApproveCorrectionActionInput { + fields: [FieldInput!]! +} + +input RejectCorrectionActionInput { + fields: [FieldInput!]! +} + scalar Map type Registration { @@ -1076,7 +1157,7 @@ interface EventSearchSet { operationHistories: [OperationHistorySearchSet] } -enum Event { +enum EventType { birth death marriage @@ -1119,6 +1200,10 @@ type SystemSettings { openIdProviderClaims: String } +scalar DateTime + +union Action = CreateAction | RegisterAction | NotifyAction | DeclareAction + input AttachmentInput { _fhirID: ID contentType: String @@ -1315,6 +1400,11 @@ input WebhookInput { permissions: [String]! } +input FieldInput { + id: String! + value: FieldValue! +} + type AssignmentData { practitionerId: String firstName: String @@ -1407,7 +1497,7 @@ type RoleLabel { } type AdvancedSeachParameters { - event: Event + event: EventType name: String registrationStatuses: [String] dateOfEvent: String @@ -1596,6 +1686,36 @@ type WebhookPermission { permissions: [String!]! } +type CreateAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! +} + +type RegisterAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! + identifiers: Identifiers! +} + +type NotifyAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! +} + +type DeclareAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! + identifiers: Identifiers! +} + enum AttachmentInputStatus { approved validated @@ -1706,6 +1826,16 @@ type AdditionalIdWithCompositionId { trackingId: String! } +type Field { + id: String! + value: FieldValue! +} + +type Identifiers { + trackingId: String! + registrationNumber: String! +} + enum TelecomSystem { other phone diff --git a/packages/gateway/src/v2-events/.eslintrc.js b/packages/gateway/src/v2-events/.eslintrc.js index 67df70de721..dcc977e47ce 100644 --- a/packages/gateway/src/v2-events/.eslintrc.js +++ b/packages/gateway/src/v2-events/.eslintrc.js @@ -13,7 +13,12 @@ module.exports = { 'no-restricted-imports': [ 'error', { - patterns: ['@gateway/*', '!@gateway/v2-events'] + patterns: [ + '@gateway/*', + '!@gateway/v2-events', + '!@gateway/graphql', + '!@gateway/environment' + ] } ] } diff --git a/packages/gateway/src/v2-events/events/root-resolvers.ts b/packages/gateway/src/v2-events/events/root-resolvers.ts new file mode 100644 index 00000000000..b1b14a7b9e5 --- /dev/null +++ b/packages/gateway/src/v2-events/events/root-resolvers.ts @@ -0,0 +1,70 @@ +/* + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. + * + * OpenCRVS is also distributed under the terms of the Civil Registration + * & Healthcare Disclaimer located at http://opencrvs.org/license. + * + * Copyright (C) The OpenCRVS Authors located at https://github.com/opencrvs/opencrvs-core/blob/master/AUTHORS. + */ +import { env } from '@gateway/environment' +import { GQLResolver } from '@gateway/graphql/schema' +import type { AppRouter } from '@opencrvs/events/src/router' +import { createTRPCClient, httpBatchLink, HTTPHeaders } from '@trpc/client' + +import superjson from 'superjson' +import uuid from 'uuid' + +const trpc = createTRPCClient({ + links: [ + httpBatchLink({ + url: env.EVENTS_URL, + transformer: superjson, + headers({ opList }) { + const headers = opList[0].context?.headers + return headers as HTTPHeaders + } + }) + ] +}) + +export const resolvers: GQLResolver = { + Query: { + async getEvent(_, { eventId }, { headers: authHeader }) { + return trpc.event.get.query(eventId) + } + }, + Mutation: { + async createEvent(_, { event }, { headers }) { + const createdEvent = await trpc.event.create.mutate( + { + event: event, + transactionId: uuid.v4() + }, + { context: { headers } } + ) + return createdEvent + }, + async notifyEvent(_, { eventId, input }, { headers }) { + return trpc.event.actions.notify.mutate( + { + eventId: eventId, + transactionId: uuid.v4(), + action: input + }, + { context: { headers } } + ) + }, + async declareEvent(_, { eventId, input }, { headers }) { + return trpc.event.actions.declare.mutate( + { + eventId: eventId, + transactionId: uuid.v4(), + action: input + }, + { context: { headers } } + ) + } + } +} diff --git a/packages/gateway/src/v2-events/events/schema.graphql b/packages/gateway/src/v2-events/events/schema.graphql new file mode 100644 index 00000000000..d1a76309808 --- /dev/null +++ b/packages/gateway/src/v2-events/events/schema.graphql @@ -0,0 +1,149 @@ +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, You can obtain one at https://mozilla.org/MPL/2.0/. +# +# OpenCRVS is also distributed under the terms of the Civil Registration +# & Healthcare Disclaimer located at http://opencrvs.org/license. +# +# Copyright (C) The OpenCRVS Authors located at https://github.com/opencrvs/opencrvs-core/blob/master/AUTHORS. + +scalar DateTime + +type Event { + type: String! + id: String! + createdAt: DateTime! + updatedAt: DateTime! + actions: [Action!]! +} + +input EventInput { + type: String! +} + +type Field { + id: String! + value: FieldValue! +} + +input FieldInput { + id: String! + value: FieldValue! +} + +union Action = CreateAction | RegisterAction | NotifyAction | DeclareAction + +type CreateAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! +} + +type NotifyAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! +} + +type DeclareAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! + identifiers: Identifiers! +} + +type RegisterAction { + type: String! + createdAt: DateTime! + createdBy: String! + fields: [Field!]! + identifiers: Identifiers! +} + +input NotifyActionInput { + fields: [FieldInput!]! +} + +input DeclareActionInput { + fields: [FieldInput!]! +} + +input RegisterActionInput { + fields: [FieldInput!]! +} + +input CertifyActionInput { + fields: [FieldInput!]! +} + +input IssueActionInput { + fields: [FieldInput!]! +} + +input RevokeActionInput { + fields: [FieldInput!]! +} + +input ReinstateActionInput { + fields: [FieldInput!]! +} + +input RevokeCorrectionActionInput { + fields: [FieldInput!]! +} + +input RequestCorrectionActionInput { + fields: [FieldInput!]! +} + +input ApproveCorrectionActionInput { + fields: [FieldInput!]! +} + +input RejectCorrectionActionInput { + fields: [FieldInput!]! +} + +type Identifiers { + trackingId: String! + registrationNumber: String! +} + +input IdentifiersInput { + trackingId: String! + registrationNumber: String! +} + +type Query { + getEvent(eventId: ID!): Event! +} + +type Mutation { + createEvent(event: EventInput!): Event! + notifyEvent(eventId: ID!, input: NotifyActionInput!): Event! + declareEvent(eventId: ID!, input: DeclareActionInput!): Event! + registerEvent(eventId: ID!, input: RegisterActionInput!): Event! + certifyEvent(eventId: ID!, input: CertifyActionInput!): Event! + issueEvent(eventId: ID!, input: IssueActionInput!): Event! + revokeEvent(eventId: ID!, input: RevokeActionInput!): Event! + reinstateEvent(eventId: ID!, input: ReinstateActionInput!): Event! + revokeCorrectionEvent( + eventId: ID! + input: RevokeCorrectionActionInput! + ): Event! + requestCorrectionEvent( + eventId: ID! + input: RequestCorrectionActionInput! + ): Event! + approveCorrectionEvent( + eventId: ID! + input: ApproveCorrectionActionInput! + ): Event! + rejectCorrectionEvent( + eventId: ID! + input: RejectCorrectionActionInput! + ): Event! +} diff --git a/packages/gateway/src/v2-events/events/type-resolvers.ts b/packages/gateway/src/v2-events/events/type-resolvers.ts new file mode 100644 index 00000000000..3082f072363 --- /dev/null +++ b/packages/gateway/src/v2-events/events/type-resolvers.ts @@ -0,0 +1,29 @@ +/* + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. + * + * OpenCRVS is also distributed under the terms of the Civil Registration + * & Healthcare Disclaimer located at http://opencrvs.org/license. + * + * Copyright (C) The OpenCRVS Authors located at https://github.com/opencrvs/opencrvs-core/blob/master/AUTHORS. + */ +import { GQLResolver } from '@gateway/graphql/schema' +import { Action, ActionType } from '@opencrvs/commons' + +export const eventResolvers: GQLResolver = { + Action: { + __resolveType: (obj: Action) => { + if (obj.type === ActionType.NOTIFY) { + return 'NotifyAction' + } + if (obj.type === ActionType.DECLARE) { + return 'DeclareAction' + } + if (obj.type === ActionType.REGISTER) { + return 'RegisterAction' + } + return 'CreateAction' + } + } +} diff --git a/packages/gateway/tsconfig.json b/packages/gateway/tsconfig.json index bdca418f56e..7c94cd211e4 100644 --- a/packages/gateway/tsconfig.json +++ b/packages/gateway/tsconfig.json @@ -3,7 +3,8 @@ "skipLibCheck": true, "baseUrl": "./src", "paths": { - "@gateway/*": ["./*"] + "@gateway/*": ["./*"], + "@events/*": ["../../events/src/*"] }, "target": "es6", "module": "node16", diff --git a/yarn.lock b/yarn.lock index fbf6531740e..2b63f903b1a 100644 --- a/yarn.lock +++ b/yarn.lock @@ -8045,6 +8045,11 @@ resolved "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.0.tgz" integrity sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A== +"@trpc/client@^11.0.0-rc.532": + version "11.0.0-rc.638" + resolved "https://registry.yarnpkg.com/@trpc/client/-/client-11.0.0-rc.638.tgz#5e35d861d905a9e1a17d919889cc5744a6993ef6" + integrity sha512-zKOZZwUMcF4cvm04aawG7dP6M9dCs7FEWHuiBy7xmU+RIonsgpolLMRXm7bFie5EhQOGizhLRGnhneGwjNzWMA== + "@trpc/server@^11.0.0-rc.532": version "11.0.0-rc.604" resolved "https://registry.yarnpkg.com/@trpc/server/-/server-11.0.0-rc.604.tgz#99929ca7840fe1d01f0adefe35536d66778f02bd"