generated from defi-wonderland/ts-turborepo-boilerplate
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: project & rounds related repositories w/kysely (#7)
# 🤖 Linear Closes GIT-90 GIT-91 ## Description - `repositories` package - Project and Rounds repositories using Kysely Query Builder ## Checklist before requesting a review - [x] I have conducted a self-review of my code. - [x] I have conducted a QA. - [ ] If it is a core feature, I have included comprehensive tests.
- Loading branch information
Showing
26 changed files
with
1,258 additions
and
5 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,59 @@ | ||
# grants-stack-indexer: repository package | ||
|
||
This package provides a data access layer for the grants-stack-indexer project, implementing the Repository pattern to abstract database operations. | ||
|
||
## Setup | ||
|
||
1. Install dependencies by running `pnpm install` in the root directory of the project. | ||
|
||
## Available Scripts | ||
|
||
Available scripts that can be run using `pnpm`: | ||
|
||
| Script | Description | | ||
| ------------- | ------------------------------------------------------- | | ||
| `build` | Build library using tsc | | ||
| `check-types` | Check for type issues using tsc | | ||
| `clean` | Remove `dist` folder | | ||
| `lint` | Run ESLint to check for coding standards | | ||
| `lint:fix` | Run linter and automatically fix code formatting issues | | ||
| `format` | Check code formatting and style using Prettier | | ||
| `format:fix` | Run formatter and automatically fix issues | | ||
| `test` | Run tests using Vitest | | ||
| `test:cov` | Run tests with coverage report | | ||
|
||
## Usage | ||
|
||
This package provides repository interfaces and implementations for projects and rounds. It uses Kysely as the query builder library. | ||
|
||
### Creating a database connection | ||
|
||
```typescript | ||
import { createKyselyPostgresDb, DatabaseConfig } from "@grants-stack-indexer/repository"; | ||
|
||
const dbConfig: DatabaseConfig = { | ||
connectionString: "postgresql://user:password@localhost:5432/mydb", | ||
}; | ||
|
||
const db = createKyselyPostgresDb(dbConfig); | ||
|
||
// Instantiate a repository | ||
const projectRepository = new KyselyProjectRepository(db, "mySchema"); | ||
|
||
const projects = await projectRepository.getProjects(10); | ||
``` | ||
|
||
## API | ||
|
||
### Repositories | ||
|
||
This package provides the following repositories: | ||
|
||
1. **IProjectRepository**: Manages project-related database operations, including project roles and pending roles. | ||
|
||
2. **IRoundRepository**: Manages round-related database operations, including round roles and pending roles. | ||
|
||
## References | ||
|
||
- [Kysely](https://kysely.dev/) | ||
- [PostgreSQL](https://www.postgresql.org/) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
{ | ||
"name": "@grants-stack-indexer/repository", | ||
"version": "0.0.1", | ||
"private": true, | ||
"description": "", | ||
"license": "MIT", | ||
"author": "Wonderland", | ||
"type": "module", | ||
"main": "./dist/src/index.js", | ||
"types": "./dist/src/index.d.ts", | ||
"directories": { | ||
"src": "src" | ||
}, | ||
"files": [ | ||
"dist/*", | ||
"package.json", | ||
"!**/*.tsbuildinfo" | ||
], | ||
"scripts": { | ||
"build": "tsc -p tsconfig.build.json", | ||
"check-types": "tsc --noEmit -p ./tsconfig.json", | ||
"clean": "rm -rf dist/", | ||
"format": "prettier --check \"{src,test}/**/*.{js,ts,json}\"", | ||
"format:fix": "prettier --write \"{src,test}/**/*.{js,ts,json}\"", | ||
"lint": "eslint \"{src,test}/**/*.{js,ts,json}\"", | ||
"lint:fix": "pnpm lint --fix", | ||
"test": "vitest run --config vitest.config.ts --passWithNoTests", | ||
"test:cov": "vitest run --config vitest.config.ts --coverage" | ||
}, | ||
"dependencies": { | ||
"@grants-stack-indexer/shared": "workspace:*", | ||
"kysely": "0.27.4", | ||
"pg": "8.13.0" | ||
}, | ||
"devDependencies": { | ||
"@types/pg": "8.11.10" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,52 @@ | ||
import { CamelCasePlugin, Kysely, PostgresDialect } from "kysely"; | ||
import { Pool, PoolConfig } from "pg"; | ||
|
||
import { | ||
PendingProjectRole as PendingProjectRoleTable, | ||
PendingRoundRole as PendingRoundRoleTable, | ||
ProjectRole as ProjectRoleTable, | ||
Project as ProjectTable, | ||
RoundRole as RoundRoleTable, | ||
Round as RoundTable, | ||
} from "../internal.js"; | ||
|
||
export interface DatabaseConfig extends PoolConfig { | ||
connectionString: string; | ||
} | ||
|
||
export interface Database { | ||
rounds: RoundTable; | ||
pendingRoundRoles: PendingRoundRoleTable; | ||
roundRoles: RoundRoleTable; | ||
projects: ProjectTable; | ||
pendingProjectRoles: PendingProjectRoleTable; | ||
projectRoles: ProjectRoleTable; | ||
} | ||
|
||
/** | ||
* Creates and configures a Kysely database instance for PostgreSQL. | ||
* | ||
* @param config - The database configuration object extending PoolConfig. | ||
* @returns A configured Kysely instance for the Database. | ||
* | ||
* This function sets up a PostgreSQL database connection using Kysely ORM. | ||
* | ||
* @example | ||
* const dbConfig: DatabaseConfig = { | ||
* connectionString: 'postgresql://user:password@localhost:5432/mydb' | ||
* }; | ||
* const db = createKyselyDatabase(dbConfig); | ||
*/ | ||
export const createKyselyPostgresDb = (config: DatabaseConfig): Kysely<Database> => { | ||
const dialect = new PostgresDialect({ | ||
pool: new Pool({ | ||
max: 15, | ||
idleTimeoutMillis: 30_000, | ||
keepAlive: true, | ||
connectionTimeoutMillis: 5_000, | ||
...config, | ||
}), | ||
}); | ||
|
||
return new Kysely<Database>({ dialect, plugins: [new CamelCasePlugin()] }); | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
// Add your external exports here | ||
export type { | ||
IRoundRepository, | ||
IRoundReadRepository, | ||
IProjectRepository, | ||
IProjectReadRepository, | ||
DatabaseConfig, | ||
} from "./internal.js"; | ||
|
||
export type { | ||
Project, | ||
ProjectType, | ||
ProjectRoleNames, | ||
NewProject, | ||
PartialProject, | ||
ProjectRole, | ||
PendingProjectRole, | ||
} from "./types/project.types.js"; | ||
|
||
export type { | ||
Round, | ||
NewRound, | ||
PartialRound, | ||
RoundRole, | ||
PendingRoundRole, | ||
} from "./types/round.types.js"; | ||
|
||
export { KyselyRoundRepository, KyselyProjectRepository } from "./repositories/kysely/index.js"; | ||
|
||
export { createKyselyPostgresDb as createKyselyDatabase } from "./internal.js"; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
export * from "./db/connection.js"; | ||
export * from "./repositories/kysely/index.js"; | ||
export * from "./interfaces/index.js"; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
export * from "./projectRepository.interface.js"; | ||
export * from "./roundRepository.interface.js"; |
103 changes: 103 additions & 0 deletions
103
packages/repository/src/interfaces/projectRepository.interface.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,103 @@ | ||
import { Address, ChainId } from "@grants-stack-indexer/shared"; | ||
|
||
import { | ||
NewPendingProjectRole, | ||
NewProject, | ||
NewProjectRole, | ||
PartialProject, | ||
PendingProjectRole, | ||
Project, | ||
ProjectRoleNames, | ||
} from "../types/project.types.js"; | ||
|
||
export interface IProjectReadRepository { | ||
/** | ||
* Retrieves all projects for a given chain ID. | ||
* @param chainId The chain ID to filter projects by. | ||
* @returns A promise that resolves to an array of Project objects. | ||
*/ | ||
getProjects(chainId: ChainId): Promise<Project[]>; | ||
|
||
/** | ||
* Retrieves a specific project by its ID and chain ID. | ||
* @param chainId The chain ID of the project. | ||
* @param projectId The unique identifier of the project. | ||
* @returns A promise that resolves to a Project object if found, or undefined if not found. | ||
*/ | ||
getProjectById(chainId: ChainId, projectId: string): Promise<Project | undefined>; | ||
|
||
/** | ||
* Retrieves all pending project roles. | ||
* @returns A promise that resolves to an array of PendingProjectRole objects. | ||
*/ | ||
getPendingProjectRoles(): Promise<PendingProjectRole[]>; | ||
|
||
/** | ||
* Retrieves pending project roles for a specific chain ID and role. | ||
* @param chainId The chain ID to filter pending roles by. | ||
* @param role The role to filter pending roles by. | ||
* @returns A promise that resolves to an array of PendingProjectRole objects. | ||
*/ | ||
getPendingProjectRolesByRole(chainId: ChainId, role: string): Promise<PendingProjectRole[]>; | ||
|
||
/** | ||
* Retrieves a project by its anchor address and chain ID. | ||
* @param chainId The chain ID of the project. | ||
* @param anchorAddress The anchor address of the project. | ||
* @returns A promise that resolves to a Project object if found, or undefined if not found. | ||
*/ | ||
getProjectByAnchor(chainId: ChainId, anchorAddress: Address): Promise<Project | undefined>; | ||
} | ||
|
||
export interface IProjectRepository extends IProjectReadRepository { | ||
/** | ||
* Inserts a new project into the repository. | ||
* @param project The new project to be inserted. | ||
* @returns A promise that resolves when the insertion is complete. | ||
*/ | ||
insertProject(project: NewProject): Promise<void>; | ||
|
||
/** | ||
* Updates an existing project in the repository. | ||
* @param where An object containing the id and chainId to identify the project to update. | ||
* @param project The partial project data to update. | ||
* @returns A promise that resolves when the update is complete. | ||
*/ | ||
updateProject(where: { id: string; chainId: ChainId }, project: PartialProject): Promise<void>; | ||
|
||
/** | ||
* Inserts a new project role into the repository. | ||
* @param projectRole The new project role to be inserted. | ||
* @returns A promise that resolves when the insertion is complete. | ||
*/ | ||
insertProjectRole(projectRole: NewProjectRole): Promise<void>; | ||
|
||
/** | ||
* Deletes multiple project roles based on the provided criteria. | ||
* @param chainId The chain ID of the project roles to delete. | ||
* @param projectId The project ID of the roles to delete. | ||
* @param role The role type to delete. | ||
* @param address Optional address to further filter the roles to delete. | ||
* @returns A promise that resolves when the deletion is complete. | ||
*/ | ||
deleteManyProjectRoles( | ||
chainId: ChainId, | ||
projectId: string, | ||
role: ProjectRoleNames, | ||
address?: Address, | ||
): Promise<void>; | ||
|
||
/** | ||
* Inserts a new pending project role into the repository. | ||
* @param pendingProjectRole The new pending project role to be inserted. | ||
* @returns A promise that resolves when the insertion is complete. | ||
*/ | ||
insertPendingProjectRole(pendingProjectRole: NewPendingProjectRole): Promise<void>; | ||
|
||
/** | ||
* Deletes multiple pending project roles based on their IDs. | ||
* @param ids An array of IDs of the pending project roles to delete. | ||
* @returns A promise that resolves when the deletion is complete. | ||
*/ | ||
deleteManyPendingProjectRoles(ids: number[]): Promise<void>; | ||
} |
Oops, something went wrong.