├── .gitignore ├── .npmrc ├── Client ├── .npmrc ├── build │ ├── favicon.ico │ ├── static │ │ ├── media │ │ │ ├── 1.c8d0a91f56308d85d671.png │ │ │ ├── s1.d188ee8ecd63e9f254da.jpg │ │ │ ├── s2.6c3a0fe2972d6b7d302a.jpg │ │ │ ├── s3.6af90c49ed3ead48f32b.jpg │ │ │ ├── s4.af6c2349bff585218d85.jpg │ │ │ ├── FFHero.e177b3dcf2d8079f7777.jpg │ │ │ ├── PJImg.a5c9e3f030dedd161f19.jpg │ │ │ ├── bhanu.128f6fa3936a77691bc5.jpg │ │ │ ├── harsh.f73562890cfbf477cfef.jpg │ │ │ ├── osama.7bc61991c5c041b4fbe0.jpg │ │ │ ├── Features.e6e085e5cc62509c9481.png │ │ │ ├── card-bg.71550beb9e90b0170350.jpg │ │ │ ├── logistics.4d159b76b1bdfe5a8f33.jpg │ │ │ ├── accountant.76fdc2ac7417a91763b1.jpg │ │ │ ├── data_entry.5cf7fe547607d3a39fb9.png │ │ │ ├── glass-right.ea24b06211e2d2217247.png │ │ │ ├── graphic_design.58143d82fe784f1642fc.png │ │ │ ├── video_editing.d1cb7df110e127d85470.png │ │ │ ├── article_writing.73015a83047882b467b8.png │ │ │ ├── android_developer.cdf54b267c58f829b53c.png │ │ │ ├── freelansters-logo.3eb14736e8d3ce1c83e5.png │ │ │ └── freelansters-logo1.2c679b5600aeb404d11a.png │ │ └── js │ │ │ └── main.fe490bc1.js.LICENSE.txt │ ├── asset-manifest.json │ └── index.html ├── public │ ├── favicon.ico │ └── index.html ├── src │ ├── vercel.json │ ├── Components │ │ ├── GetHired.jsx │ │ ├── Logout.jsx │ │ ├── ProStars.jsx │ │ ├── FFlancer.jsx │ │ ├── ProfileData.jsx │ │ ├── GoToTop.jsx │ │ ├── Cards.jsx │ │ ├── Breadcrumb.jsx │ │ ├── Error.jsx │ │ ├── Hero.jsx │ │ ├── Footer.jsx │ │ ├── Cdata.jsx │ │ ├── SingleJob.jsx │ │ ├── ProfileCards.jsx │ │ ├── CateCards.css │ │ ├── PostJobs.jsx │ │ ├── Navbar.jsx │ │ ├── Profile.jsx │ │ ├── About.jsx │ │ ├── CateCards.jsx │ │ └── Filter.jsx │ ├── reducer │ │ ├── UseReducer.js │ │ ├── freelancerReducer.js │ │ ├── jobReducer.js │ │ └── filterReducer.js │ ├── Helpers │ │ └── FormatPrice.js │ ├── index.js │ ├── schemas │ │ └── index.jsx │ ├── Img │ │ └── imgindex.js │ ├── Styles │ │ ├── GlobalStyle.js │ │ └── Modal.scss │ ├── context │ │ ├── filtercontext.js │ │ ├── freelancercontext.js │ │ └── jobcontext.js │ ├── FindFreelancer.js │ ├── FindJobs.js │ ├── Routing.jsx │ ├── App.css │ └── Login.css ├── .gitignore └── package.json ├── Server ├── db │ └── conn.js ├── model │ ├── FFSchema.js │ ├── FJSchema.js │ ├── tempSchema.js │ └── userSchema.js ├── middleware │ └── authenticate.js ├── package.json ├── server.js ├── .gitignore └── router │ └── auth.js ├── LICENSE └── README.md /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | legacy-peer-deps=true 2 | -------------------------------------------------------------------------------- /Client/.npmrc: -------------------------------------------------------------------------------- 1 | legacy-peer-deps=true 2 | -------------------------------------------------------------------------------- /Client/build/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/favicon.ico -------------------------------------------------------------------------------- /Client/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/public/favicon.ico -------------------------------------------------------------------------------- /Client/src/vercel.json: -------------------------------------------------------------------------------- 1 | { 2 | "rewrites": [{ 3 | "source": "/(.*)", 4 | "destination": "/" }] 5 | } -------------------------------------------------------------------------------- /Client/build/static/media/1.c8d0a91f56308d85d671.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/1.c8d0a91f56308d85d671.png -------------------------------------------------------------------------------- /Client/build/static/media/s1.d188ee8ecd63e9f254da.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/s1.d188ee8ecd63e9f254da.jpg -------------------------------------------------------------------------------- /Client/build/static/media/s2.6c3a0fe2972d6b7d302a.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/s2.6c3a0fe2972d6b7d302a.jpg -------------------------------------------------------------------------------- /Client/build/static/media/s3.6af90c49ed3ead48f32b.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/s3.6af90c49ed3ead48f32b.jpg -------------------------------------------------------------------------------- /Client/build/static/media/s4.af6c2349bff585218d85.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/s4.af6c2349bff585218d85.jpg -------------------------------------------------------------------------------- /Client/build/static/media/FFHero.e177b3dcf2d8079f7777.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/FFHero.e177b3dcf2d8079f7777.jpg -------------------------------------------------------------------------------- /Client/build/static/media/PJImg.a5c9e3f030dedd161f19.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/PJImg.a5c9e3f030dedd161f19.jpg -------------------------------------------------------------------------------- /Client/build/static/media/bhanu.128f6fa3936a77691bc5.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/bhanu.128f6fa3936a77691bc5.jpg -------------------------------------------------------------------------------- /Client/build/static/media/harsh.f73562890cfbf477cfef.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/harsh.f73562890cfbf477cfef.jpg -------------------------------------------------------------------------------- /Client/build/static/media/osama.7bc61991c5c041b4fbe0.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/osama.7bc61991c5c041b4fbe0.jpg -------------------------------------------------------------------------------- /Client/build/static/media/Features.e6e085e5cc62509c9481.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/Features.e6e085e5cc62509c9481.png -------------------------------------------------------------------------------- /Client/build/static/media/card-bg.71550beb9e90b0170350.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/card-bg.71550beb9e90b0170350.jpg -------------------------------------------------------------------------------- /Client/build/static/media/logistics.4d159b76b1bdfe5a8f33.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/logistics.4d159b76b1bdfe5a8f33.jpg -------------------------------------------------------------------------------- /Client/build/static/media/accountant.76fdc2ac7417a91763b1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/accountant.76fdc2ac7417a91763b1.jpg -------------------------------------------------------------------------------- /Client/build/static/media/data_entry.5cf7fe547607d3a39fb9.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/data_entry.5cf7fe547607d3a39fb9.png -------------------------------------------------------------------------------- /Client/build/static/media/glass-right.ea24b06211e2d2217247.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/glass-right.ea24b06211e2d2217247.png -------------------------------------------------------------------------------- /Client/src/Components/GetHired.jsx: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | const GetHired = () => { 4 | return
Work In Progress!
; 5 | }; 6 | 7 | export default GetHired; 8 | -------------------------------------------------------------------------------- /Client/build/static/media/graphic_design.58143d82fe784f1642fc.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/graphic_design.58143d82fe784f1642fc.png -------------------------------------------------------------------------------- /Client/build/static/media/video_editing.d1cb7df110e127d85470.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/video_editing.d1cb7df110e127d85470.png -------------------------------------------------------------------------------- /Client/build/static/media/article_writing.73015a83047882b467b8.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/article_writing.73015a83047882b467b8.png -------------------------------------------------------------------------------- /Client/build/static/media/android_developer.cdf54b267c58f829b53c.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/android_developer.cdf54b267c58f829b53c.png -------------------------------------------------------------------------------- /Client/build/static/media/freelansters-logo.3eb14736e8d3ce1c83e5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/freelansters-logo.3eb14736e8d3ce1c83e5.png -------------------------------------------------------------------------------- /Client/build/static/media/freelansters-logo1.2c679b5600aeb404d11a.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Bhanu1776/Freelansters/HEAD/Client/build/static/media/freelansters-logo1.2c679b5600aeb404d11a.png -------------------------------------------------------------------------------- /Client/src/reducer/UseReducer.js: -------------------------------------------------------------------------------- 1 | export const initialState = null; 2 | 3 | export const reducer = (state, action) => { 4 | if (action.type === "USER") { 5 | return action.payload; 6 | } 7 | 8 | return state; 9 | } -------------------------------------------------------------------------------- /Server/db/conn.js: -------------------------------------------------------------------------------- 1 | const mongoose = require('mongoose'); 2 | 3 | const DB = process.env.DATABASE; 4 | 5 | mongoose.connect(DB).then(() => { 6 | console.log('connection successful'); 7 | }).catch((err) => console.log('Connection Unsuccessful :(')); 8 | -------------------------------------------------------------------------------- /Client/src/Helpers/FormatPrice.js: -------------------------------------------------------------------------------- 1 | const FormatPrice=({price})=>{ 2 | return Intl.NumberFormat("en-IN",{ 3 | style:"currency", 4 | currency:'INR', 5 | maximumFractionDigits:2, 6 | }).format(price); 7 | }; 8 | 9 | export default FormatPrice -------------------------------------------------------------------------------- /Client/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | .env 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /Client/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom/client'; 3 | import { GlobalStyle } from './Styles/GlobalStyle'; 4 | import "swiper/css/bundle"; 5 | import Routing from './Routing' 6 | 7 | const root = ReactDOM.createRoot(document.getElementById('root')); 8 | 9 | 10 | root.render( 11 | <> 12 | 13 | 14 | 15 | 16 | 17 | 18 | ); -------------------------------------------------------------------------------- /Client/src/schemas/index.jsx: -------------------------------------------------------------------------------- 1 | import * as Yup from "yup"; 2 | 3 | export const signUpSchema = Yup.object({ 4 | name: Yup.string().min(2).max(25).required('Please Enter your name'), 5 | email: Yup.string().email().required('Please Enter your email'), 6 | phone: Yup.string().min(10).max(13).required('Please Enter your number'), 7 | password: Yup.string().min(8).required('Please Enter your Password'), 8 | cpassword: Yup.string().required().oneOf([Yup.ref("password"), null], "Password must match") 9 | }) -------------------------------------------------------------------------------- /Server/model/FFSchema.js: -------------------------------------------------------------------------------- 1 | const mongoose = require('mongoose'); 2 | 3 | 4 | const FFSchema = new mongoose.Schema({ 5 | title: { 6 | type: String, 7 | required: true 8 | }, 9 | hours: { 10 | type: Number, 11 | required: true 12 | }, 13 | price: { 14 | type: Number, 15 | required: true 16 | }, 17 | name: { 18 | type: String, 19 | required: true 20 | }, 21 | 22 | }, { 23 | timestamps: true 24 | }) 25 | 26 | //* Collection Creation 27 | const Freelancers = mongoose.model('Freelancers', FFSchema) 28 | 29 | module.exports = Freelancers; -------------------------------------------------------------------------------- /Server/middleware/authenticate.js: -------------------------------------------------------------------------------- 1 | const jwt = require('jsonwebtoken') 2 | const User = require('../model/userSchema'); 3 | 4 | const Authenticate = async (req, res, next) => { 5 | try { 6 | const token = req.cookies.jwtoken1; 7 | const verifyToken = jwt.verify(token, process.env.SECRET_KEY); 8 | 9 | const rootUser = await User.findOne({ _id: verifyToken._id, "tokens.token": token }) 10 | 11 | if (!rootUser) { throw new Error('User Not Found!') } 12 | 13 | req.token = token; 14 | req.rootUser = rootUser; 15 | req.userId = rootUser._id; 16 | 17 | next(); 18 | } 19 | catch (err) { 20 | res.status(401).send('Unauthorized:No token provided'); 21 | console.log("🚀 ~ file: authenticate.js:22 ~ Authenticate ~ err", err) 22 | } 23 | } 24 | 25 | module.exports = Authenticate; 26 | 27 | -------------------------------------------------------------------------------- /Server/model/FJSchema.js: -------------------------------------------------------------------------------- 1 | const mongoose = require('mongoose'); 2 | 3 | 4 | const FJSchema = new mongoose.Schema({ 5 | category: { 6 | type: String, 7 | // required: true 8 | }, 9 | title: { 10 | type: String, 11 | required: true 12 | }, 13 | date: { 14 | type: String, 15 | // required: true 16 | }, 17 | duration: { 18 | type: String, 19 | // required: true 20 | }, 21 | description: { 22 | type: String, 23 | required: true 24 | }, 25 | price: { 26 | type: String, 27 | // required: true 28 | }, 29 | image: { 30 | type: String, 31 | // required: true 32 | }, 33 | 34 | }, { 35 | timestamps: true 36 | }) 37 | 38 | //* Collection Creation 39 | const Jobs = mongoose.model('Jobs', FJSchema) 40 | 41 | module.exports = Jobs; -------------------------------------------------------------------------------- /Client/src/reducer/freelancerReducer.js: -------------------------------------------------------------------------------- 1 | const FreelancerReducer = (state, action) => { 2 | switch (action.type) { 3 | case "SET_LOADING": 4 | return { 5 | ...state, 6 | isLoading: true, 7 | }; 8 | 9 | case "SET_API_DATA": 10 | // const featureData = action.payload.filter((curElem)=>{ 11 | // return curElem.featured === true; 12 | // }); 13 | 14 | return { 15 | ...state, 16 | isLoading: false, 17 | freelancer: action.payload, 18 | // featureJobs: featureData, 19 | } 20 | 21 | case "API_ERROR": 22 | return { 23 | ...state, 24 | isLoading: false, 25 | isError: true, 26 | }; 27 | 28 | default: 29 | return state; 30 | } 31 | } 32 | 33 | export default FreelancerReducer; -------------------------------------------------------------------------------- /Client/src/Components/Logout.jsx: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useContext } from "react"; 2 | import { useNavigate } from "react-router-dom"; 3 | import { UserContext } from "../Routing"; 4 | /* eslint-disable no-unused-vars */ 5 | 6 | const Logout = () => { 7 | const { state, dispatch } = useContext(UserContext); 8 | 9 | const navigate = useNavigate(); 10 | 11 | // * Promises 12 | useEffect(() => { 13 | fetch(process.env.BACKEND_URL+"/Logout", { 14 | method: "GET", 15 | headers: { 16 | Accept: "application/json", 17 | "Content-Type": "application/json", 18 | }, 19 | credentials: "include", 20 | }) 21 | .then((res) => { 22 | dispatch({ type: "USER", payload: false }); 23 | navigate("/Login"); 24 | if (!res.status === 200) { 25 | const error = new Error(res.error); 26 | throw error; 27 | } 28 | }) 29 | .catch((err) => { 30 | console.log(err); 31 | }); 32 | }); 33 | 34 | return
Logout
; 35 | }; 36 | 37 | export default Logout; 38 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022 Bhanu Sunka 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Client/src/Components/ProStars.jsx: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { FaStar, FaStarHalfAlt } from "react-icons/fa"; 3 | import { AiOutlineStar } from "react-icons/ai"; 4 | import styled from "styled-components"; 5 | 6 | const ProStars = ({ stars, reviews }) => { 7 | const ratingStar = Array.from({ length: 5 }, (elem, index) => { 8 | let number = index + 0.5; 9 | 10 | return ( 11 | 12 | {stars >= index + 1 ? ( 13 | 14 | ) : stars >= number ? ( 15 | 16 | ) : ( 17 | 18 | )} 19 | 20 | ); 21 | }); 22 | return ( 23 | 24 |
{ratingStar}
25 |
26 | ); 27 | }; 28 | const Wrapper = styled.section` 29 | .icon-style { 30 | display: flex; 31 | align-items: center; 32 | justify-content: flex-start; 33 | 34 | .icon { 35 | font-size: 1.7rem; 36 | color: orange; 37 | } 38 | .empty-icon { 39 | font-size: 2.6rem; 40 | } 41 | } 42 | `; 43 | 44 | export default ProStars; 45 | -------------------------------------------------------------------------------- /Server/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "freelansters", 3 | "version": "1.0.0", 4 | "description": "Backend for Freelansters", 5 | "main": "server.js", 6 | "scripts": { 7 | "start": "node server.js" 8 | }, 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/Bhanu1776/Freelansters" 12 | }, 13 | "keywords": [ 14 | "Express", 15 | "Mongodb", 16 | "NodeJS" 17 | ], 18 | "author": "Bhanu1776", 19 | "license": "MIT", 20 | "bugs": { 21 | "url": "https://github.com/Bhanu1776/Freelansters/issues" 22 | }, 23 | "homepage": "https://github.com/Bhanu1776/Freelansters/#readme", 24 | "dependencies": { 25 | "axios": "^1.4.0", 26 | "bcryptjs": "^2.4.3", 27 | "cookie-parser": "^1.4.6", 28 | "cors": "^2.8.5", 29 | "express": "^4.18.2", 30 | "http-proxy-middleware": "^2.0.6", 31 | "jsonwebtoken": "^9.0.0", 32 | "mongoose": "^7.3.0", 33 | "node-latest": "^4.0.1", 34 | "nodemon": "^2.0.22", 35 | "npm": "^9.7.1", 36 | "react": "^18.2.0", 37 | "react-dom": "^18.2.0", 38 | "react-router-dom": "^6.13.0", 39 | "react-scripts": "^5.0.1", 40 | "update": "^0.7.4", 41 | "web-vitals": "^3.3.2" 42 | }, 43 | "devDependencies": { 44 | "dotenv": "^16.3.1" 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /Client/src/Img/imgindex.js: -------------------------------------------------------------------------------- 1 | const Images = { 2 | // slider1: require('./slider1.jpg'), 3 | // slider2: require('./slider2.jpg'), 4 | // slider3: require('./slider3.jpg'), 5 | // glass: require('./glass-right.png'), 6 | // shape1: require('./1.png'), 7 | // shape2: require('./2.png'), 8 | // shape3: require('./3.png'), 9 | // shape4: require('./4.png'), 10 | // shape5: require('./5.png'), 11 | // shape6: require('./6.png'), 12 | // shape7: require('./7.png'), 13 | // shape8: require('./8.png'), 14 | // shape9: require('./9.png'), 15 | // shape10: require('./10.png'), 16 | // shape11: require('./11.png'), 17 | // shape14: require('./14.png'), 18 | // shape15: require('./15.png'), 19 | // Features: require('./Features.png'), 20 | // bhanu: require('./bhanu.jpg'), 21 | // harsh: require('./harsh.jpg'), 22 | // osama: require('./osama.jpg'), 23 | // card1: require('./card-bg.jpg'), 24 | // FFhero: require('./FFHero.jpg'), 25 | // PJImg: require('./PJImg.jpg'), 26 | // s1: require('./s1.jpg'), 27 | // s2: require('./s2.jpg'), 28 | // s3: require('./s3.jpg'), 29 | // s4: require('./s4.jpg'), 30 | // logo1: require('./freelansters-logo1.png'), 31 | // logo: require('./freelansters-logo.png'), 32 | 33 | 34 | } 35 | export default Images; -------------------------------------------------------------------------------- /Client/src/Styles/GlobalStyle.js: -------------------------------------------------------------------------------- 1 | import { createGlobalStyle } from "styled-components"; 2 | 3 | export const GlobalStyle = createGlobalStyle` 4 | 5 | * { 6 | margin: 0px; 7 | padding: 0px; 8 | box-sizing: border-box; 9 | } 10 | img{ 11 | user-select: none; 12 | } 13 | button{ 14 | cursor: pointer; 15 | } 16 | body { 17 | background-color: var(--shady-white-color); 18 | } 19 | html { 20 | scroll-behavior: smooth; 21 | } 22 | 23 | :root { 24 | --shady-white-color: #f5f5f5; /* #fafffe*/ 25 | --accent-color: #1cd6ce; /*#00c8aa*/ 26 | --section-font: "Acme", sans-serif; 27 | --primary-font: "PT Serif", serif; 28 | --clr-neutral-900: hsl(207, 19%, 9%); 29 | --clr-neutral-100: hsl(0, 0%, 100%); 30 | --clr-accent-400: hsl(142, 90%, 61%); 31 | --padding: 1.5rem; 32 | } 33 | 34 | ::-webkit-scrollbar { 35 | width: 11px; 36 | } 37 | ::-webkit-scrollbar-thumb { 38 | background: linear-gradient(transparent, #09a991); 39 | border-radius: 6px; 40 | } 41 | ::-webkit-scrollbar-thumb:hover { 42 | background: linear-gradient(transparent, #1cd6ce); 43 | } 44 | 45 | /*--------------------------------------------CSS FOR PROGRASSBAR-------------------------------------------------------------------- */ 46 | .progressbar{ 47 | background-color: rgba(255, 255, 255, 0); 48 | height:5px; 49 | position: sticky; 50 | top:0; 51 | left:0; 52 | z-index: 4; 53 | width: 100%; 54 | } 55 | 56 | .progressbarIn{ 57 | height:5px; 58 | background: #00c8aa; 59 | } 60 | 61 | ` -------------------------------------------------------------------------------- /Client/src/reducer/jobReducer.js: -------------------------------------------------------------------------------- 1 | const JobReducer = (state, action) => { 2 | switch (action.type) { 3 | case "SET_LOADING": 4 | return { 5 | ...state, 6 | isLoading: true, 7 | }; 8 | 9 | case "SET_API_DATA": 10 | // const featureData = action.payload.filter((curElem)=>{ 11 | // return curElem.featured === true; 12 | // }); 13 | 14 | return { 15 | ...state, 16 | isLoading: false, 17 | jobs: action.payload, 18 | // featureJobs: featureData, 19 | } 20 | 21 | case "API_ERROR": 22 | return { 23 | ...state, 24 | isLoading: false, 25 | isError: true, 26 | }; 27 | 28 | case "SET_SINGLE_LOADING": 29 | return { 30 | ...state, 31 | isSingleLoading: true, 32 | }; 33 | 34 | case "SET_SINGLE_JOB": 35 | return { 36 | ...state, 37 | isSingleLoading: false, 38 | singleJob: action.payload, 39 | }; 40 | 41 | case "SET_SINGLE_ERROR": 42 | return { 43 | ...state, 44 | isSingleLoading: false, 45 | isError: true, 46 | }; 47 | 48 | default: 49 | return state; 50 | } 51 | } 52 | 53 | export default JobReducer; -------------------------------------------------------------------------------- /Client/src/context/filtercontext.js: -------------------------------------------------------------------------------- 1 | import React, { createContext, useContext, useEffect, useReducer } from "react"; 2 | import { useJobContext } from "./jobcontext"; 3 | import reducer from "../reducer/filterReducer"; 4 | 5 | const FilterContext = createContext(); 6 | 7 | const initialState = { 8 | filter_jobs:[], 9 | all_jobs:[], 10 | filters:{ 11 | searchQueryInput:"", 12 | title: "all", 13 | category: "all", 14 | }, 15 | }; 16 | 17 | export const FilterContextProvider=({children})=>{ 18 | const {jobs} = useJobContext(); 19 | 20 | const [state,dispatch] = useReducer(reducer,initialState); 21 | 22 | useEffect(()=>{ 23 | dispatch({ type: "LOAD_FILTER_JOBS", payload: jobs }); 24 | }, [jobs, ]); 25 | 26 | useEffect(() => { 27 | dispatch({ type: "LOAD_FILTER_JOBS", payload: jobs }); 28 | dispatch({ type: "FILTER_JOBS"}) 29 | }, [state.filters]) 30 | 31 | 32 | 33 | 34 | 35 | // SEARCHING JOBS 36 | const updateFilterValue = (event) =>{ 37 | let name = event.target.name; 38 | let value = event.target.value; 39 | return dispatch({ type: "UPDATE_FILTER_VALUE", payload: {name, value}}) 40 | }; 41 | 42 | 43 | return( 44 | 45 | {children} 46 | 47 | ); 48 | }; 49 | 50 | 51 | export const useFilterContext = ()=>{ 52 | return useContext(FilterContext); 53 | }; -------------------------------------------------------------------------------- /Client/src/context/freelancercontext.js: -------------------------------------------------------------------------------- 1 | import { createContext, useContext, useEffect, useReducer } from "react"; 2 | import reducer from "../reducer/freelancerReducer"; 3 | const FreelancerContext = createContext(); 4 | 5 | const FilterFreelancer = ({ children }) => { 6 | 7 | useEffect(() => { 8 | getFreelancer(); 9 | // eslint-disable-next-line react-hooks/exhaustive-deps 10 | }, []); 11 | 12 | const initialState = { 13 | isLoading: false, 14 | isError: false, 15 | freelancer: [], 16 | 17 | }; 18 | 19 | const [state, dispatch] = useReducer(reducer, initialState); 20 | 21 | // ALL JOBS 22 | const getFreelancer = async () => { 23 | dispatch({ type: "SET_LOADING" }); 24 | try { 25 | const res = await fetch(process.env.BACKEND_URL+"/FreelancersFetch", { 26 | method: "GET", 27 | headers: { 28 | "Content-Type": "application/json", 29 | }, 30 | }); 31 | 32 | const FreelancerData = await res.json(); 33 | const freelancer = FreelancerData.data 34 | dispatch({ type: "SET_API_DATA", payload: freelancer }); 35 | console.log(freelancer); 36 | } catch (error) { 37 | dispatch({ type: "API_ERROR" }); 38 | } 39 | }; 40 | 41 | return ({children}); 42 | }; 43 | 44 | // Custom Hooks 45 | const useFreelancerContext = () => { 46 | return useContext(FreelancerContext); 47 | }; 48 | 49 | export { FreelancerContext, FilterFreelancer, useFreelancerContext } -------------------------------------------------------------------------------- /Server/model/tempSchema.js: -------------------------------------------------------------------------------- 1 | const mongoose = require('mongoose'); 2 | 3 | const tempSchema = new mongoose.Schema({ 4 | name: { 5 | type: String, 6 | }, 7 | email: { 8 | type: String, 9 | // required: true, 10 | unique: true 11 | }, 12 | phone: { 13 | type: Number, 14 | unique: true 15 | }, 16 | password: { 17 | type: String, 18 | // required: true 19 | }, 20 | cpassword: { 21 | type: String, 22 | // required: true 23 | }, 24 | Jobs: { 25 | category: { 26 | type: String, 27 | }, 28 | date: { 29 | type: String, 30 | }, 31 | duration: { 32 | type: String, 33 | }, 34 | description: { 35 | type: String, 36 | }, 37 | price: { 38 | type: String, 39 | }, 40 | img: { 41 | type: String, 42 | }, 43 | }, 44 | Freelancers: { 45 | title: { 46 | type: String, 47 | }, 48 | hours: { 49 | type: Number, 50 | }, 51 | price: { 52 | type: Number, 53 | }, 54 | special: { 55 | type: String, 56 | }, 57 | time: { 58 | type: String, 59 | }, 60 | description: { 61 | type: String, 62 | }, 63 | img: { 64 | type: String, 65 | }, 66 | reviews: { 67 | type: String, 68 | }, 69 | stars: { 70 | type: Number, 71 | }, 72 | }, 73 | }, 74 | { 75 | timestamps: true 76 | }) 77 | 78 | //* Collection Creation 79 | const temp = mongoose.model('temp', tempSchema) 80 | 81 | module.exports = temp; -------------------------------------------------------------------------------- /Client/src/Components/FFlancer.jsx: -------------------------------------------------------------------------------- 1 | /* eslint-disable no-unused-vars */ 2 | import React from "react"; 3 | import ProfileCards from "./ProfileCards"; 4 | import ProfileData from "./ProfileData"; 5 | import styled from "styled-components"; 6 | import Hero from "./Hero"; 7 | import { useFreelancerContext } from "../context/freelancercontext"; 8 | 9 | const FFHeroImg = 10 | 'url("https://images.unsplash.com/photo-1487528278747-ba99ed528ebc?ixlib=rb-4.0.3&ixid=MnwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHx8&auto=format&fit=crop&w=1170&q=80")'; 11 | 12 | const FFlancer = (curElem) => { 13 | const { isLoading, freelancer } = useFreelancerContext(); 14 | if (isLoading) { 15 | return
..........LOADING
; 16 | } 17 | 18 | return ( 19 | <> 20 | 26 | 27 | 28 | {ProfileData.map((val) => { 29 | return ( 30 | 39 | ); 40 | })} 41 | 42 | 43 | ); 44 | }; 45 | const CardsHolder = styled.div` 46 | display: flex; 47 | justify-content: space-evenly; 48 | align-items: center; 49 | flex-direction: row; 50 | row-gap: 20px; 51 | column-gap: 20px; 52 | margin-top: 20px; 53 | flex-wrap: wrap; 54 | `; 55 | 56 | export default FFlancer; 57 | -------------------------------------------------------------------------------- /Client/src/Components/ProfileData.jsx: -------------------------------------------------------------------------------- 1 | import Images from "../Img/imgindex"; 2 | const Cdata = [ 3 | { 4 | id: "1", 5 | proSpecial: "Android Developer", 6 | proTime: "2hrs", 7 | proPrice: "1500", 8 | proImg: 9 | "https://xsgames.co/randomusers/assets/avatars/male/46.jpg", 10 | proName: "Alex Jordan", 11 | proStars: "5", 12 | proReviews: "60", 13 | }, 14 | { 15 | id: "2", 16 | proSpecial: "Video Editor", 17 | proTime: "3hrs", 18 | proPrice: "2000", 19 | proImg: 20 | "https://expertphotography.b-cdn.net/wp-content/uploads/2020/08/social-media-profile-photos-3.jpg", 21 | proName: "Jake Paul", 22 | proStars: "3.2", 23 | proReviews: "50", 24 | }, 25 | { 26 | id: "3", 27 | proSpecial: "Data Entry Operator", 28 | proTime: "1hrs", 29 | proPrice: "500", 30 | proImg: "https://ik.imagekit.io/bhanu1776/Freelansters/osama.jpg?updatedAt=1682608749618", 31 | proName: "Osama Shaikh", 32 | proStars: "4.5", 33 | proReviews: "50", 34 | }, 35 | { 36 | id: "4", 37 | proSpecial: "Programmer", 38 | proTime: "2hrs", 39 | proPrice: "2000", 40 | proImg: 41 | "https://www.rd.com/wp-content/uploads/2017/09/01-shutterstock_476340928-Irina-Bg.jpg", 42 | proName: "Cathlyn Dsouza", 43 | proStars: "4.2", 44 | proReviews: "50", 45 | }, 46 | { 47 | id: "5", 48 | proSpecial: "Logistics", 49 | proTime: "1hrs", 50 | proPrice: "1000", 51 | proImg: 52 | "https://www.vivahonline.com/profileimages/profile_11%20SDN_01553%20copy.jpg", 53 | proName: "Vijay Mishra", 54 | proStars: "3.7", 55 | proReviews: "50", 56 | }, 57 | { 58 | id: "6", 59 | proSpecial: "Graphic Designer", 60 | proTime: "1hrs", 61 | proPrice: 400, 62 | proImg: "https://incois.gov.in/hrd/profileimages/076.jpg", 63 | proName: "Aslam Khan", 64 | proStars: "2", 65 | proReviews: "50", 66 | }, 67 | ]; 68 | 69 | export default Cdata; 70 | -------------------------------------------------------------------------------- /Server/server.js: -------------------------------------------------------------------------------- 1 | const dotenv = require('dotenv'); 2 | const express = require('express'); 3 | const cors = require('cors'); 4 | const cookie_parser = require('cookie-parser') 5 | const app = express(); 6 | 7 | dotenv.config({ path: './config.env' }); 8 | 9 | const PORT = process.env.PORT || 5000; 10 | require('./db/conn.js') 11 | 12 | const FJSchema = require('./model/FJSchema'); 13 | const FFSchema = require('./model/FFSchema'); 14 | const tempSchema = require('./model/tempSchema'); 15 | 16 | app.use(cors({ 17 | origin: ["http://localhost:3000", process.env.BASE_URL], 18 | credentials: true, 19 | methods: "GET,HEAD,PUT,PATCH,POST,DELETE", 20 | allowedHeaders: "Content-Type,Authorization", 21 | })); 22 | 23 | app.use(express.json()); 24 | app.use(cookie_parser()); 25 | app.use(require('./router/auth')); 26 | 27 | 28 | app.get('/', (req, res) => { 29 | res.send("Reserved for Freelansters.com"); 30 | }) 31 | 32 | app.get('/Login', (req, res) => { 33 | res.send('Hello world from the Login server'); 34 | }) 35 | app.get('/register', (req, res) => { 36 | res.send('Hello world from the Login server'); 37 | }) 38 | 39 | app.post('/Jobs', (req, res) => { 40 | const Jobs = FJSchema(req.body); 41 | Jobs.save(); 42 | res.send(req.body); 43 | }) 44 | 45 | app.get('/JobsFetch', async (req, res) => { 46 | const JobsFetch = await FJSchema.find({}); 47 | res.json({ 48 | data: JobsFetch 49 | }) 50 | }) 51 | 52 | app.post('/Freelancers', (req, res) => { 53 | const Freelancers = FFSchema(req.body); 54 | Freelancers.save(); 55 | res.send(req.body); 56 | }) 57 | 58 | app.post('/tempSchema', (req, res) => { 59 | const temp = tempSchema(req.body); 60 | temp.save(); 61 | res.send(req.body); 62 | }) 63 | 64 | app.get('/FreelancersFetch', async (req, res) => { 65 | const FreelancersFetch = await FFSchema.find({}); 66 | res.json({ 67 | data: FreelancersFetch 68 | }) 69 | }) 70 | 71 | app.listen(PORT, () => { 72 | console.log(`Server is running at port no ${PORT}`); 73 | }) -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |

Freelansters - MERN Stack Web-Application

2 | 3 | ## Technologies 🔧 4 | 5 | - HTML, CSS, Javascript 6 | - React 7 | - NodeJs 8 | - Express 9 | - MongoDB 10 | - Styled Components 11 | - MUI 12 | - JWT Auth 13 | - Twilio 14 | - And much more 🎒 15 | 16 | ## Screenshots 📸 17 | 18 | ![Freelansters Homepage)](https://imgur.com/irBJEk5.png) 19 | 20 | ![Freelansters FindJobs)](https://imgur.com/wd9htRN.png) 21 | 22 | ![Freelansters FJ)](https://imgur.com/XaJ4vDu.png) 23 | 24 | ## Code Example/Issues 🔍 25 | 26 | If you have any issues, please let me know in the issues section or directly to sunkabhanu281202@gmail.com 27 | 28 | ## Installation 💾 29 | 30 | ```bash 31 | git clone https://github.com/Bhanu1776/Freelansters.git 32 | ``` 33 | 34 | Create config.env file in `backend` folder and Fill your `.env` variables: 35 | 36 | ```env 37 | PORT= 38 | DATABASE= 39 | SECRET_KEY= 40 | ``` 41 | 42 | Install deps: 43 | 44 | ```bash 45 | npm install 46 | ``` 47 | 48 | Run React server from `Client` folder : 49 | 50 | ```bash 51 | npm start 52 | ``` 53 | 54 | Simultaneously Run Node.js Server : 55 | 56 | ```bash 57 | node server.js 58 | ``` 59 | 60 | ## Contributing 61 | 62 | This is an open source project, and contributions of any kind are welcome and appreciated. Open issues, bugs, and feature requests are all listed on the [issues](https://github.com/Bhanu1776/Freelansters/issues) tab and labeled accordingly. Feel free to open bug tickets and make feature requests. 63 | 64 | ## Contributors 💣 65 | 66 | 67 | 68 | 69 | 70 | ## Support Me 🫂 71 | 72 | 73 | 74 |
75 | 76 | © 2022 Bhanu Sunka and contributors\ 77 | This project is licensed under the [**MIT license**](https://github.com/Bhanu1776/Freelancers-Hub/blob/master/LICENSE). 78 | 79 | [![forthebadge](https://forthebadge.com/images/badges/built-with-love.svg)](https://forthebadge.com) 80 | -------------------------------------------------------------------------------- /Client/src/context/jobcontext.js: -------------------------------------------------------------------------------- 1 | import { createContext, useContext, useEffect, useReducer } from "react"; 2 | import reducer from '../reducer/jobReducer' 3 | const JobContext = createContext(); 4 | 5 | const FilterJobs = ({ children }) => { 6 | 7 | useEffect(() => { 8 | getJobs(); 9 | // eslint-disable-next-line react-hooks/exhaustive-deps 10 | }, []); 11 | 12 | 13 | const initialState = { 14 | isLoading: false, 15 | isError: false, 16 | jobs: [], 17 | isSingleLoading: false, 18 | singleJob: {}, 19 | }; 20 | 21 | const [state, dispatch] = useReducer(reducer, initialState); 22 | 23 | const getJobs = async () => { 24 | dispatch({ type: "SET_LOADING" }); 25 | try { 26 | const res = await fetch(process.env.BACKEND_URL+"/JobsFetch", { 27 | method: "GET", 28 | headers: { 29 | "Content-Type": "application/json", 30 | }, 31 | }); 32 | 33 | const CardsData = await res.json(); 34 | const jobs = CardsData.data 35 | dispatch({ type: "SET_API_DATA", payload: jobs }); 36 | } catch (error) { 37 | dispatch({ type: "API_ERROR" }); 38 | } 39 | }; 40 | 41 | const getSingleJob = async (_id) => { 42 | dispatch({ type: "SET_SINGLE_LOADING" }); 43 | try { 44 | const res = await fetch(process.env.BACKEND_URL+"/JobsFetch", { 45 | method: "GET", 46 | headers: { 47 | "Content-Type": "application/json", 48 | }, 49 | }); 50 | const SingleCardData = await res.json(); 51 | const singleJob = SingleCardData.data; 52 | dispatch({ type: "SET_SINGLE_JOB", payload: singleJob }); 53 | } catch (error) { 54 | dispatch({ type: "SET_SINGLE_ERROR" }); 55 | } 56 | } 57 | return ({children}); 58 | }; 59 | 60 | // Custom Hooks 61 | const useJobContext = () => { 62 | return useContext(JobContext); 63 | }; 64 | 65 | export { JobContext, FilterJobs, useJobContext } -------------------------------------------------------------------------------- /Client/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "freelanster", 3 | "version": "0.1.0", 4 | "private": true, 5 | "proxy": "http://localhost:5000", 6 | "dependencies": { 7 | "@emotion/react": "^11.11.4", 8 | "@emotion/styled": "^11.11.0", 9 | "@iconscout/react-unicons": "^2.0.2", 10 | "@material-ui/core": "^4.12.4", 11 | "@material-ui/icons": "^4.11.3", 12 | "@mui/icons-material": "^5.15.13", 13 | "@mui/material": "^5.15.13", 14 | "@testing-library/jest-dom": "^6.4.2", 15 | "@testing-library/react": "^14.2.1", 16 | "@testing-library/user-event": "^14.5.2", 17 | "axios": "^1.6.7", 18 | "bcryptjs": "^2.4.3", 19 | "cookie-parser": "^1.4.6", 20 | "cors": "^2.8.5", 21 | "dotenv": "^16.4.5", 22 | "express": "^4.18.3", 23 | "formik": "^2.4.5", 24 | "framer-motion": "^11.0.12", 25 | "http-proxy-middleware": "^2.0.6", 26 | "jsonwebtoken": "^9.0.2", 27 | "razorpay": "^2.9.2", 28 | "rc-slider": "^10.5.0", 29 | "react": "^18.2.0", 30 | "react-dom": "^18.2.0", 31 | "react-helmet": "^6.1.0", 32 | "react-icons": "^5.0.1", 33 | "react-intersection-observer": "^9.8.1", 34 | "react-modal": "^3.16.1", 35 | "react-router-dom": "^6.22.3", 36 | "react-scripts": "^5.0.1", 37 | "react-tippy": "^1.4.0", 38 | "react-toastify": "^10.0.4", 39 | "sass": "^1.71.1", 40 | "styled-components": "^6.1.8", 41 | "swiper": "^11.0.7", 42 | "twilio": "^5.0.0", 43 | "web-vitals": "^3.5.2", 44 | "yup": "^1.4.0" 45 | }, 46 | "scripts": { 47 | "start": "react-scripts start", 48 | "build": "react-scripts build", 49 | "test": "react-scripts test", 50 | "eject": "react-scripts eject" 51 | }, 52 | "config": { 53 | "cz-emoji": { 54 | "skipQuestions": [ 55 | "issues", 56 | "breaking" 57 | ] 58 | } 59 | }, 60 | "eslintConfig": { 61 | "extends": [ 62 | "react-app", 63 | "react-app/jest" 64 | ] 65 | }, 66 | "browserslist": { 67 | "production": [ 68 | ">0.2%", 69 | "not dead", 70 | "not op_mini all" 71 | ], 72 | "development": [ 73 | "last 1 chrome version", 74 | "last 1 firefox version", 75 | "last 1 safari version" 76 | ] 77 | } 78 | } 79 | -------------------------------------------------------------------------------- /Client/src/reducer/filterReducer.js: -------------------------------------------------------------------------------- 1 | import { checkboxClasses } from "@mui/material"; 2 | 3 | const filterReducer = (state,action) =>{ 4 | 5 | switch(action.type){ 6 | case "LOAD_FILTER_JOBS": 7 | return{ 8 | ...state, 9 | filter_jobs:[...action.payload], 10 | all_jobs:[...action.payload], 11 | // lol_jobs:[], 12 | title_jobs:[] 13 | }; 14 | 15 | case "UPDATE_FILTER_VALUE": 16 | const {name,value}=action.payload; 17 | return{ 18 | ...state, 19 | filters:{ 20 | ...state.filters, 21 | [name]:value, 22 | }, 23 | 24 | } 25 | 26 | case "FILTER_JOBS": 27 | let {all_jobs} = state; 28 | let tempFilterJobs = [...all_jobs]; 29 | let titleFilterJobs =[...all_jobs]; 30 | const { title, category } = state.filters; 31 | 32 | 33 | // if (searchQueryInput){ 34 | // tempFilterJobs = tempFilterJobs.filter((curElem)=>{ 35 | // return curElem.name.toLowerCase().include(searchQueryInput); 36 | // }); 37 | // } 38 | 39 | // if(title){ 40 | // tempFilterJobs = tempFilterJobs.filter((curElem)=>{ 41 | // return curElem.category === title; 42 | // }); 43 | // } 44 | 45 | 46 | if(title){ 47 | tempFilterJobs = tempFilterJobs.filter((curElem) => curElem.title === title); 48 | // console.log("AFTER JOBS:", lol_jobs); 49 | } 50 | 51 | 52 | 53 | // if (category) { 54 | 55 | // const lol_jobs = tempFilterJobs.filter((curElem) => curElem.category === category); 56 | // console.log("AFTER JOBS:", lol_jobs); 57 | // } 58 | 59 | return{ 60 | ...state, 61 | all_jobs: tempFilterJobs 62 | } 63 | default: 64 | return state; 65 | 66 | } 67 | } 68 | 69 | export default filterReducer; 70 | 71 | 72 | 73 | -------------------------------------------------------------------------------- /Server/.gitignore: -------------------------------------------------------------------------------- 1 | config.env 2 | 3 | /node_modules 4 | 5 | # Logs 6 | logs 7 | *.log 8 | npm-debug.log* 9 | yarn-debug.log* 10 | yarn-error.log* 11 | lerna-debug.log* 12 | 13 | # Diagnostic reports (https://nodejs.org/api/report.html) 14 | report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json 15 | 16 | # Runtime data 17 | pids 18 | *.pid 19 | *.seed 20 | *.pid.lock 21 | 22 | # Directory for instrumented libs generated by jscoverage/JSCover 23 | lib-cov 24 | 25 | # Coverage directory used by tools like istanbul 26 | coverage 27 | *.lcov 28 | 29 | # nyc test coverage 30 | .nyc_output 31 | 32 | # Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) 33 | .grunt 34 | 35 | # Bower dependency directory (https://bower.io/) 36 | bower_components 37 | 38 | # node-waf configuration 39 | .lock-wscript 40 | 41 | # Compiled binary addons (https://nodejs.org/api/addons.html) 42 | build/Release 43 | 44 | # Dependency directories 45 | node_modules/ 46 | jspm_packages/ 47 | 48 | # TypeScript v1 declaration files 49 | typings/ 50 | 51 | # TypeScript cache 52 | *.tsbuildinfo 53 | 54 | # Optional npm cache directory 55 | .npm 56 | 57 | # Optional eslint cache 58 | .eslintcache 59 | 60 | # Microbundle cache 61 | .rpt2_cache/ 62 | .rts2_cache_cjs/ 63 | .rts2_cache_es/ 64 | .rts2_cache_umd/ 65 | 66 | # Optional REPL history 67 | .node_repl_history 68 | 69 | # Output of 'npm pack' 70 | *.tgz 71 | 72 | # Yarn Integrity file 73 | .yarn-integrity 74 | 75 | # dotenv environment variables file 76 | .env 77 | .env.test 78 | 79 | # parcel-bundler cache (https://parceljs.org/) 80 | .cache 81 | 82 | # Next.js build output 83 | .next 84 | 85 | # Nuxt.js build / generate output 86 | .nuxt 87 | dist 88 | 89 | # Gatsby files 90 | .cache/ 91 | # Comment in the public line in if your project uses Gatsby and *not* Next.js 92 | # https://nextjs.org/blog/next-9-1#public-directory-support 93 | # public 94 | 95 | # vuepress build output 96 | .vuepress/dist 97 | 98 | # Serverless directories 99 | .serverless/ 100 | 101 | # FuseBox cache 102 | .fusebox/ 103 | 104 | # DynamoDB Local files 105 | .dynamodb/ 106 | 107 | # TernJS port file 108 | .tern-port 109 | 110 | # IMP notes 111 | Lessons.txt 112 | -------------------------------------------------------------------------------- /Server/model/userSchema.js: -------------------------------------------------------------------------------- 1 | const mongoose = require('mongoose'); 2 | const bcrypt = require('bcryptjs'); 3 | const jwt = require('jsonwebtoken'); 4 | 5 | 6 | const userSchema = new mongoose.Schema({ 7 | name: { 8 | type: String, 9 | required: true 10 | }, 11 | email: { 12 | type: String, 13 | required: true, 14 | unique: true 15 | }, 16 | phone: { 17 | type: Number, 18 | required: true, 19 | unique: true 20 | }, 21 | password: { 22 | type: String, 23 | required: true 24 | }, 25 | cpassword: { 26 | type: String, 27 | required: true 28 | }, 29 | 30 | special: { 31 | type: String, 32 | }, 33 | time: { 34 | type: String, 35 | }, 36 | price: { 37 | type: Number, 38 | }, 39 | description: { 40 | type: String, 41 | }, 42 | img: { 43 | type: String, 44 | }, 45 | reviews: { 46 | type: String, 47 | }, 48 | stars: { 49 | type: Number, 50 | }, 51 | tokens: [ 52 | { // There are going to be many tokens right thats why taking an array. 53 | token: { 54 | type: String, 55 | required: true 56 | } 57 | } 58 | ], 59 | }, { 60 | timestamps: true 61 | } 62 | ) 63 | 64 | 65 | //* Code for hashing the password 66 | 67 | userSchema.pre('save', async function (next) { // Bcoz of 'pre' method, 'next' func will automatically call itself before save() func in auth.js.. 68 | if (this.isModified('password')) { 69 | this.password = await bcrypt.hash(this.password, 12); 70 | this.cpassword = await bcrypt.hash(this.cpassword, 12); 71 | } 72 | }); 73 | 74 | //* For generating token 75 | userSchema.methods.generateAuthToken = async function () { 76 | try { 77 | let token = jwt.sign({ _id: this._id }, process.env.SECRET_KEY) 78 | this.tokens = this.tokens.concat({ token: token }); 79 | await this.save(); 80 | return token; 81 | } 82 | catch (err) { 83 | console.log("🚀 ~ file: userSchema.js:83 ~ err", err) 84 | } 85 | } 86 | 87 | //* Collection Creation 88 | const User = mongoose.model('Users', userSchema) 89 | 90 | module.exports = User; -------------------------------------------------------------------------------- /Client/build/asset-manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "files": { 3 | "main.css": "/static/css/main.f4e52759.css", 4 | "main.js": "/static/js/main.fe490bc1.js", 5 | "static/media/PJImg.jpg": "/static/media/PJImg.a5c9e3f030dedd161f19.jpg", 6 | "static/media/s3.jpg": "/static/media/s3.6af90c49ed3ead48f32b.jpg", 7 | "static/media/s4.jpg": "/static/media/s4.af6c2349bff585218d85.jpg", 8 | "static/media/logistics.jpg": "/static/media/logistics.4d159b76b1bdfe5a8f33.jpg", 9 | "static/media/accountant.jpg": "/static/media/accountant.76fdc2ac7417a91763b1.jpg", 10 | "static/media/graphic_design.png": "/static/media/graphic_design.58143d82fe784f1642fc.png", 11 | "static/media/card-bg.jpg": "/static/media/card-bg.71550beb9e90b0170350.jpg", 12 | "static/media/s2.jpg": "/static/media/s2.6c3a0fe2972d6b7d302a.jpg", 13 | "static/media/data_entry.png": "/static/media/data_entry.5cf7fe547607d3a39fb9.png", 14 | "static/media/FFHero.jpg": "/static/media/FFHero.e177b3dcf2d8079f7777.jpg", 15 | "static/media/video_editing.png": "/static/media/video_editing.d1cb7df110e127d85470.png", 16 | "static/media/article_writing.png": "/static/media/article_writing.73015a83047882b467b8.png", 17 | "static/media/bhanu.jpg": "/static/media/bhanu.128f6fa3936a77691bc5.jpg", 18 | "static/media/glass-right.png": "/static/media/glass-right.ea24b06211e2d2217247.png", 19 | "static/media/harsh.jpg": "/static/media/harsh.f73562890cfbf477cfef.jpg", 20 | "static/media/freelansters-logo.png": "/static/media/freelansters-logo.3eb14736e8d3ce1c83e5.png", 21 | "static/media/android_developer.png": "/static/media/android_developer.cdf54b267c58f829b53c.png", 22 | "static/media/osama.jpg": "/static/media/osama.7bc61991c5c041b4fbe0.jpg", 23 | "static/media/s1.jpg": "/static/media/s1.d188ee8ecd63e9f254da.jpg", 24 | "static/media/Features.png": "/static/media/Features.e6e085e5cc62509c9481.png", 25 | "static/media/freelansters-logo1.png": "/static/media/freelansters-logo1.2c679b5600aeb404d11a.png", 26 | "static/media/1.png": "/static/media/1.c8d0a91f56308d85d671.png", 27 | "index.html": "/index.html", 28 | "main.f4e52759.css.map": "/static/css/main.f4e52759.css.map", 29 | "main.fe490bc1.js.map": "/static/js/main.fe490bc1.js.map" 30 | }, 31 | "entrypoints": [ 32 | "static/css/main.f4e52759.css", 33 | "static/js/main.fe490bc1.js" 34 | ] 35 | } -------------------------------------------------------------------------------- /Client/src/FindFreelancer.js: -------------------------------------------------------------------------------- 1 | import React, { useContext, useState, useEffect } from 'react' 2 | import { useNavigate } from 'react-router-dom'; 3 | import { Helmet } from "react-helmet"; 4 | import Navbar from './Components/Navbar'; 5 | import FindFreelan from './Components/FFlancer'; 6 | import GoToTop from './Components/GoToTop'; 7 | import Footer from './Components/Footer'; 8 | import { FilterFreelancer } from './context/freelancercontext'; 9 | import { UserContext } from "./Routing"; 10 | 11 | 12 | const FindFreelancer = () => { 13 | 14 | const navigate = useNavigate(); 15 | // eslint-disable-next-line no-unused-vars 16 | const { state, dispatch } = useContext(UserContext); 17 | 18 | const [loading, setLoading] = useState(true); 19 | const preloader = document.getElementById('preloader'); 20 | if (preloader) { 21 | setTimeout(() => { 22 | preloader.style.display = 'none'; 23 | setLoading(false); 24 | }, 0); 25 | } 26 | 27 | const callFF = async () => { 28 | 29 | try { 30 | const res = await fetch(process.env.BACKEND_URL+'/FreelancersFetch', { 31 | method: "GET", //! IMP 32 | headers: { 33 | Accept: "application/json", 34 | "Content-Type": "application/json" 35 | }, 36 | credentials: "include" 37 | }); 38 | dispatch({ type: "USER", payload: true }); 39 | 40 | const data = await res.json(); 41 | console.log(data); 42 | 43 | if (!res.status === 200) { 44 | const error = new Error(res.error); 45 | throw error; 46 | } 47 | } catch (err) { 48 | console.log(err); 49 | navigate('/Login') 50 | } 51 | } 52 | 53 | useEffect(() => { 54 | callFF(); 55 | // eslint-disable-next-line react-hooks/exhaustive-deps 56 | }, []) 57 | 58 | return ( 59 | !loading && ( 60 | 61 | <> 62 | 63 | 64 | 65 | Find Freelancer 66 | 67 | 68 | 69 | 70 | 71 | 72 |