diff --git a/app/api/auth/route.js b/app/api/auth/route.js index 5f1bb5a..8858035 100755 --- a/app/api/auth/route.js +++ b/app/api/auth/route.js @@ -9,7 +9,7 @@ export async function POST(req) { try { // Parse JSON body safely const body = await req.json() - const { email, password, captchaToken, action } = body || {} + const { email, password, captchaToken, action, name } = body || {} // Validate required fields if (!email || !password) { @@ -34,8 +34,11 @@ export async function POST(req) { } if (action === 'signup') { - // Create Supabase user - const { user, error } = await supabase.auth.admin.createUser({ email, password }) + // Create Supabase user with metadata + const { user, error } = await supabase.auth.signUp( + { email, password }, + { data: { display_name: name } } + ) if (error) { return new Response(JSON.stringify({ success: false, message: error.message }), { status: 400 }) } diff --git a/app/login/page.jsx b/app/login/page.jsx index 684a89a..fa65f82 100755 --- a/app/login/page.jsx +++ b/app/login/page.jsx @@ -1,85 +1,111 @@ -'use client' -import { useState, useEffect } from 'react' -import { supabase } from '../../lib/supabase' -import { useRouter } from 'next/navigation' -import { FiMail, FiLock, FiUser, FiLogIn, FiUserPlus, FiSun, FiMoon } from 'react-icons/fi' -import { motion } from 'framer-motion' -import Link from 'next/link' -import dynamic from 'next/dynamic' +"use client"; +import { useState, useEffect } from "react"; +import { supabase } from "../../lib/supabase"; +import { useRouter } from "next/navigation"; +import { + FiMail, + FiLock, + FiUser, + FiLogIn, + FiUserPlus, + FiSun, + FiMoon, +} from "react-icons/fi"; +import { motion } from "framer-motion"; +import Link from "next/link"; +import dynamic from "next/dynamic"; const Turnstile = dynamic( - () => import('@marsidev/react-turnstile').then((mod) => mod.Turnstile), + () => import("@marsidev/react-turnstile").then((mod) => mod.Turnstile), { ssr: false } -) +); export default function LoginPage() { - const [email, setEmail] = useState('') - const [password, setPassword] = useState('') - const [isLogin, setIsLogin] = useState(true) - const [loading, setLoading] = useState(false) - const [error, setError] = useState('') - const [theme, setTheme] = useState('light') - const [captchaToken, setCaptchaToken] = useState(null) - const router = useRouter() + const [email, setEmail] = useState(""); + const [password, setPassword] = useState(""); + const [name, setName] = useState(""); + const [isLogin, setIsLogin] = useState(true); + const [loading, setLoading] = useState(false); + const [error, setError] = useState(""); + const [theme, setTheme] = useState("light"); + const [captchaToken, setCaptchaToken] = useState(null); + const router = useRouter(); useEffect(() => { - const savedTheme = localStorage.getItem('theme') || 'light' - setTheme(savedTheme) - document.documentElement.classList.toggle('dark', savedTheme === 'dark') - }, []) + const savedTheme = localStorage.getItem("theme") || "light"; + setTheme(savedTheme); + document.documentElement.classList.toggle("dark", savedTheme === "dark"); + }, []); const toggleTheme = () => { - const newTheme = theme === 'light' ? 'dark' : 'light' - setTheme(newTheme) - localStorage.setItem('theme', newTheme) - document.documentElement.classList.toggle('dark', newTheme === 'dark') - } + const newTheme = theme === "light" ? "dark" : "light"; + setTheme(newTheme); + localStorage.setItem("theme", newTheme); + document.documentElement.classList.toggle("dark", newTheme === "dark"); + }; const handleAuth = async () => { - setLoading(true) - setError('') + setLoading(true); + setError(""); try { - if (!captchaToken) throw new Error('Please complete captcha') + if (!captchaToken) throw new Error("Please complete captcha"); if (isLogin) { // Verify captcha first via API route - const verifyRes = await fetch('/api/auth', { - method: 'POST', - headers: { 'Content-Type': 'application/json' }, - body: JSON.stringify({ email, password, captchaToken, action: 'login' }), - }) - const verifyData = await verifyRes.json() - if (!verifyData.success) throw new Error(verifyData.message || 'Captcha verification failed') + const verifyRes = await fetch("/api/auth", { + method: "POST", + headers: { "Content-Type": "application/json" }, + body: JSON.stringify({ + email, + password, + captchaToken, + action: "login", + }), + }); + const verifyData = await verifyRes.json(); + if (!verifyData.success) + throw new Error(verifyData.message || "Captcha verification failed"); // After captcha verified, login using frontend anon key - const { error } = await supabase.auth.signInWithPassword({ email, password }) - if (error) throw error + const { error } = await supabase.auth.signInWithPassword({ + email, + password, + }); + if (error) throw error; - router.push('/dashboard') + router.push("/dashboard"); } else { // Signup flow remains the same - const res = await fetch('/api/auth', { - method: 'POST', - headers: { 'Content-Type': 'application/json' }, - body: JSON.stringify({ email, password, captchaToken, action: 'signup' }), - }) - const data = await res.json() - if (!data.success) throw new Error(data.message || 'Signup failed') - alert(data.message) - setIsLogin(true) + const res = await fetch("/api/auth", { + method: "POST", + headers: { "Content-Type": "application/json" }, + body: JSON.stringify({ + email, + password, + captchaToken, + action: "signup", + name, + }), + }); + const data = await res.json(); + if (!data.success) throw new Error(data.message || "Signup failed"); + alert(data.message); + setIsLogin(true); } } catch (err) { - setError(err.message || 'Something went wrong') + setError(err.message || "Something went wrong"); } finally { - setLoading(false) + setLoading(false); } - } + }; const handleGoogleSignIn = async () => { - const { error } = await supabase.auth.signInWithOAuth({ provider: 'google' }) - if (error) console.error('Google sign-in error:', error.message) - } + const { error } = await supabase.auth.signInWithOAuth({ + provider: "google", + }); + if (error) console.error("Google sign-in error:", error.message); + }; return (
@@ -91,19 +117,54 @@ export default function LoginPage() { {/* Header */}
-

{isLogin ? 'Welcome Back' : 'Create Account'}

+

+ {isLogin ? "Welcome Back" : "Create Account"} +

- {isLogin ? 'Sign in to access your dashboard' : 'Join us to get started'} + {isLogin + ? "Sign in to access your dashboard" + : "Join us to get started"}

-
+
+ {/* Google OAuth */} + +
+ +
+
+ + or + +
+
+
{error && ( - + {error} )} @@ -145,6 +206,8 @@ export default function LoginPage() { type="text" className="w-full pl-10 pr-4 py-3 rounded-lg border border-gray-300 dark:border-gray-600 focus:outline-none focus:ring-2 focus:ring-blue-500 dark:bg-neutral-950 dark:text-gray-200" placeholder="Full name" + value={name} + onChange={(e) => setName(e.target.value)} />
)} @@ -162,19 +225,19 @@ export default function LoginPage() { disabled={loading} className={`w-full flex items-center justify-center py-3 px-4 rounded-lg text-white font-medium transition-all ${ loading - ? 'bg-gray-400 dark:bg-gray-600 cursor-not-allowed' - : 'bg-blue-600 hover:bg-blue-700 dark:hover:bg-blue-800 shadow-md hover:shadow-lg' + ? "bg-gray-400 dark:bg-gray-600 cursor-not-allowed" + : "bg-blue-600 hover:bg-blue-700 dark:hover:bg-blue-800 shadow-md hover:shadow-lg" }`} > {loading ? ( - 'Processing...' + "Processing..." ) : isLogin ? ( <> - Sign In + Continue ) : ( <> - Sign Up + Continue )} @@ -184,48 +247,45 @@ export default function LoginPage() {
{isLogin ? (

- Don't have an account?{' '} -

) : (

- Already have an account?{' '} -

)}
- {/* Google OAuth */} -
-
- or -
-
- - -
- By continuing, you agree to our{' '} - + By continuing, you agree to our{" "} + Terms of Service - {' '} - and{' '} - + {" "} + and{" "} + Privacy Policy
- ) -} \ No newline at end of file + ); +} diff --git a/app/visualizer/stack/implementation/usingLinkedList/animation.jsx b/app/visualizer/stack/implementation/usingLinkedList/animation.jsx deleted file mode 100755 index 714945f..0000000 --- a/app/visualizer/stack/implementation/usingLinkedList/animation.jsx +++ /dev/null @@ -1,41 +0,0 @@ -'use client'; -import Footer from '@/app/components/footer'; -import ExploreOther from '@/app/components/ui/exploreOther'; -import Content from'@/app/visualizer/stack/implementation/usingLinkedList/content'; -import CodeBlock from'@/app/visualizer/stack/implementation/usingLinkedList/codeBlock'; -import GoBackButton from "@/app/components/ui/goback"; -import BackToTop from "@/app/components/ui/backtotop"; - -const InfixToPostfixVisualizer = () => { - return ( -
-
- - { /* go back block here */} -
- -
- - { /* main logic here */} -

- Stack Implementation -

-
- -

- - -
-
- -
- ); -}; - -export default InfixToPostfixVisualizer; \ No newline at end of file diff --git a/app/visualizer/stack/implementation/usingLinkedList/codeBlock.jsx b/app/visualizer/stack/implementation/usingLinkedList/codeBlock.jsx index ceb35eb..2f095c2 100755 --- a/app/visualizer/stack/implementation/usingLinkedList/codeBlock.jsx +++ b/app/visualizer/stack/implementation/usingLinkedList/codeBlock.jsx @@ -452,10 +452,10 @@ int main() { initial={{ opacity: 0, y: 20 }} animate={{ opacity: 1, y: 0 }} transition={{ duration: 0.3 }} - className="bg-white dark:bg-gray-800 rounded-xl shadow-lg overflow-hidden border border-gray-200 dark:border-gray-700 transition-colors duration-300" + className="bg-white dark:bg-neutral-950 rounded-xl shadow-lg overflow-hidden border border-gray-200 dark:border-gray-700 transition-colors duration-300" > {/* Header */} -
+

diff --git a/app/visualizer/stack/implementation/usingLinkedList/content.jsx b/app/visualizer/stack/implementation/usingLinkedList/content.jsx index 4d5120d..1e3aa28 100755 --- a/app/visualizer/stack/implementation/usingLinkedList/content.jsx +++ b/app/visualizer/stack/implementation/usingLinkedList/content.jsx @@ -1,4 +1,29 @@ -const Content = () => { +"use client"; +import React from "react"; +import { useEffect, useState } from "react"; + +const content = () => { + const [theme, setTheme] = useState("light"); + const [mounted, setMounted] = useState(false); + + useEffect(() => { + const updateTheme = () => { + const savedTheme = localStorage.getItem("theme") || "light"; + setTheme(savedTheme); + }; + + updateTheme(); + setMounted(true); + + window.addEventListener("storage", updateTheme); + window.addEventListener("themeChange", updateTheme); + + return () => { + window.removeEventListener("storage", updateTheme); + window.removeEventListener("themeChange", updateTheme); + }; + }, []); + const paragraph = [ `A stack implemented using a linked list follows the LIFO (Last In First Out) principle. Unlike array implementation, linked list stacks dynamically allocate memory for each element and don't have size limitations (until memory is exhausted).`, ]; @@ -53,8 +78,37 @@ const Content = () => { ]; return ( -
-
+
+
+
+ {mounted && ( + + )} +
+
+ + Daily DSA Challenge by{" "} + + Hello World + + +
+
+
{/* Header Section */}

@@ -68,42 +122,22 @@ const Content = () => {

- {/* Core Operations */} -
-

- - Core Stack Operations -

-
- {["push(item)", "pop()", "peek()", "isEmpty()", "size()"].map((op) => ( -
- - {op} - -
- ))} -
-
- {/* Algorithmic Steps */}
-

- - Algorithmic Steps -

+

+ + Algorithmic Steps +

{/* Stack Basic Operations */} -
+

Stack Basic Operations

-
+
    {opeartions.map((item, index) => (
  • @@ -127,13 +161,13 @@ const Content = () => {
{/* Stack Helper Operations */} -
+

Stack Helper Operations

-
+
    {helper.map((item, index) => (
  • @@ -158,45 +192,6 @@ const Content = () => {
- {/* Visual Representation */} -
-

- - Visual Representation -

-
-
-
-
-
- Head -
-
-
-
8
-
(top)
-
-
-
-
- 17 -
-
-
- 42 -
-
-
- null -
-
-
-
- Stack after operations: push(42), push(17), push(8) -
-
-
- {/* Time Complexity */}

@@ -206,10 +201,10 @@ const Content = () => {
- - - - + + + @@ -224,13 +219,13 @@ const Content = () => { ].map(([op, comp, reason], index) => ( - - + - @@ -272,10 +267,10 @@ const Content = () => {
OperationComplexity +
OperationComplexity Reason
{op} + {op} {comp} + {reason}
- - - - + + + + @@ -288,13 +283,13 @@ const Content = () => { ].map(([feature, ll, arr], index) => ( - - + - @@ -308,4 +303,4 @@ const Content = () => { ); }; - export default Content; \ No newline at end of file + export default content; \ No newline at end of file diff --git a/app/visualizer/stack/implementation/usingLinkedList/page.jsx b/app/visualizer/stack/implementation/usingLinkedList/page.jsx index dff7373..e37954a 100755 --- a/app/visualizer/stack/implementation/usingLinkedList/page.jsx +++ b/app/visualizer/stack/implementation/usingLinkedList/page.jsx @@ -1,32 +1,106 @@ -import Animation from "@/app/visualizer/stack/implementation/usingLinkedList/animation"; import Navbar from "@/app/components/navbarinner"; +import Breadcrumbs from "@/app/components/ui/Breadcrumbs"; +import ArticleActions from "@/app/components/ui/ArticleActions"; +import Content from "@/app/visualizer/stack/implementation/usingLinkedList/content"; +import Code from "@/app/visualizer/stack/implementation/usingLinkedList/codeBlock"; +import ModuleCard from "@/app/components/ui/ModuleCard"; +import { MODULE_MAPS } from "@/lib/modulesMap"; +import Footer from "@/app/components/footer"; +import ExploreOther from "@/app/components/ui/exploreOther"; +import BackToTopButton from "@/app/components/ui/backtotop"; export const metadata = { - title: 'Stack Implementation using Linked List | Learn Stack in DSA with JS, C, Python, Java Code', - description: 'Explore how to implement a Stack using a Linked List with step-by-step visual explanations, animations, and complete code in JavaScript, C, Python, and Java. Ideal for DSA learners and coding interview prep.', - keywords: [ - 'Stack using Linked List', - 'Stack Implementation', - 'Stack Implementation in JavaScript', - 'Stack Implementation in C', - 'Stack Implementation in Python', - 'Stack Implementation in Java', - 'Linked List Stack', - 'DSA Stack', - 'Data Structures Stack', - 'Stack Push Pop Linked List', - 'Learn Stack DSA', - 'Visualize Stack Implementation', - 'Stack Code Examples', + title: + "Stack Implementation using Linked List | Learn Stack in DSA with JS, C, Python, Java Code", + description: + "Explore how to implement a Stack using a Linked List with step-by-step visual explanations, animations, and complete code in JavaScript, C, Python, and Java. Ideal for DSA learners and coding interview prep.", + keywords: [ + "Stack using Linked List", + "Stack Implementation", + "Stack Implementation in JavaScript", + "Stack Implementation in C", + "Stack Implementation in Python", + "Stack Implementation in Java", + "Linked List Stack", + "DSA Stack", + "Data Structures Stack", + "Stack Push Pop Linked List", + "Learn Stack DSA", + "Visualize Stack Implementation", + "Stack Code Examples", + ], + robots: "index, follow", + openGraph: { + images: [ + { + url: "/og/stack/stackLinkedList.png", + width: 1200, + height: 630, + alt: "Stack Implementation using Linked List", + }, ], - robots: 'index, follow', - }; + }, +}; -export default function Page(){ - return( +export default function Page() { + const paths = [ + { name: "Home", href: "/" }, + { name: "Visualizer", href: "/visualizer" }, + { name: "Stack : Implementation Using Linked List", href: "" }, + ]; + + return ( <> - - +
+ +
+ +
+
+
+ +
+ +
+
+

+ Stack +

+
+

+ Implementation Using Linked List +

+ +
+
+ +
+ +
+ +
+ +
+ +
+ +
+ +
+
+ + +
); -}; \ No newline at end of file +} diff --git a/lib/modulesMap.js b/lib/modulesMap.js index e630b2f..0430848 100755 --- a/lib/modulesMap.js +++ b/lib/modulesMap.js @@ -13,5 +13,5 @@ export const MODULE_MAPS = { postfix : "ca3daf8d-23f8-4ade-adfd-4bd0a88d3da2", prefix : "a2971df4-5e48-4320-bc91-3de3242cac48", stackArray : "4e0dd1e0-a8c7-4066-845c-b5917383d5c2", - stackLinkedList : "", + stackLinkedList : "69ecfabf-97d3-433e-972e-54ea4c91374f", } \ No newline at end of file diff --git a/public/modules/stackLinkedList.png b/public/modules/stackLinkedList.png new file mode 100755 index 0000000..2cf7450 Binary files /dev/null and b/public/modules/stackLinkedList.png differ diff --git a/public/og/stack/stackLinkedList.png b/public/og/stack/stackLinkedList.png new file mode 100755 index 0000000..c5e2fe0 Binary files /dev/null and b/public/og/stack/stackLinkedList.png differ
FeatureLinked ListArray
FeatureLinked ListArray
{feature} + {feature} {ll} + {arr}