Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix nextjs #45

Merged
merged 2 commits into from
Nov 4, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 8 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,4 +35,11 @@ Scratch Auth is licensed under the MIT License. For more details, please refer t

If you have any questions or feedback, feel free to reach out via [GitHub Discussions](https://github.com/scratch-auth/pkg/discussions).

Thank you for using Scratch Auth!
Thank you for using Scratch Auth!

---

# Document

- [Next.js](https://github.com/scratch-auth/pkg/blob/main/packages/nextjs/README.md)
- [React](https://github.com/scratch-auth/pkg/blob/main/packages/react/README.md)
53 changes: 52 additions & 1 deletion packages/nextjs/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ SCRATCH_AUTH_SECRET_KEY=***************************************
This page will decode the session and verify account information. You need to add this file to the path of the `redirect_url` that you set in `scratch-auth.config.ts`. During the redirect, the session will be set in the `privateCode` parameter.

```tsx filename="app/api/auth/page.tsx"
// /src/app/api/auth/page.tsx
"use client";

import React, { useEffect } from "react";
Expand Down Expand Up @@ -72,6 +73,7 @@ By using Scratch Auth’s pre-built components, you can control the content disp
- `<LogInButton />`: An unstyled component that links to the login page. In this example, since no properties or environment variables are specified for the login URL, the component will link to the login page of the account portal.

```tsx filename="app/page.tsx"
// /src/app/page.tsx
import React from "react";
import {
LogInButton,
Expand Down Expand Up @@ -106,6 +108,7 @@ export default function Page() {
| debug | Debug mode |

```tsx filename="scratch-auth.config.ts"
// /scratch-auth.config.ts
import { ScratchAuthConfig } from "@scratch-auth/nextjs/src/types";
import { type ClassValue, clsx } from "clsx";
import { twMerge } from "tailwind-merge";
Expand Down Expand Up @@ -137,4 +140,52 @@ up and create the first user.

</Steps>

[@Looky1173](https://github.com/Looky1173) / [@Fun117](https://github.com/Fun117)
[@Looky1173](https://github.com/Looky1173) / [@Fun117](https://github.com/Fun117)

---

# プロバイダー

バージョン `0.0.2` で実装される認証プロバイダー機能です。

プロバイダーの設定をすることで、ログインしていないユーザーに特定の制限を設定できます。

```ts
type ConfigProps = {
noLogin: {
redirect?: string;
function?: () => void;
children?: React.ReactNode;
};
};
```

制限したい要素の親要素に、`ScratchAuthProvider` を設置してください。

```tsx
// /src/app/dashboard/layout.tsx
import ScratchAuthProvider from "@scratch-auth/nextjs/src/components/provider";

export default function DashboardLayout({
children,
}: Readonly<{
children: React.ReactNode;
}>) {
return <ScratchAuthProvider>{children}</ScratchAuthProvider>;
}
```

ログインしているユーザーは認証プロバイダーで制限されている要素を表示することができます。

```tsx
// /src/app/dashboard/page.tsx
import React from 'react'

function page() {
return (
<div>page</div>
)
}

export default page
```
2 changes: 1 addition & 1 deletion packages/nextjs/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@scratch-auth/nextjs",
"version": "0.0.1",
"version": "0.0.2-beta-1410m-20241104",
"description": "Scratch Auth is a simple OAuth service for Scratch. It provides developers with an easy-to-understand API and users with a smooth login experience. By using @scratch-auth/nextjs, you can easily implement OAuth functionality into your site.",
"main": "./src/index.d.ts",
"scripts": {
Expand Down
61 changes: 61 additions & 0 deletions packages/nextjs/src/components/provider.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
"use client";

import React from "react";
import { useUser } from "../hooks/useUser";

type ConfigProps = {
noLogin: {
redirect?: string;
function?: () => void;
children?: React.ReactNode;
};
};

export interface ScratchAuthProviderProps {
children: React.ReactNode;
config?: ConfigProps;
}

const ScratchAuthProvider = ({
children,
config = {
noLogin: {
redirect: "/",
},
},
}: ScratchAuthProviderProps) => {
const { user, loading, refreshUser } = useUser();

React.useEffect(() => {
const handleCookieChange = () => {
refreshUser(); // クッキーが変化した際にユーザー情報を更新
};

if (typeof window !== undefined) {
window.addEventListener("sah-sessionchange", handleCookieChange); // クッキーの変化を監視

return () => {
window.removeEventListener("sah-sessionchange", handleCookieChange); // クリーンアップ
};
}
}, [refreshUser]);

if (loading) {
return <>{config?.noLogin.children}</> || null;
}

if (!user) {
if (config?.noLogin.redirect && typeof window !== undefined) {
window.location.href = config?.noLogin.redirect;
return null;
}
if (config?.noLogin.function) {
config?.noLogin.function();
}
return <>{config?.noLogin.children}</> || null;
}
return <>{children}</>;
};
ScratchAuthProvider.displayName = "ScratchAuthProvider";

export default ScratchAuthProvider;
2 changes: 2 additions & 0 deletions packages/nextjs/src/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,5 @@ export * from "./hooks/useUser.ts";
export * from "./elements/Logined.tsx";
export * from "./elements/UserButton.tsx";
export * from "./elements/account.tsx";

export * from "./components/provider.tsx";
2 changes: 1 addition & 1 deletion packages/nextjs/src/server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -128,4 +128,4 @@ export async function isLoggedIn(): Promise<boolean> {
export async function checkRedirectState(): Promise<boolean> {
const session = await checkSession();
return !!session; // ログイン済みかどうか
}
}
1 change: 1 addition & 0 deletions packages/react/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
# COMING SOON
2 changes: 1 addition & 1 deletion pages/docs/nextjs/quickstart.ja.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -163,4 +163,4 @@ pnpm dev
</Tabs>
[http://localhost:3000 ↗](http://localhost:3000) にあるアプリのホームページにアクセスします。サインアップして最初のユーザーを作成します。

</Steps>
</Steps>
9 changes: 9 additions & 0 deletions test/nextjs/src/app/dashboard/layout.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import ScratchAuthProvider from "@scratch-auth/nextjs/src/components/provider";

export default function DashboardLayout({
children,
}: Readonly<{
children: React.ReactNode;
}>) {
return <ScratchAuthProvider>{children}</ScratchAuthProvider>;
}
9 changes: 9 additions & 0 deletions test/nextjs/src/app/dashboard/page.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
import React from 'react'

function page() {
return (
<div>page</div>
)
}

export default page
Loading