diff --git a/Geeks code with firebase/geeks/package-lock.json b/Geeks code with firebase/geeks/package-lock.json index dbe74c40..70b7b71f 100644 --- a/Geeks code with firebase/geeks/package-lock.json +++ b/Geeks code with firebase/geeks/package-lock.json @@ -15,6 +15,7 @@ "firebase": "^9.20.0", "react": "^18.2.0", "react-dom": "^18.2.0", + "react-helmet": "^6.1.0", "react-icons": "^4.8.0", "react-router-dom": "^6.10.0", "react-scripts": "5.0.1", @@ -15087,6 +15088,25 @@ "resolved": "https://registry.npmjs.org/react-error-overlay/-/react-error-overlay-6.0.11.tgz", "integrity": "sha512-/6UZ2qgEyH2aqzYZgQPxEnz33NJ2gNsnHA2o5+o4wW9bLM/JYQitNP9xPhsXwC08hMMovfGe/8retsdDsczPRg==" }, + "node_modules/react-fast-compare": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/react-fast-compare/-/react-fast-compare-3.2.2.tgz", + "integrity": "sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==" + }, + "node_modules/react-helmet": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/react-helmet/-/react-helmet-6.1.0.tgz", + "integrity": "sha512-4uMzEY9nlDlgxr61NL3XbKRy1hEkXmKNXhjbAIOVw5vcFrsdYbH2FEwcNyWvWinl103nXgzYNlns9ca+8kFiWw==", + "dependencies": { + "object-assign": "^4.1.1", + "prop-types": "^15.7.2", + "react-fast-compare": "^3.1.1", + "react-side-effect": "^2.1.0" + }, + "peerDependencies": { + "react": ">=16.3.0" + } + }, "node_modules/react-icons": { "version": "4.8.0", "resolved": "https://registry.npmjs.org/react-icons/-/react-icons-4.8.0.tgz", @@ -15210,6 +15230,14 @@ } } }, + "node_modules/react-side-effect": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/react-side-effect/-/react-side-effect-2.1.2.tgz", + "integrity": "sha512-PVjOcvVOyIILrYoyGEpDN3vmYNLdy1CajSFNt4TDsVQC5KpTijDvWVoR+/7Rz2xT978D8/ZtFceXxzsPwZEDvw==", + "peerDependencies": { + "react": "^16.3.0 || ^17.0.0 || ^18.0.0" + } + }, "node_modules/read-cache": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/read-cache/-/read-cache-1.0.0.tgz", diff --git a/Geeks code with firebase/geeks/package.json b/Geeks code with firebase/geeks/package.json index bd018ddc..3072aa99 100644 --- a/Geeks code with firebase/geeks/package.json +++ b/Geeks code with firebase/geeks/package.json @@ -10,6 +10,7 @@ "firebase": "^9.20.0", "react": "^18.2.0", "react-dom": "^18.2.0", + "react-helmet": "^6.1.0", "react-icons": "^4.8.0", "react-router-dom": "^6.10.0", "react-scripts": "5.0.1", diff --git a/Geeks code with firebase/geeks/public/favicon.ico b/Geeks code with firebase/geeks/public/favicon.ico deleted file mode 100644 index a11777cc..00000000 Binary files a/Geeks code with firebase/geeks/public/favicon.ico and /dev/null differ diff --git a/Geeks code with firebase/geeks/public/index.html b/Geeks code with firebase/geeks/public/index.html index aa069f27..611a8a4c 100644 --- a/Geeks code with firebase/geeks/public/index.html +++ b/Geeks code with firebase/geeks/public/index.html @@ -2,7 +2,7 @@ - + - React App + Geeks Hub diff --git a/Geeks code with firebase/geeks/public/logo192.png b/Geeks code with firebase/geeks/public/logo192.png deleted file mode 100644 index fc44b0a3..00000000 Binary files a/Geeks code with firebase/geeks/public/logo192.png and /dev/null differ diff --git a/Geeks code with firebase/geeks/public/logo512.png b/Geeks code with firebase/geeks/public/logo512.png deleted file mode 100644 index a4e47a65..00000000 Binary files a/Geeks code with firebase/geeks/public/logo512.png and /dev/null differ diff --git a/Geeks code with firebase/geeks/src/ActiveUsers.js b/Geeks code with firebase/geeks/src/ActiveUsers.js index f665e77c..6f8cb37e 100644 --- a/Geeks code with firebase/geeks/src/ActiveUsers.js +++ b/Geeks code with firebase/geeks/src/ActiveUsers.js @@ -109,10 +109,10 @@ function ActiveUsers() { trial.RemaningHours = 0; trial.isSub = false; - price = Math.round(time * 10) ; + price = Math.round(time * 100)/100 ; } } else { - price = Math.round(time * 10) ; + price = Math.round(time * 100)/100 ; } console.log("price i" + price); diff --git a/Geeks code with firebase/geeks/src/EmployeesAdmin.js b/Geeks code with firebase/geeks/src/EmployeesAdmin.js index cf3432b9..195f3f04 100644 --- a/Geeks code with firebase/geeks/src/EmployeesAdmin.js +++ b/Geeks code with firebase/geeks/src/EmployeesAdmin.js @@ -29,14 +29,14 @@ const{authUserData , setauthUserData, update , setUpdate} = useContext(UserConte //this is the state for the modal that shows when the user is is active status is updated const [showModal, setShowModal] = useState(false); -// this is the state shown in the modal of the add employee modal -const [showAddEmployeeModal, setShowAddEmployeeModal] = useState(false); +// show the modal for the add employee +const [showAddModal, setShowAddModal] = useState(false); + +//this is the state for the email of the new employee +const [email, setEmail] = useState(''); + -//this is for the new employee email -const [newEmployeeEmail, setNewEmployeeEmail] = useState(''); -//this is for the new employee data -const [empData,setEmpData] = useState({}); @@ -73,15 +73,63 @@ const [empData,setEmpData] = useState({}); await updateDoc(userRef, { isWorking: false, thisMonth : activeShift.thisMonth + 1, + }); await setUpdate(update + 1); setShowModal(true); + } + // this is the function for the admin to add a new employee by search in users collection by emaail an check that the user is not already an employee the add him to emplyee collection + const addEmployee = async (email) => { + //get all users docs + const users = collection(db, 'users'); + const data = await getDocs(users); + //filter the user by email + const filteredData = data.docs.map((doc) => ({ + id: doc.id, + + ...doc.data() + })).filter((user) => user.Email === email); + //if the user is found add him to the employee collection + if (filteredData.length > 0) { + const userRef = doc(db, 'users', filteredData[0].id); + const employeeRef = doc(db, 'employees', filteredData[0].id); + const employeeDocSnap = await getDoc(employeeRef); + if (!employeeDocSnap.exists()) { + await setDoc(employeeRef, { + name: filteredData[0].Name, + email: filteredData[0].Email, + isWorking: false, + thisMonth: 0, + prevMonth: 0, + } + + + ); + + await updateDoc(userRef, { + isEmployee: true, + + }); + + setShowAddModal(false); + + + } + else { + alert('this user is already an employee'); + } + + + + } +} + // this is the function for the admin to add a new employee @@ -144,7 +192,47 @@ const [empData,setEmpData] = useState({});
) : null} - +{showAddModal ? ( + <> +
+
+ {/*content*/} +
+ {/*header*/} +
+

+ Add New employee +

+ +
+ {/*body*/} + + {/*footer*/} +
+ setEmail(e.target.value)} /> + + +
+
+
+
+
+ + ) : null} @@ -219,7 +307,7 @@ add employee button */}
- +
@@ -257,9 +345,9 @@ add employee button */} scope="row" class="px-6 py-4 font-medium text-gray-900 whitespace-nowrap dark:text-white" > - {employee.Name} + {employee.name && employee.name } - {employee.Email} + {employee.email} {employee.thisMonth} {employee.prevMonth} diff --git a/Geeks code with firebase/geeks/src/LandingPage.js b/Geeks code with firebase/geeks/src/LandingPage.js index b896d6d2..9562ef75 100644 --- a/Geeks code with firebase/geeks/src/LandingPage.js +++ b/Geeks code with firebase/geeks/src/LandingPage.js @@ -4,9 +4,19 @@ import Header from './components/Header'; import Footer from './components/Footer'; import Features from './components/Features'; import Pricing from './components/Pricing'; +import { Helmet } from 'react-helmet'; + function LandingPage() { return ( + <> + + + +
@@ -61,6 +71,7 @@ function LandingPage() {
+ ); } diff --git a/Geeks code with firebase/geeks/src/Login.js b/Geeks code with firebase/geeks/src/Login.js index 79994647..6982443e 100644 --- a/Geeks code with firebase/geeks/src/Login.js +++ b/Geeks code with firebase/geeks/src/Login.js @@ -14,9 +14,15 @@ export default function Login() { const { user, setUser } = useContext(AuthContext); const [email, setEmail] = useState(''); const [password, setPassword] = useState(''); + const [error, setError] = useState(null); const handleSubmit = async (event) => { event.preventDefault(); + if (!email || !password) { + setError('Please enter email and password'); + return; + } + else { try { const userCredential = await signInWithEmailAndPassword(auth, email, password); const user = userCredential.user; @@ -41,13 +47,16 @@ export default function Login() { setUser(null); } } catch (error) { - console.log(error); + setError(error.message); + + } + } }; return ( -
-
+ +
@@ -66,33 +75,26 @@ export default function Login() { {/* Username input */}
setEmail(event.target.value)} /> - +
{/* Password input */}
setPassword(event.target.value)} placeholder="Password" /> - +
{/* Submit button */} @@ -102,6 +104,7 @@ export default function Login() { type="submit" data-te-ripple-init data-te-ripple-color="light" + onClick={handleSubmit} style={{ background: "linear-gradient(to right, #4F46E5, #8B55E0, #4338CA)", @@ -113,7 +116,8 @@ export default function Login() { {/* Forgot password link */} {/* Forgot password? */}
- + {error &&

{error}

+ } {/* Register button */}

Don't have an account?

@@ -126,6 +130,8 @@ export default function Login() { > Register + +
@@ -153,6 +159,5 @@ export default function Login() {
-
); } \ No newline at end of file diff --git a/Geeks code with firebase/geeks/src/NewUser.js b/Geeks code with firebase/geeks/src/NewUser.js index 7b6965c3..7306479a 100644 --- a/Geeks code with firebase/geeks/src/NewUser.js +++ b/Geeks code with firebase/geeks/src/NewUser.js @@ -8,6 +8,8 @@ import { useContext } from 'react'; import {useNavigate} from 'react-router-dom' import { Gprovider } from './config/firebase'; import { getDoc } from 'firebase/firestore' +import {MdAssuredWorkload} from 'react-icons/md' +import {AiTwotonePhone} from 'react-icons/ai' export default function NewUser() { @@ -30,6 +32,12 @@ export default function NewUser() { const handleSubmit = async (e) => { e.preventDefault() + if( Password !== ConfirmPassword || !FirstName || !LastName || !Email || !Password || !PhoneNumber || !Faculty) + { + setError('Please enter all fields correctly') + return; + } + else{ try{ await createUserWithEmailAndPassword(auth, Email,Password) .then (async (userCredential) => { @@ -50,6 +58,7 @@ export default function NewUser() { [] ,id : user.uid ,subRequest: false + ,isBlocked : false }) }) @@ -67,66 +76,13 @@ export default function NewUser() { } catch(error){ - console.log(error) + setError(error.message) } - + } } -const handleSignInWithGoogle = async () => { - try{ - await signInWithPopup(auth, Gprovider) - .then (async (userCredential) => { - const user = userCredential.user; - console.log(user) - await setDoc(doc(users, user.uid), { - Name : user.displayName, - Email: user.email, - PhoneNumber: '', - Faculty: '', - Password: '', - isAdmin : false, - isEmployee : false, - isActive : false, - isSub : false, - RemaningHours : 0, - Reservations : [], - id : user.uid - ,subRequest: false - - }) - }) - - setUser(auth.currentUser); - console.log(auth.currentUser); - - - - } - catch(error){ - console.log(error) - } - - - const userDocRef = doc(db, "users", auth.currentUser.uid); - - const userDocSnap = await getDoc(userDocRef); - - if (userDocSnap.exists()) { - console.log('User document exists'); - if (userDocSnap.data().isAdmin) { - navigate('/admin'); - } - else { - navigate('/home'); - } - // do something with the user document - } else { - console.log('User document does not exist'); - } - -} const tohome = () =>{ navigate('/'); } @@ -167,9 +123,9 @@ const tohome = () =>{ navigate('/'); }

Hello Again!

+ ="text-gray-800 font-bold text-2xl mb-1">Welcome to Geeks Hub

Welcome Back

+ ="text-sm font-normal text-gray-600 mb-7">

{/* first name */}
@@ -180,17 +136,17 @@ const tohome = () =>{ navigate('/'); } clip-rule="evenodd" /> setFirstName(e.target.value)} type="text" name="" id="" placeholder="Full name" /> + =" pl-2 outline-none border-none" onChange={(e) => setFirstName(e.target.value)} type="text" name="" id="" placeholder="First Name" />
{/* last name */}
- - + ="h-5 w-5 text-gray-400" viewBox="0 0 20 20" + fill="currentColor"> + + setLastName(e.target.value)} />
@@ -204,7 +160,10 @@ const tohome = () =>{ navigate('/'); } d="M16 12a4 4 0 10-8 0 4 4 0 008 0zm0 0v1.5a2.5 2.5 0 005 0V12a9 9 0 10-9 9m4.5-1.206a8.959 8.959 0 01-4.5 1.207" /> setEmail(e.target.value)} /> + + =" pl-2 outline-none border-none" type="Email" name="" id="" placeholder="Email Address" onChange={(e)=>setEmail(e.target.value)} + + /> {/* password */}
{ navigate('/'); } clip-rule="evenodd" /> setPassword(e.target.value)} /> + =" pl-2 outline-none border-none" type="password" name="" id="" placeholder="Password" onChange={(e) => setPassword(e.target.value)} />
{/* confirm password */}
+ ="flex items-center border-2 mt-2 py-2 px-3 rounded-2xl"> @@ -229,39 +188,31 @@ const tohome = () =>{ navigate('/'); } d="M5 9V7a5 5 0 0110 0v2a2 2 0 012 2v5a2 2 0 01-2 2H5a2 2 0 01-2-2v-5a2 2 0 012-2zm8-2v2H7V7a3 3 0 016 0z" clip-rule="evenodd" /> - + setConfirmPassword(e.target.value)} + className + =" pl-2 outline-none border-none" type="password" name="" id="" placeholder="confirm password" />
{/* phone number*/}
- - - + ="flex items-center border-2 mt-2 py-2 px-3 rounded-2xl"> + + setPhoneNumber(e.target.value)} />
{/* your faculty */}
- - - + ="flex items-center border-2 mt-2 py-2 px-3 rounded-2xl"> + + setFaculty(e.target.value)} />
+ {error &&

{error}

} - Forgot Password ? +