diff --git a/.env.example b/.env.example index 5652074..c597f6e 100644 --- a/.env.example +++ b/.env.example @@ -1 +1,2 @@ +KIBELA_API_URL= KIBELA_ACCESS_TOKEN= diff --git a/.github/workflows/check.yaml b/.github/workflows/check.yaml new file mode 100644 index 0000000..193c7e7 --- /dev/null +++ b/.github/workflows/check.yaml @@ -0,0 +1,102 @@ +name: Check +on: + push: + branches: + - main + pull_request: + types: + - opened + - synchronize + - reopened + +permissions: + contents: read + +jobs: + lint: + runs-on: ubuntu-latest + timeout-minutes: 5 + steps: + - name: Setup | Checkout + uses: actions/checkout@v4 + + - name: Setup | Install pnpm + uses: pnpm/action-setup@v4 + with: + run_install: false + + - name: Setup | Node.js + uses: actions/setup-node@v4 + with: + node-version-file: .nvmrc + cache: pnpm + + - name: Setup | Install Dependencies + run: pnpm install --frozen-lockfile + + - name: Run | Lint + run: pnpm run lint + + typecheck: + runs-on: ubuntu-latest + timeout-minutes: 5 + steps: + - name: Setup | Checkout + uses: actions/checkout@v4 + + - name: Setup | Install pnpm + uses: pnpm/action-setup@v4 + with: + run_install: false + + - name: Setup | Node.js + uses: actions/setup-node@v4 + with: + node-version-file: .nvmrc + cache: pnpm + + - name: Setup | Install Dependencies + run: pnpm install --frozen-lockfile + + - name: Run | Type Check + run: pnpm run typecheck + + check-schema: + runs-on: ubuntu-latest + timeout-minutes: 5 + steps: + - name: Setup | Checkout + uses: actions/checkout@v4 + + - name: Setup | Install pnpm + uses: pnpm/action-setup@v4 + with: + run_install: false + + - name: Setup | Node.js + uses: actions/setup-node@v4 + with: + node-version-file: .nvmrc + cache: pnpm + + - name: Setup | Install Dependencies + run: pnpm install --frozen-lockfile + + - name: Setup | Generate Type for GraphQL + run: pnpm codegen + + - name: Run | Check Diff + run: | + fail=0 + + # Check Type + if [ "$(git diff --ignore-space-at-eol --text src/graphql | wc -l)" -gt "0" ]; then + echo "Detected uncommitted changes in type definitions. See status below:" + git diff --ignore-space-at-eol --text app/libs/database.ts + fail=1 + fi + + if [ "$fail" -gt "0" ]; then + echo "Detected uncommitted changes in schema definitions. Please commit the changes before pushing." + exit 1 + fi diff --git a/.npmrc b/.npmrc new file mode 100644 index 0000000..1dab4ed --- /dev/null +++ b/.npmrc @@ -0,0 +1 @@ +save-exact = true diff --git a/.nvmrc b/.nvmrc new file mode 100644 index 0000000..ec7ba0e --- /dev/null +++ b/.nvmrc @@ -0,0 +1 @@ +22.10.0 diff --git a/graphql/query.graphql b/graphql/query.graphql index be2a267..fe2b1ac 100644 --- a/graphql/query.graphql +++ b/graphql/query.graphql @@ -1,5 +1,5 @@ -query GetAllPosts { - folderFromPath(path: "https://tuatmcc.kibe.la/folders/3754") { +query GetAllPosts($folderPath: String!) { + folderFromPath(path: $folderPath) { id name notes(first: 1000) { diff --git a/package.json b/package.json index 4a72f62..8898f10 100644 --- a/package.json +++ b/package.json @@ -8,6 +8,7 @@ "start": "next start", "lint": "biome check .", "fmt": "biome check . --write", + "typecheck": "tsc --noEmit", "codegen": "graphql-codegen --config codegen.ts", "get-graphql-schema": "get-graphql-schema" }, @@ -35,5 +36,6 @@ "postcss": "^8", "tailwindcss": "^3.4.1", "typescript": "^5" - } + }, + "packageManager": "pnpm@9.15.0" } diff --git a/src/app/[id]/page.tsx b/src/app/[id]/page.tsx index f68263b..205442e 100644 --- a/src/app/[id]/page.tsx +++ b/src/app/[id]/page.tsx @@ -2,7 +2,7 @@ import { GetAllPostsDocument, GetPostDocument } from "@/graphql/request"; import type { GetAllPostsQuery, GetPostQuery } from "@/graphql/types"; import { query } from "@/lib/client"; -export async function generateStaticParams() { +export async function generateStaticParams(): Promise<{ id: string }[]> { const { data: { folderFromPath: { notes }, @@ -10,26 +10,34 @@ export async function generateStaticParams() { error, } = await query({ query: GetAllPostsDocument, + variables: { + folderPath: "https://tuatmcc.kibe.la/folders/3754", + }, }); + await new Promise((resolve) => setTimeout(resolve, 100)); - if (error) { + if (error || !notes.edges?.length) { throw error; } - return notes.edges - ?.map((edge) => ({ - id: edge?.node?.id, - })) - .filter((id) => Boolean(id)); + return notes.edges.flatMap((edge) => { + if (!edge?.node?.id) return []; + return { id: edge.node.id }; + }); } -export default async function Blog({ params }: { params: { id: string } }) { - const { id } = params; +export default async function Blog({ + params, +}: { + params: Promise<{ id: string }>; +}) { + const { id } = await params; const { data, error } = await query({ query: GetPostDocument, variables: { id }, }); + await new Promise((resolve) => setTimeout(resolve, 100)); if (error) { throw error; diff --git a/src/app/_components/HomeContainer/index.tsx b/src/app/_components/HomeContainer/index.tsx index c7b8d6c..c11a25f 100644 --- a/src/app/_components/HomeContainer/index.tsx +++ b/src/app/_components/HomeContainer/index.tsx @@ -11,10 +11,14 @@ export const HomeContainer = async () => { }, } = await query({ query: GetAllPostsDocument, + variables: { + folderPath: "https://tuatmcc.kibe.la/folders/3754", + }, }); if (error) { throw error; } + await new Promise((resolve) => setTimeout(resolve, 100)); return (
diff --git a/src/app/layout.tsx b/src/app/layout.tsx index 853ba3e..659596e 100644 --- a/src/app/layout.tsx +++ b/src/app/layout.tsx @@ -1,7 +1,6 @@ import type { Metadata } from "next"; import localFont from "next/font/local"; import "./globals.css"; -import { Provider } from "@urql/next"; const geistSans = localFont({ src: "./fonts/GeistVF.woff", diff --git a/src/graphql/request.ts b/src/graphql/request.ts index 637520b..090b652 100644 --- a/src/graphql/request.ts +++ b/src/graphql/request.ts @@ -6,8 +6,8 @@ import gql from 'graphql-tag'; type GraphQLClientRequestHeaders = RequestOptions['requestHeaders']; export const GetAllPostsDocument = gql` - query GetAllPosts { - folderFromPath(path: "https://tuatmcc.kibe.la/folders/3754") { + query GetAllPosts($folderPath: String!) { + folderFromPath(path: $folderPath) { id name notes(first: 1000) { @@ -41,7 +41,7 @@ const defaultWrapper: SdkFunctionWrapper = (action, _operationName, _operationTy export function getSdk(client: GraphQLClient, withWrapper: SdkFunctionWrapper = defaultWrapper) { return { - GetAllPosts(variables?: Types.GetAllPostsQueryVariables, requestHeaders?: GraphQLClientRequestHeaders): Promise { + GetAllPosts(variables: Types.GetAllPostsQueryVariables, requestHeaders?: GraphQLClientRequestHeaders): Promise { return withWrapper((wrappedRequestHeaders) => client.request(GetAllPostsDocument, variables, {...requestHeaders, ...wrappedRequestHeaders}), 'GetAllPosts', 'query', variables); }, GetPost(variables: Types.GetPostQueryVariables, requestHeaders?: GraphQLClientRequestHeaders): Promise { diff --git a/src/graphql/types.ts b/src/graphql/types.ts index 5bef7ed..7d313e5 100644 --- a/src/graphql/types.ts +++ b/src/graphql/types.ts @@ -3617,7 +3617,9 @@ export enum WatchState { WatchNoteUpdate = 'WATCH_NOTE_UPDATE' } -export type GetAllPostsQueryVariables = Exact<{ [key: string]: never; }>; +export type GetAllPostsQueryVariables = Exact<{ + folderPath: Scalars['String']['input']; +}>; export type GetAllPostsQuery = { readonly __typename?: 'Query', readonly folderFromPath: { readonly __typename?: 'Folder', readonly id: string, readonly name: string, readonly notes: { readonly __typename?: 'NoteConnection', readonly totalCount: number, readonly edges?: ReadonlyArray<{ readonly __typename?: 'NoteEdge', readonly node?: { readonly __typename?: 'Note', readonly id: string, readonly title: string, readonly createdAt: any } | null } | null> | null } } }; diff --git a/src/lib/client.ts b/src/lib/client.ts index 5495e3b..2773e5f 100644 --- a/src/lib/client.ts +++ b/src/lib/client.ts @@ -9,7 +9,7 @@ export const { getClient, query, PreloadQuery } = registerApolloClient(() => { return new ApolloClient({ cache: new InMemoryCache(), link: new HttpLink({ - uri: "https://tuatmcc.kibe.la/api/v1", + uri: process.env.KIBELA_API_URL, headers: { Authorization: `Bearer ${process.env.KIBELA_ACCESS_TOKEN}`, },