update profile route and updated user page functionality
This commit is contained in:
parent
6af6da358b
commit
589c9e59c4
7 changed files with 128 additions and 81 deletions
|
@ -7,27 +7,42 @@ import { UserInfo } from "../models/UserInfo"
|
|||
export async function PUT(req){
|
||||
mongoose.connect(process.env.MONGO_URL)
|
||||
const data = await req.json();
|
||||
const session = await getServerSession(authOptions)
|
||||
const email = session.user.email
|
||||
const {name, image, ...otherUserInfo} = data
|
||||
|
||||
await User.updateOne({email}, {name, image});
|
||||
|
||||
//update userInfo
|
||||
await UserInfo.findOneAndUpdate({email}, otherUserInfo, {upsert:true});
|
||||
const {_id, name, image, ...otherUserInfo} = data;
|
||||
|
||||
let filter = {};
|
||||
if(_id) {
|
||||
filter = {_id}
|
||||
} else {
|
||||
const session = await getServerSession(authOptions);
|
||||
const email = session.user.email;
|
||||
filter = {email};
|
||||
}
|
||||
const user = await User.findOne(filter);
|
||||
await User.updateOne(filter, {name, image});
|
||||
await UserInfo.findOneAndUpdate({email:user.email}, otherUserInfo, {upsert:true});
|
||||
|
||||
return Response.json(true)
|
||||
}
|
||||
|
||||
export async function GET(){
|
||||
export async function GET(req){
|
||||
mongoose.connect(process.env.MONGO_URL)
|
||||
const session = await getServerSession(authOptions)
|
||||
const email = session?.user?.email
|
||||
if(!email){
|
||||
return Response.json({})
|
||||
const url = new URL(req.url);
|
||||
const _id = url.searchParams.get('_id');
|
||||
|
||||
let filterUser = {}
|
||||
if(_id) {
|
||||
filterUser={_id}
|
||||
|
||||
} else {
|
||||
const session = await getServerSession(authOptions)
|
||||
const email = session?.user?.email
|
||||
if(!email){
|
||||
return Response.json({})
|
||||
}
|
||||
filterUser = {email}
|
||||
}
|
||||
const user = await User.findOne({email}).lean()
|
||||
const userInfo = await UserInfo.findOne({email}).lean()
|
||||
const user = await User.findOne(filterUser).lean()
|
||||
const userInfo = await UserInfo.findOne({email:user.email}).lean()
|
||||
|
||||
return Response.json({...user, ...userInfo})
|
||||
}
|
|
@ -21,7 +21,7 @@ const LoginPage = () => {
|
|||
}
|
||||
|
||||
return (
|
||||
<div className='px-5 mt-10'>
|
||||
<div className='px-5 mt-10 mb-10'>
|
||||
<p className='text-center text-2xl font-semibold uppercase mb-5 text-[#FF5580]'>Login</p>
|
||||
<form className='block max-w-xs mx-auto' onSubmit={handleFormSubmit}>
|
||||
<input type='email' name="email" placeholder='Enter your email' value={email} onChange={ev => setEmail(ev.target.value)} disabled={loginInProgress} className=' disabled:bg-gray-300 disabled:cursor-not-allowed'/>
|
||||
|
|
|
@ -6,36 +6,22 @@ import React, { useEffect, useState } from 'react'
|
|||
import toast from 'react-hot-toast';
|
||||
import UserTabs from "../../components/layout/UserTab"
|
||||
import EditImage from "../../components/layout/EditImage"
|
||||
import UserForm from "../../components/layout/UserForm"
|
||||
|
||||
const ProfilePage = () => {
|
||||
//use session
|
||||
const session = useSession();
|
||||
const {status} = session;
|
||||
//profile update
|
||||
const [userName, setUserName] = useState('');
|
||||
const [image, setImage] = useState('');
|
||||
const [phoneNumber, setPhoneNumber] = useState('');
|
||||
const [streetAddress, setStreetAddress] = useState('');
|
||||
const [city, setCity] = useState('');
|
||||
const [stateProvince, setStateProvince] = useState('');
|
||||
const [zipCode, setZipCode] = useState('');
|
||||
const [country, setCountry] = useState('');
|
||||
const [user, setUser] = useState(null);
|
||||
const [isAdmin, setIsAdmin] = useState(false);
|
||||
const [profileFetchd, setProfileFetched] = useState(false);
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
if(status === 'authenticated'){
|
||||
setUserName(session.data.user.name)
|
||||
setImage(session.data.user.image)
|
||||
fetch('/api/profile').then(response => {
|
||||
response.json().then(data => {
|
||||
setPhoneNumber(data.phoneNumber);
|
||||
setStreetAddress(data.streetAddress);
|
||||
setCity(data.city);
|
||||
setStateProvince(data.stateProvince);
|
||||
setZipCode(data.zipCode);
|
||||
setCountry(data.country);
|
||||
setUser(data)
|
||||
setIsAdmin(data.admin);
|
||||
setProfileFetched(true);
|
||||
})
|
||||
|
@ -44,14 +30,14 @@ const ProfilePage = () => {
|
|||
},[session, status])
|
||||
|
||||
|
||||
async function handleInfoUpdate(ev){
|
||||
async function handleInfoUpdate(ev, data){
|
||||
ev.preventDefault()
|
||||
|
||||
const savingPromise = new Promise(async (resolve, reject) => {
|
||||
const response = await fetch('/api/profile', {
|
||||
method: 'PUT',
|
||||
headers: {'Content-Type': 'application/json'},
|
||||
body: JSON.stringify({name:userName, image, phoneNumber, streetAddress, city, stateProvince, zipCode, country}),
|
||||
body: JSON.stringify({data}),
|
||||
});
|
||||
if(response.ok)
|
||||
resolve()
|
||||
|
@ -78,48 +64,7 @@ const ProfilePage = () => {
|
|||
return (
|
||||
<div className='px-5 mb-10'>
|
||||
<UserTabs isAdmin={isAdmin}/>
|
||||
<div className='max-w-md mx-auto mt-10'>
|
||||
<div className='flex flex-col gap-2 justify-center items-center max-w-[100px] mx-auto'>
|
||||
<EditImage link={image} setLink={setImage}/>
|
||||
</div>
|
||||
<form className='mt-5 text-sm sm:text-base flex flex-col gap-0 sm:gap-1' onSubmit={handleInfoUpdate}>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Name</label>
|
||||
<input type='text' placeholder='Name' value={userName} onChange={ev => setUserName(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Email</label>
|
||||
<input type='text' value={session.data.user.email} disabled={true} className='disabled:bg-gray-200 disabled:text-gray-400'/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Phone number</label>
|
||||
<input type='tel' placeholder='Phone number' value={phoneNumber} onChange={ev => setPhoneNumber(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Street Address</label>
|
||||
<input type='text' placeholder='Address' value={streetAddress} onChange={ev => setStreetAddress(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>City</label>
|
||||
<input type='text' placeholder='City' value={city} onChange={ev => setCity(ev.target.value)}/>
|
||||
</div>
|
||||
<div className='flex flex-col sm:flex-row gap-0 sm:gap-2'>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>State/Province</label>
|
||||
<input type='text' placeholder='State/Province' value={stateProvince} onChange={ev => setStateProvince(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Zip/Postal code</label>
|
||||
<input type='text' placeholder='Zip/Postal code' value={zipCode} onChange={ev => setZipCode(ev.target.value)}/>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Country</label>
|
||||
<input type='text' placeholder='Country' value={country} onChange={ev => setCountry(ev.target.value)}/>
|
||||
</div>
|
||||
<button className='w-full bg-pink-500 text-white p-2 rounded-md hover:opacity-80 duration-300 disabled:cursor-not-allowed'>Save</button>
|
||||
</form>
|
||||
</div>
|
||||
<UserForm user={user} onSave={handleInfoUpdate}/>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -31,7 +31,7 @@ const RegisterPage = () => {
|
|||
}
|
||||
|
||||
return (
|
||||
<div className='px-5 mt-10'>
|
||||
<div className='px-5 mt-10 mb-10'>
|
||||
<p className='text-center text-2xl font-semibold uppercase mb-5 text-[#FF5580]'>Register</p>
|
||||
{userCreated && (
|
||||
<div className='my-4 text-center text-green-600 font-bold'>
|
||||
|
|
|
@ -1,10 +1,32 @@
|
|||
"use client"
|
||||
import React from 'react'
|
||||
import React, { use, useEffect, useState } from 'react'
|
||||
import UserTab from '../../../components/layout/UserTab'
|
||||
import useProfile from '../../../components/UseProfile';
|
||||
import UserForm from '../../../components/layout/UserForm';
|
||||
import { useParams } from 'next/navigation';
|
||||
|
||||
const EditUsersPage = () => {
|
||||
const {data, loading} = useProfile();
|
||||
const {id} = useParams();
|
||||
const [user, setUser] = useState(null);
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
fetch('/api/profile?_id='+id).then(res => {
|
||||
res.json().then(user => {
|
||||
setUser(user)
|
||||
})
|
||||
})
|
||||
}, [])
|
||||
|
||||
function handleSaveButton(ev, data){
|
||||
ev.preventDefault();
|
||||
fetch('/api/profile', {
|
||||
method: 'PUT',
|
||||
headers: {'Content-Type':'application/json'},
|
||||
body: JSON.stringify({...data, _id:id}),
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
@ -16,8 +38,11 @@ const EditUsersPage = () => {
|
|||
}
|
||||
|
||||
return (
|
||||
<div className='px-5'>
|
||||
<div className='px-5 mb-10'>
|
||||
<UserTab isAdmin={true}/>
|
||||
<div className='max-w-md mx-auto mt-10'>
|
||||
<UserForm user={user} onSave={handleSaveButton}/>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -28,7 +28,7 @@ const Userspage = () => {
|
|||
|
||||
|
||||
return (
|
||||
<div className='px-5'>
|
||||
<div className='px-5 mb-10'>
|
||||
<UserTab isAdmin={true}/>
|
||||
<div className='max-w-md mx-auto mt-10'>
|
||||
{users?.length > 0 && users.map(user => (
|
||||
|
|
62
donutshop_ecommerce/src/components/layout/UserForm.js
Normal file
62
donutshop_ecommerce/src/components/layout/UserForm.js
Normal file
|
@ -0,0 +1,62 @@
|
|||
"use client"
|
||||
import React, { useState } from 'react'
|
||||
import EditImage from '../../components/layout/EditImage'
|
||||
|
||||
const UserForm = ({user, onSave}) => {
|
||||
const [userName, setUserName] = useState(user?.name || '');
|
||||
const [image, setImage] = useState(user?.image || '');
|
||||
const [phoneNumber, setPhoneNumber] = useState(user?.phoneNumber || '');
|
||||
const [streetAddress, setStreetAddress] = useState(user?.streetAddress || '');
|
||||
const [city, setCity] = useState(user?.city || '');
|
||||
const [stateProvince, setStateProvince] = useState(user?.stateProvince || '');
|
||||
const [zipCode, setZipCode] = useState(user?.zipCode || '');
|
||||
const [country, setCountry] = useState(user?.country || '');
|
||||
|
||||
|
||||
return (
|
||||
<div className='max-w-md mx-auto mt-10'>
|
||||
<div className='flex flex-col gap-2 justify-center items-center max-w-[100px] mx-auto'>
|
||||
<EditImage link={image} setLink={setImage}/>
|
||||
</div>
|
||||
<form className='mt-5 text-sm sm:text-base flex flex-col gap-0 sm:gap-1' onSubmit={ev => onSave(ev, {name:userName, image, phoneNumber, streetAddress, city, stateProvince, zipCode, country,})}>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Name</label>
|
||||
<input type='text' placeholder='Name' value={userName} onChange={ev => setUserName(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Email</label>
|
||||
<input type='text' value={user.email} disabled={true} className='disabled:bg-gray-200 disabled:text-gray-400'/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Phone number</label>
|
||||
<input type='tel' placeholder='Phone number' value={phoneNumber} onChange={ev => setPhoneNumber(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Street Address</label>
|
||||
<input type='text' placeholder='Address' value={streetAddress} onChange={ev => setStreetAddress(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>City</label>
|
||||
<input type='text' placeholder='City' value={city} onChange={ev => setCity(ev.target.value)}/>
|
||||
</div>
|
||||
<div className='flex flex-col sm:flex-row gap-0 sm:gap-2'>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>State/Province</label>
|
||||
<input type='text' placeholder='State/Province' value={stateProvince} onChange={ev => setStateProvince(ev.target.value)}/>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Zip/Postal code</label>
|
||||
<input type='text' placeholder='Zip/Postal code' value={zipCode} onChange={ev => setZipCode(ev.target.value)}/>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<label className='text-gray-700 text-sm font-semibold'>Country</label>
|
||||
<input type='text' placeholder='Country' value={country} onChange={ev => setCountry(ev.target.value)}/>
|
||||
</div>
|
||||
<button className='w-full bg-pink-500 text-white p-2 rounded-md hover:opacity-80 duration-300 disabled:cursor-not-allowed'>Save</button>
|
||||
</form>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
export default UserForm
|
Loading…
Add table
Reference in a new issue