Skip to content

Commit

Permalink
Initial user db schemas (#24)
Browse files Browse the repository at this point in the history
  • Loading branch information
royscheeren authored Jan 9, 2024
2 parents 41afc9f + b790015 commit 786a537
Show file tree
Hide file tree
Showing 17 changed files with 1,401 additions and 541 deletions.
2 changes: 1 addition & 1 deletion apps/envited.ascs.digital/.env.example
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
ENV='local'
ENV='development'
REGION='eu-central-1'

# .env.development only
Expand Down
27 changes: 27 additions & 0 deletions apps/envited.ascs.digital/common/database/data/roles.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
export const ROLES = [
{
id: 'admin',
name: 'Admin',
description: 'Admin role',
},
{
id: 'federator',
name: 'Federator',
description: 'Federator role',
},
{
id: 'principal',
name: 'Principal',
description: 'Principal role',
},
{
id: 'provider',
name: 'Provider',
description: 'Provider role',
},
{
id: 'user',
name: 'User',
description: 'User role',
},
]
2 changes: 1 addition & 1 deletion apps/envited.ascs.digital/common/database/database.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ export const initDb =
max: 1,
}

if (!equals(process.env.ENV, 'local')) {
if (!equals(process.env.ENV, 'development')) {
try {
const { password, dbname, port, host, username } = await getSecret(process.env.RDS_SECRET_ARN!)
config = {
Expand Down
27 changes: 25 additions & 2 deletions apps/envited.ascs.digital/common/database/migrate.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,35 @@
import { RDSDataClient } from '@aws-sdk/client-rds-data'
import { fromIni } from '@aws-sdk/credential-providers'
import { PostgresJsDatabase } from 'drizzle-orm/postgres-js'
import { migrate as PGMigrate } from 'drizzle-orm/postgres-js/migrator'
import { migrate as AWSDataApiMigrate } from 'drizzle-orm/aws-data-api/pg/migrator'
import { drizzle as RDSDrizzle } from 'drizzle-orm/aws-data-api/pg'

import { connectDb } from './database'
import * as schema from './schema'

const runMigration = async () => {
const db = await connectDb()

try {
await PGMigrate(db as PostgresJsDatabase, { migrationsFolder: `../../drizzle/${process.env.ENV}` })
if (process.env.ENV === 'development') {
const db = await connectDb()
await PGMigrate(db as PostgresJsDatabase, { migrationsFolder: `../drizzle/${process.env.ENV}` })
return
}

const rdsClient = new RDSDataClient({
credentials: fromIni({ profile: process.env.AWS_PROFILE || '' }),
region: 'eu-central-1',
})

const db = RDSDrizzle(rdsClient, {
database: process.env.RDS_DB_NAME || '',
secretArn: process.env.RDS_SECRET_ARN || '',
resourceArn: process.env.RDS_RESOURCE_ARN || '',
schema,
})

await AWSDataApiMigrate(db, { migrationsFolder: `../drizzle/${process.env.ENV}` })
} catch (error) {
console.error(error)
} finally {
Expand Down
104 changes: 104 additions & 0 deletions apps/envited.ascs.digital/common/database/schema.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
import { relations } from 'drizzle-orm'
import { boolean, pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core'

export const user = pgTable('user', {
id: text('id').unique().primaryKey(),
name: text('name'),
email: text('email'),
isAscsMember: boolean('is_ascs_member'),
isEnvitedMember: boolean('is_envited_member'),
streetAddress: text('street_address'),
postalCode: text('postal_code'),
addressLocality: text('address_location'),
addressCountry: text('address_country'),
vatId: text('vat_id'),
privacyPolicyAccepted: text('privacy_policy_accepted'),
articlesOfAssociationAccepted: text('articles_of_association_accepted'),
contributionRulesAccepted: text('contribution_rules_accepted'),
issuerId: text('issuer_id')
.references(() => issuer.id)
.notNull(),
addressTypeId: uuid('address_type_id').references(() => addressType.id),
issuanceDate: timestamp('issuance_date'),
expirationDate: timestamp('expiration_date'),
createdAt: timestamp('created_at'),
updatedAt: timestamp('updated_at'),
})

export const userRelations = relations(user, ({ many }) => ({
usersToCredentialTypes: many(usersToCredentialTypes),
usersToRoles: many(usersToRoles),
}))

export const role = pgTable('role', {
id: text('id').unique().primaryKey(),
name: text('name'),
description: text('description'),
})

export const roleRelations = relations(role, ({ many }) => ({
usersToRoles: many(usersToRoles),
}))

export const addressType = pgTable('addressType', {
id: uuid('id').defaultRandom().primaryKey(),
name: text('name'),
description: text('description'),
})

export const issuer = pgTable('issuer', {
id: text('id').unique().primaryKey(),
name: text('name'),
url: text('url'),
type: text('type'),
})

export const credentialType = pgTable('credentialType', {
id: uuid('id').defaultRandom().primaryKey(),
name: text('name'),
description: text('description'),
})

export const credentialTypeRelations = relations(credentialType, ({ many }) => ({
usersToCredentialTypes: many(usersToCredentialTypes),
}))

export const usersToCredentialTypes = pgTable('usersToCredentialTypes', {
userId: text('user_id')
.references(() => user.id)
.notNull(),
credentialTypeId: uuid('credential_type_id')
.references(() => credentialType.id)
.notNull(),
})

export const usersToRoles = pgTable('usersToRoles', {
userId: text('user_id')
.references(() => user.id)
.notNull(),
roleId: text('role_id')
.references(() => role.id)
.notNull(),
})

export const usersToCredentialTypesRelations = relations(usersToCredentialTypes, ({ one }) => ({
credentialType: one(credentialType, {
fields: [usersToCredentialTypes.credentialTypeId],
references: [credentialType.id],
}),
user: one(user, {
fields: [usersToCredentialTypes.userId],
references: [user.id],
}),
}))

export const usersToRolesRelations = relations(usersToRoles, ({ one }) => ({
role: one(role, {
fields: [usersToRoles.roleId],
references: [role.id],
}),
user: one(user, {
fields: [usersToRoles.userId],
references: [user.id],
}),
}))
31 changes: 31 additions & 0 deletions apps/envited.ascs.digital/common/database/seed.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,37 @@
import { RDSDataClient } from '@aws-sdk/client-rds-data'
import { fromIni } from '@aws-sdk/credential-providers'
import { drizzle as RDSDrizzle } from 'drizzle-orm/aws-data-api/pg'

import { ROLES } from './data/roles'
import { connectDb } from './database'
import { role } from './schema'
import * as schema from './schema'

const insertRoles = (connection: any) => async (roles: any[]) =>
connection.insert(role).values(roles).execute()

const seed = async () => {
try {
// Insert seeding requirements here
let connection = null

if (process.env.ENV === 'development') {
connection = await connectDb()
return
} else {
const rdsClient = new RDSDataClient({
credentials: fromIni({ profile: process.env.AWS_PROFILE || '' }),
region: 'eu-central-1',
})

connection = RDSDrizzle(rdsClient, {
database: process.env.RDS_DB_NAME || '',
secretArn: process.env.RDS_SECRET_ARN || '',
resourceArn: process.env.RDS_RESOURCE_ARN || '',
schema,
})
}
await insertRoles(connection)(ROLES)
} catch (error) {
console.error(error)
} finally {
Expand Down
6 changes: 6 additions & 0 deletions apps/envited.ascs.digital/common/types/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,3 +32,9 @@ export type Action<T> = {
type: T
data?: Obj
}

export type Role = {
id: string
name: string
description: string
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
CREATE TABLE IF NOT EXISTS "addressType" (
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
"name" text,
"description" text
);
--> statement-breakpoint
CREATE TABLE IF NOT EXISTS "credentialType" (
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
"name" text,
"description" text
);
--> statement-breakpoint
CREATE TABLE IF NOT EXISTS "issuer" (
"id" text PRIMARY KEY NOT NULL,
"name" text,
"url" text,
"type" text,
CONSTRAINT "issuer_id_unique" UNIQUE("id")
);
--> statement-breakpoint
CREATE TABLE IF NOT EXISTS "role" (
"id" text PRIMARY KEY NOT NULL,
"name" text,
"description" text,
CONSTRAINT "role_id_unique" UNIQUE("id")
);
--> statement-breakpoint
CREATE TABLE IF NOT EXISTS "user" (
"id" text PRIMARY KEY NOT NULL,
"name" text,
"email" text,
"is_ascs_member" boolean,
"is_envited_member" boolean,
"street_address" text,
"postal_code" text,
"address_location" text,
"address_country" text,
"vat_id" text,
"privacy_policy_accepted" text,
"articles_of_association_accepted" text,
"contribution_rules_accepted" text,
"issuer_id" text NOT NULL,
"address_type_id" uuid,
"issuance_date" timestamp,
"expiration_date" timestamp,
"created_at" timestamp,
"updated_at" timestamp,
CONSTRAINT "user_id_unique" UNIQUE("id")
);
--> statement-breakpoint
CREATE TABLE IF NOT EXISTS "usersToCredentialTypes" (
"user_id" text NOT NULL,
"credential_type_id" uuid NOT NULL
);
--> statement-breakpoint
CREATE TABLE IF NOT EXISTS "usersToRoles" (
"user_id" text NOT NULL,
"role_id" text NOT NULL
);
--> statement-breakpoint
DO $$ BEGIN
ALTER TABLE "user" ADD CONSTRAINT "user_issuer_id_issuer_id_fk" FOREIGN KEY ("issuer_id") REFERENCES "issuer"("id") ON DELETE no action ON UPDATE no action;
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
--> statement-breakpoint
DO $$ BEGIN
ALTER TABLE "user" ADD CONSTRAINT "user_address_type_id_addressType_id_fk" FOREIGN KEY ("address_type_id") REFERENCES "addressType"("id") ON DELETE no action ON UPDATE no action;
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
--> statement-breakpoint
DO $$ BEGIN
ALTER TABLE "usersToCredentialTypes" ADD CONSTRAINT "usersToCredentialTypes_user_id_user_id_fk" FOREIGN KEY ("user_id") REFERENCES "user"("id") ON DELETE no action ON UPDATE no action;
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
--> statement-breakpoint
DO $$ BEGIN
ALTER TABLE "usersToCredentialTypes" ADD CONSTRAINT "usersToCredentialTypes_credential_type_id_credentialType_id_fk" FOREIGN KEY ("credential_type_id") REFERENCES "credentialType"("id") ON DELETE no action ON UPDATE no action;
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
--> statement-breakpoint
DO $$ BEGIN
ALTER TABLE "usersToRoles" ADD CONSTRAINT "usersToRoles_user_id_user_id_fk" FOREIGN KEY ("user_id") REFERENCES "user"("id") ON DELETE no action ON UPDATE no action;
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
--> statement-breakpoint
DO $$ BEGIN
ALTER TABLE "usersToRoles" ADD CONSTRAINT "usersToRoles_role_id_role_id_fk" FOREIGN KEY ("role_id") REFERENCES "role"("id") ON DELETE no action ON UPDATE no action;
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
Loading

0 comments on commit 786a537

Please sign in to comment.