mirror of
https://github.com/AustinKelsay/plebdevs.git
synced 2025-06-23 16:05:24 +00:00
github signup, creates user and kind0, can open nostr profile from plebdevs profile now
This commit is contained in:
parent
91cfd7a3cb
commit
c9d702576e
@ -56,7 +56,7 @@ const UserAvatar = () => {
|
|||||||
return null; // Or return a loader/spinner/placeholder
|
return null; // Or return a loader/spinner/placeholder
|
||||||
} else if (user && Object.keys(user).length > 0) {
|
} else if (user && Object.keys(user).length > 0) {
|
||||||
// User exists, show username or pubkey
|
// User exists, show username or pubkey
|
||||||
const displayName = user.username || user?.email || user?.pubkey.slice(0, 10) + '...';
|
const displayName = user.username || user?.name || user?.email || user?.pubkey.slice(0, 10) + '...' || "Anon";
|
||||||
|
|
||||||
const items = [
|
const items = [
|
||||||
{
|
{
|
||||||
|
@ -70,6 +70,11 @@ const UserProfile = () => {
|
|||||||
copyToClipboard(nip19.npubEncode(user?.pubkey));
|
copyToClipboard(nip19.npubEncode(user?.pubkey));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: 'Open Nostr Profile',
|
||||||
|
icon: 'pi pi-external-link',
|
||||||
|
command: () => window.open(`https://nostr.com/${nip19.npubEncode(user?.pubkey)}`, '_blank')
|
||||||
}
|
}
|
||||||
];
|
];
|
||||||
|
|
||||||
@ -106,7 +111,7 @@ const UserProfile = () => {
|
|||||||
|
|
||||||
|
|
||||||
<h1 className="text-center text-2xl my-2">
|
<h1 className="text-center text-2xl my-2">
|
||||||
{user.username || user?.email || "Anon"}
|
{user.username || user?.name || user?.email || "Anon"}
|
||||||
</h1>
|
</h1>
|
||||||
{user.pubkey && (
|
{user.pubkey && (
|
||||||
<h2 className="text-center text-xl my-2 truncate max-tab:px-4 max-mob:px-4">
|
<h2 className="text-center text-xl my-2 truncate max-tab:px-4 max-mob:px-4">
|
||||||
|
@ -176,6 +176,11 @@ const UserSettings = () => {
|
|||||||
command: () => {
|
command: () => {
|
||||||
copyToClipboard(nip19.npubEncode(user?.pubkey));
|
copyToClipboard(nip19.npubEncode(user?.pubkey));
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: 'Open Nostr Profile',
|
||||||
|
icon: 'pi pi-external-link',
|
||||||
|
command: () => window.open(`https://nostr.com/${nip19.npubEncode(user?.pubkey)}`, '_blank')
|
||||||
}
|
}
|
||||||
];
|
];
|
||||||
|
|
||||||
@ -211,7 +216,7 @@ const UserSettings = () => {
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<h1 className="text-center text-2xl my-2">
|
<h1 className="text-center text-2xl my-2">
|
||||||
{user.username || user?.email || "Anon"}
|
{user.username || user?.name || user?.email || "Anon"}
|
||||||
</h1>
|
</h1>
|
||||||
{user.pubkey && (
|
{user.pubkey && (
|
||||||
<h2 className="text-center text-xl my-2 truncate max-tab:px-4 max-mob:px-4">
|
<h2 className="text-center text-xl my-2 truncate max-tab:px-4 max-mob:px-4">
|
||||||
|
@ -1,23 +1,21 @@
|
|||||||
import NextAuth from "next-auth";
|
import NextAuth from "next-auth";
|
||||||
import CredentialsProvider from "next-auth/providers/credentials";
|
import CredentialsProvider from "next-auth/providers/credentials";
|
||||||
import EmailProvider from "next-auth/providers/email";
|
import EmailProvider from "next-auth/providers/email";
|
||||||
import NDK from "@nostr-dev-kit/ndk";
|
|
||||||
import { PrismaAdapter } from "@next-auth/prisma-adapter";
|
import { PrismaAdapter } from "@next-auth/prisma-adapter";
|
||||||
import prisma from "@/db/prisma";
|
import prisma from "@/db/prisma";
|
||||||
import nodemailer from 'nodemailer';
|
import nodemailer from 'nodemailer';
|
||||||
import { findKind0Fields } from "@/utils/nostr";
|
import { findKind0Fields } from "@/utils/nostr";
|
||||||
import { generateSecretKey, getPublicKey } from 'nostr-tools/pure'
|
import { generateSecretKey, getPublicKey } from 'nostr-tools/pure'
|
||||||
import { bytesToHex } from '@noble/hashes/utils'
|
import { bytesToHex } from '@noble/hashes/utils'
|
||||||
import { updateUser, getUserByPubkey, createUser, getUserByEmail } from "@/db/models/userModels";
|
import { updateUser, getUserByPubkey, createUser } from "@/db/models/userModels";
|
||||||
import { createRole } from "@/db/models/roleModels";
|
import { createRole } from "@/db/models/roleModels";
|
||||||
import appConfig from "@/config/appConfig";
|
import appConfig from "@/config/appConfig";
|
||||||
|
import GithubProvider from "next-auth/providers/github";
|
||||||
|
import { SimplePool } from "nostr-tools";
|
||||||
|
import { finalizeEvent } from "nostr-tools";
|
||||||
|
|
||||||
// todo: currently email accounts ephemeral privkey gets saved to db but not anon user, is this required at all given the newer auth setup?
|
// todo: currently email accounts ephemeral privkey gets saved to db but not anon user, is this required at all given the newer auth setup?
|
||||||
|
|
||||||
const ndk = new NDK({
|
|
||||||
explicitRelayUrls: [...appConfig.defaultRelayUrls]
|
|
||||||
});
|
|
||||||
|
|
||||||
const authorize = async (pubkey) => {
|
const authorize = async (pubkey) => {
|
||||||
await ndk.connect();
|
await ndk.connect();
|
||||||
const user = ndk.getUser({ pubkey });
|
const user = ndk.getUser({ pubkey });
|
||||||
@ -125,6 +123,10 @@ export const authOptions = {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
|
GithubProvider({
|
||||||
|
clientId: process.env.GITHUB_CLIENT_ID,
|
||||||
|
clientSecret: process.env.GITHUB_CLIENT_SECRET
|
||||||
|
}),
|
||||||
CredentialsProvider({
|
CredentialsProvider({
|
||||||
id: "anonymous",
|
id: "anonymous",
|
||||||
name: "Anonymous",
|
name: "Anonymous",
|
||||||
@ -148,7 +150,7 @@ export const authOptions = {
|
|||||||
|
|
||||||
// Check if user exists in the database
|
// Check if user exists in the database
|
||||||
let dbUser = await getUserByPubkey(pubkey);
|
let dbUser = await getUserByPubkey(pubkey);
|
||||||
|
|
||||||
if (!dbUser) {
|
if (!dbUser) {
|
||||||
// Create new user if not exists
|
// Create new user if not exists
|
||||||
dbUser = await createUser({
|
dbUser = await createUser({
|
||||||
@ -156,7 +158,7 @@ export const authOptions = {
|
|||||||
username: pubkey.slice(0, 8), // Use first 8 characters of pubkey as username
|
username: pubkey.slice(0, 8), // Use first 8 characters of pubkey as username
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return user object with pubkey and privkey
|
// Return user object with pubkey and privkey
|
||||||
return { ...dbUser, pubkey, privkey };
|
return { ...dbUser, pubkey, privkey };
|
||||||
},
|
},
|
||||||
@ -175,18 +177,60 @@ export const authOptions = {
|
|||||||
const sk = generateSecretKey();
|
const sk = generateSecretKey();
|
||||||
const pubkey = getPublicKey(sk);
|
const pubkey = getPublicKey(sk);
|
||||||
const privkey = bytesToHex(sk);
|
const privkey = bytesToHex(sk);
|
||||||
|
|
||||||
// Update the user in the database
|
// Update the user in the database
|
||||||
await prisma.user.update({
|
await prisma.user.update({
|
||||||
where: { id: user.id },
|
where: { id: user.id },
|
||||||
data: { pubkey, privkey }
|
data: { pubkey, privkey }
|
||||||
});
|
});
|
||||||
|
|
||||||
// Update the user object
|
// Update the user object
|
||||||
user.pubkey = pubkey;
|
user.pubkey = pubkey;
|
||||||
user.privkey = privkey;
|
user.privkey = privkey;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Add new condition for first-time GitHub sign up
|
||||||
|
if (trigger === "signUp" && account?.provider === "github") {
|
||||||
|
const sk = generateSecretKey();
|
||||||
|
const pubkey = getPublicKey(sk);
|
||||||
|
const privkey = bytesToHex(sk);
|
||||||
|
|
||||||
|
// Update the user in the database
|
||||||
|
await prisma.user.update({
|
||||||
|
where: { id: user.id },
|
||||||
|
data: { pubkey, privkey, name: user.name, username: user.name, avatar: user.image || null }
|
||||||
|
});
|
||||||
|
|
||||||
|
// Publish kind0 event to nostr
|
||||||
|
try {
|
||||||
|
const pool = new SimplePool();
|
||||||
|
const relays = [
|
||||||
|
"wss://relay.damus.io",
|
||||||
|
"wss://relay.nostr.band",
|
||||||
|
"wss://relay.primal.net",
|
||||||
|
"wss://relay.devs.tools"
|
||||||
|
];
|
||||||
|
|
||||||
|
const event = finalizeEvent({
|
||||||
|
kind: 0,
|
||||||
|
created_at: Math.floor(Date.now() / 1000),
|
||||||
|
tags: [],
|
||||||
|
content: JSON.stringify({
|
||||||
|
name: user.name,
|
||||||
|
picture: user.image
|
||||||
|
})
|
||||||
|
}, privkey);
|
||||||
|
|
||||||
|
await Promise.any(pool.publish(relays, event));
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Failed to publish kind0 event:', error);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Update user object with nostr keys
|
||||||
|
user.pubkey = pubkey;
|
||||||
|
user.privkey = privkey;
|
||||||
|
}
|
||||||
|
|
||||||
if (user) {
|
if (user) {
|
||||||
token.user = user;
|
token.user = user;
|
||||||
if (user.pubkey && user.privkey) {
|
if (user.pubkey && user.privkey) {
|
||||||
@ -218,14 +262,14 @@ export const authOptions = {
|
|||||||
},
|
},
|
||||||
async signIn({ user, account }) {
|
async signIn({ user, account }) {
|
||||||
if (account.provider === 'anonymous') {
|
if (account.provider === 'anonymous') {
|
||||||
return {
|
return {
|
||||||
...user,
|
...user,
|
||||||
pubkey: user.pubkey,
|
pubkey: user.pubkey,
|
||||||
privkey: user.privkey,
|
privkey: user.privkey,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
secret: process.env.NEXTAUTH_SECRET,
|
secret: process.env.NEXTAUTH_SECRET,
|
||||||
session: { strategy: "jwt" },
|
session: { strategy: "jwt" },
|
||||||
|
@ -78,6 +78,13 @@ export default function SignIn() {
|
|||||||
rounded
|
rounded
|
||||||
onClick={() => setShowEmailInput(!showEmailInput)}
|
onClick={() => setShowEmailInput(!showEmailInput)}
|
||||||
/>
|
/>
|
||||||
|
<GenericButton
|
||||||
|
label={"login with github"}
|
||||||
|
icon="pi pi-github"
|
||||||
|
className="text-[#f8f8ff] w-[250px] my-4 mx-auto"
|
||||||
|
rounded
|
||||||
|
onClick={() => signIn("github")}
|
||||||
|
/>
|
||||||
{showEmailInput && (
|
{showEmailInput && (
|
||||||
<form onSubmit={handleEmailSignIn} className="flex flex-col items-center bg-gray-700 w-fit mx-auto p-4 rounded-lg">
|
<form onSubmit={handleEmailSignIn} className="flex flex-col items-center bg-gray-700 w-fit mx-auto p-4 rounded-lg">
|
||||||
<InputText
|
<InputText
|
||||||
|
Loading…
x
Reference in New Issue
Block a user