| @@ -0,0 +1,23 @@ | |||
| { | |||
| "extends": [ | |||
| "plugin:storybook/recommended", | |||
| "next", | |||
| "next/core-web-vitals", | |||
| "eslint:recommended" | |||
| ], | |||
| "globals": { | |||
| "React": "readonly" | |||
| }, | |||
| "overrides": [ | |||
| { | |||
| "files": ["*.stories.@(ts|tsx|js|jsx|mjs|cjs)"], | |||
| "rules": { | |||
| // example of overriding a rule | |||
| "storybook/hierarchy-separator": "error" | |||
| } | |||
| } | |||
| ], | |||
| "rules": { | |||
| "no-unused-vars": [1, { "args": "after-used", "argsIgnorePattern": "^_" }] | |||
| } | |||
| } | |||
| @@ -0,0 +1,33 @@ | |||
| # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. | |||
| # dependencies | |||
| /node_modules | |||
| /.pnp | |||
| .pnp.js | |||
| # testing | |||
| /coverage | |||
| # next.js | |||
| /.next/ | |||
| /out/ | |||
| # production | |||
| /build | |||
| # misc | |||
| .DS_Store | |||
| *.pem | |||
| # debug | |||
| npm-debug.log* | |||
| yarn-debug.log* | |||
| yarn-error.log* | |||
| .pnpm-debug.log* | |||
| # local env files | |||
| .env*.local | |||
| .env | |||
| # vercel | |||
| .vercel | |||
| @@ -0,0 +1,4 @@ | |||
| #!/usr/bin/env sh | |||
| . "$(dirname -- "$0")/_/husky.sh" | |||
| npx --no -- commitlint --edit $1 | |||
| @@ -0,0 +1,4 @@ | |||
| #!/usr/bin/env sh | |||
| . "$(dirname -- "$0")/_/husky.sh" | |||
| yarn lint | |||
| @@ -0,0 +1,4 @@ | |||
| #!/usr/bin/env sh | |||
| . "$(dirname -- "$0")/_/husky.sh" | |||
| #yarn build | |||
| @@ -0,0 +1 @@ | |||
| engine-strict=true | |||
| @@ -0,0 +1 @@ | |||
| lts/fermium | |||
| @@ -0,0 +1,4 @@ | |||
| .yarn | |||
| .next | |||
| dist | |||
| node_modules | |||
| @@ -0,0 +1,6 @@ | |||
| { | |||
| "trailingComma": "es5", | |||
| "tabWidth": 2, | |||
| "semi": true, | |||
| "singleQuote": true | |||
| } | |||
| @@ -0,0 +1,34 @@ | |||
| This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app). | |||
| ## Getting Started | |||
| First, run the development server: | |||
| ```bash | |||
| npm run dev | |||
| # or | |||
| yarn dev | |||
| ``` | |||
| Open [http://localhost:3000](http://localhost:3000) with your browser to see the result. | |||
| You can start editing the page by modifying `pages/index.tsx`. The page auto-updates as you edit the file. | |||
| [API routes](https://nextjs.org/docs/api-routes/introduction) can be accessed on [http://localhost:3000/api/hello](http://localhost:3000/api/hello). This endpoint can be edited in `pages/api/hello.ts`. | |||
| The `pages/api` directory is mapped to `/api/*`. Files in this directory are treated as [API routes](https://nextjs.org/docs/api-routes/introduction) instead of React pages. | |||
| ## Learn More | |||
| To learn more about Next.js, take a look at the following resources: | |||
| - [Next.js Documentation](https://nextjs.org/docs) - learn about Next.js features and API. | |||
| - [Learn Next.js](https://nextjs.org/learn) - an interactive Next.js tutorial. | |||
| You can check out [the Next.js GitHub repository](https://github.com/vercel/next.js/) - your feedback and contributions are welcome! | |||
| ## Deploy on Vercel | |||
| The easiest way to deploy your Next.js app is to use the [Vercel Platform](https://vercel.com/new?utm_medium=default-template&filter=next.js&utm_source=create-next-app&utm_campaign=create-next-app-readme) from the creators of Next.js. | |||
| Check out our [Next.js deployment documentation](https://nextjs.org/docs/deployment) for more details. | |||
| @@ -0,0 +1,50 @@ | |||
| // build: Changes that affect the build system or external dependencies (example scopes: gulp, broccoli, npm) | |||
| // ci: Changes to our CI configuration files and scripts (example scopes: Travis, Circle, BrowserStack, SauceLabs) | |||
| // docs: Documentation only changes | |||
| // feat: A new feature | |||
| // fix: A bug fix | |||
| // perf: A code change that improves performance | |||
| // refactor: A code change that neither fixes a bug nor adds a feature | |||
| // style: Changes that do not affect the meaning of the code (white-space, formatting, missing semi-colons, etc) | |||
| // test: Adding missing tests or correcting existing tests | |||
| module.exports = { | |||
| extends: ['@commitlint/config-conventional'], | |||
| rules: { | |||
| 'body-leading-blank': [1, 'always'], | |||
| 'body-max-line-length': [2, 'always', 100], | |||
| 'footer-leading-blank': [1, 'always'], | |||
| 'footer-max-line-length': [2, 'always', 100], | |||
| 'header-max-length': [2, 'always', 100], | |||
| 'scope-case': [2, 'always', 'lower-case'], | |||
| 'subject-case': [ | |||
| 2, | |||
| 'never', | |||
| ['sentence-case', 'start-case', 'pascal-case', 'upper-case'], | |||
| ], | |||
| 'subject-empty': [2, 'never'], | |||
| 'subject-full-stop': [2, 'never', '.'], | |||
| 'type-case': [2, 'always', 'lower-case'], | |||
| 'type-empty': [2, 'never'], | |||
| 'type-enum': [ | |||
| 2, | |||
| 'always', | |||
| [ | |||
| 'build', | |||
| 'chore', | |||
| 'ci', | |||
| 'docs', | |||
| 'feat', | |||
| 'fix', | |||
| 'perf', | |||
| 'refactor', | |||
| 'revert', | |||
| 'style', | |||
| 'test', | |||
| 'translation', | |||
| 'security', | |||
| 'changeset', | |||
| ], | |||
| ], | |||
| }, | |||
| }; | |||
| @@ -0,0 +1,5 @@ | |||
| /// <reference types="next" /> | |||
| /// <reference types="next/image-types/global" /> | |||
| // NOTE: This file should not be edited | |||
| // see https://nextjs.org/docs/basic-features/typescript for more information. | |||
| @@ -0,0 +1,6 @@ | |||
| module.exports = { | |||
| i18n: { | |||
| defaultLocale: 'en', | |||
| locales: ['en'], | |||
| }, | |||
| }; | |||
| @@ -0,0 +1,19 @@ | |||
| /** @type {import('next').NextConfig} */ | |||
| const { i18n } = require('./next-i18next.config'); | |||
| const nextConfig = { | |||
| images: { | |||
| domains: ['www.business2community.com'], | |||
| }, | |||
| env: { | |||
| NEXT_PUBLIC_STRIPE_PUBLIC_API_KEY: | |||
| process.env.NEXT_PUBLIC_STRIPE_PUBLIC_API_KEY, | |||
| NEXT_PUBLIC_MAP_KEY: process.env.NEXT_PUBLIC_NEXT_PUBLIC_MAP_KEY, | |||
| NEXT_PUBLIC_SEND_GRID: process.env.NEXT_PUBLIC_SEND_GRID, | |||
| }, | |||
| reactStrictMode: true, | |||
| swcMinify: true, | |||
| i18n, | |||
| }; | |||
| module.exports = nextConfig; | |||
| @@ -0,0 +1,25 @@ | |||
| { | |||
| "name": "coffe-ts", | |||
| "version": "0.1.0", | |||
| "private": true, | |||
| "scripts": { | |||
| "dev": "next dev", | |||
| "build": "next build", | |||
| "start": "next start", | |||
| "lint": "next lint" | |||
| }, | |||
| "dependencies": { | |||
| "@types/mongodb": "^4.0.7", | |||
| "next": "12.3.1", | |||
| "react": "18.2.0", | |||
| "react-dom": "18.2.0" | |||
| }, | |||
| "devDependencies": { | |||
| "@types/node": "18.8.3", | |||
| "@types/react": "18.0.21", | |||
| "@types/react-dom": "18.0.6", | |||
| "eslint": "8.25.0", | |||
| "eslint-config-next": "12.3.1", | |||
| "typescript": "4.8.4" | |||
| } | |||
| } | |||
| @@ -0,0 +1,8 @@ | |||
| import '../styles/globals.css' | |||
| import type { AppProps } from 'next/app' | |||
| function MyApp({ Component, pageProps }: AppProps) { | |||
| return <Component {...pageProps} /> | |||
| } | |||
| export default MyApp | |||
| @@ -0,0 +1,13 @@ | |||
| // Next.js API route support: https://nextjs.org/docs/api-routes/introduction | |||
| import type { NextApiRequest, NextApiResponse } from 'next' | |||
| type Data = { | |||
| name: string | |||
| } | |||
| export default function handler( | |||
| req: NextApiRequest, | |||
| res: NextApiResponse<Data> | |||
| ) { | |||
| res.status(200).json({ name: 'John Doe' }) | |||
| } | |||
| @@ -0,0 +1,72 @@ | |||
| import type { NextPage } from 'next' | |||
| import Head from 'next/head' | |||
| import Image from 'next/image' | |||
| import styles from '../styles/Home.module.css' | |||
| const Home: NextPage = () => { | |||
| return ( | |||
| <div className={styles.container}> | |||
| <Head> | |||
| <title>Create Next App</title> | |||
| <meta name="description" content="Generated by create next app" /> | |||
| <link rel="icon" href="/favicon.ico" /> | |||
| </Head> | |||
| <main className={styles.main}> | |||
| <h1 className={styles.title}> | |||
| Welcome to <a href="https://nextjs.org">Next.js!</a> | |||
| </h1> | |||
| <p className={styles.description}> | |||
| Get started by editing{' '} | |||
| <code className={styles.code}>pages/index.tsx</code> | |||
| </p> | |||
| <div className={styles.grid}> | |||
| <a href="https://nextjs.org/docs" className={styles.card}> | |||
| <h2>Documentation →</h2> | |||
| <p>Find in-depth information about Next.js features and API.</p> | |||
| </a> | |||
| <a href="https://nextjs.org/learn" className={styles.card}> | |||
| <h2>Learn →</h2> | |||
| <p>Learn about Next.js in an interactive course with quizzes!</p> | |||
| </a> | |||
| <a | |||
| href="https://github.com/vercel/next.js/tree/canary/examples" | |||
| className={styles.card} | |||
| > | |||
| <h2>Examples →</h2> | |||
| <p>Discover and deploy boilerplate example Next.js projects.</p> | |||
| </a> | |||
| <a | |||
| href="https://vercel.com/new?utm_source=create-next-app&utm_medium=default-template&utm_campaign=create-next-app" | |||
| className={styles.card} | |||
| > | |||
| <h2>Deploy →</h2> | |||
| <p> | |||
| Instantly deploy your Next.js site to a public URL with Vercel. | |||
| </p> | |||
| </a> | |||
| </div> | |||
| </main> | |||
| <footer className={styles.footer}> | |||
| <a | |||
| href="https://vercel.com?utm_source=create-next-app&utm_medium=default-template&utm_campaign=create-next-app" | |||
| target="_blank" | |||
| rel="noopener noreferrer" | |||
| > | |||
| Powered by{' '} | |||
| <span className={styles.logo}> | |||
| <Image src="/vercel.svg" alt="Vercel Logo" width={72} height={16} /> | |||
| </span> | |||
| </a> | |||
| </footer> | |||
| </div> | |||
| ) | |||
| } | |||
| export default Home | |||
| @@ -0,0 +1,4 @@ | |||
| <svg width="283" height="64" viewBox="0 0 283 64" fill="none" | |||
| xmlns="http://www.w3.org/2000/svg"> | |||
| <path d="M141.04 16c-11.04 0-19 7.2-19 18s8.96 18 20 18c6.67 0 12.55-2.64 16.19-7.09l-7.65-4.42c-2.02 2.21-5.09 3.5-8.54 3.5-4.79 0-8.86-2.5-10.37-6.5h28.02c.22-1.12.35-2.28.35-3.5 0-10.79-7.96-17.99-19-17.99zm-9.46 14.5c1.25-3.99 4.67-6.5 9.45-6.5 4.79 0 8.21 2.51 9.45 6.5h-18.9zM248.72 16c-11.04 0-19 7.2-19 18s8.96 18 20 18c6.67 0 12.55-2.64 16.19-7.09l-7.65-4.42c-2.02 2.21-5.09 3.5-8.54 3.5-4.79 0-8.86-2.5-10.37-6.5h28.02c.22-1.12.35-2.28.35-3.5 0-10.79-7.96-17.99-19-17.99zm-9.45 14.5c1.25-3.99 4.67-6.5 9.45-6.5 4.79 0 8.21 2.51 9.45 6.5h-18.9zM200.24 34c0 6 3.92 10 10 10 4.12 0 7.21-1.87 8.8-4.92l7.68 4.43c-3.18 5.3-9.14 8.49-16.48 8.49-11.05 0-19-7.2-19-18s7.96-18 19-18c7.34 0 13.29 3.19 16.48 8.49l-7.68 4.43c-1.59-3.05-4.68-4.92-8.8-4.92-6.07 0-10 4-10 10zm82.48-29v46h-9V5h9zM36.95 0L73.9 64H0L36.95 0zm92.38 5l-27.71 48L73.91 5H84.3l17.32 30 17.32-30h10.39zm58.91 12v9.69c-1-.29-2.06-.49-3.2-.49-5.81 0-10 4-10 10V51h-9V17h9v9.2c0-5.08 5.91-9.2 13.2-9.2z" fill="#000"/> | |||
| </svg> | |||
| @@ -0,0 +1,46 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| interface CreateUserResponse { | |||
| message: string; | |||
| } | |||
| export const createUser = async ( | |||
| fullName: string, | |||
| username: string, | |||
| email: string, | |||
| password: string, | |||
| address: string, | |||
| address2: string, | |||
| city: string, | |||
| country: string, | |||
| postcode: string | |||
| ): Promise<CreateUserResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.account.createUser}`, | |||
| { | |||
| method: 'POST', | |||
| body: JSON.stringify({ | |||
| fullName, | |||
| username, | |||
| email, | |||
| password, | |||
| address, | |||
| address2, | |||
| city, | |||
| country, | |||
| postcode, | |||
| }), | |||
| headers: { | |||
| 'Content-Type': 'application/json', | |||
| }, | |||
| } | |||
| ); | |||
| const data: CreateUserResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,12 @@ | |||
| export default { | |||
| account: { | |||
| createUser: '/api/auth/signup', | |||
| }, | |||
| products: '/api/product', | |||
| productsIds: '/api/product/productIds', | |||
| productsByCategory: '/api/product/category/', | |||
| featuredProducts: '/api/product/featured-products', | |||
| order: '/api/order', | |||
| userUpdate: '/api/user', | |||
| question: '/api/question', | |||
| }; | |||
| @@ -0,0 +1,27 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| import { OrderData } from '../../utils/interface/orderInterface'; | |||
| interface OrderDataDB extends OrderData { | |||
| id: string; | |||
| _id: string; | |||
| __v: number; | |||
| } | |||
| interface OrderResponse { | |||
| message: string; | |||
| orders: Array<OrderDataDB>; | |||
| } | |||
| export const getOrdersForOwner = async (id: string): Promise<OrderResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.order}?ownerID=${id}` | |||
| ); | |||
| const data: OrderResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,32 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| import { OrderData } from '../../utils/interface/orderInterface'; | |||
| interface OrderDataDB extends OrderData { | |||
| id: string; | |||
| _id: string; | |||
| __v: number; | |||
| } | |||
| interface OrderResponse { | |||
| message: string; | |||
| order: OrderDataDB; | |||
| } | |||
| export const postOrder = async ( | |||
| orderData: OrderData | |||
| ): Promise<OrderResponse> => { | |||
| const response = await fetch(`http://localhost:3000${apiEndpoints.order}`, { | |||
| method: 'POST', | |||
| body: JSON.stringify(orderData), | |||
| headers: { | |||
| 'Content-Type': 'application/json', | |||
| }, | |||
| }); | |||
| const data: OrderResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,28 @@ | |||
| import { ProductData } from '../../utils/interface/productInterface'; | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| interface ProductDataDB extends ProductData { | |||
| id: string; | |||
| _id: string; | |||
| __v: number; | |||
| } | |||
| interface FeaturedProductsResponse { | |||
| message: string; | |||
| featuredProducts: Array<ProductDataDB>; | |||
| } | |||
| export const getFeaturedProducts = | |||
| async (): Promise<FeaturedProductsResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.featuredProducts}` | |||
| ); | |||
| const data: FeaturedProductsResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,23 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| interface SingleProductResponse { | |||
| message: string; | |||
| product: object; | |||
| similarProducts: Array<object>; | |||
| } | |||
| export const getProductData = async ( | |||
| productId: string | |||
| ): Promise<SingleProductResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.products}/${productId}` | |||
| ); | |||
| const data: SingleProductResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,27 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| interface ProductsResponse { | |||
| message: string; | |||
| product: object; | |||
| productCount: number; | |||
| next: string; | |||
| previous: string; | |||
| } | |||
| export const getAllProducts = async ( | |||
| pageIndex: number, | |||
| category = 'All', | |||
| filter = 'asc' | |||
| ): Promise<ProductsResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.products}?pageIndex=${pageIndex}&category=${category}&filterType=${filter}` | |||
| ); | |||
| const data: ProductsResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,30 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| import { QuestionData } from '../../utils/interface/questionInterface'; | |||
| interface QuestionResponse { | |||
| message: string; | |||
| question: { [key: string]: string }; | |||
| } | |||
| export const postQuestion = async ( | |||
| questionData: QuestionData | |||
| ): Promise<QuestionResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.question}`, | |||
| { | |||
| method: 'POST', | |||
| body: JSON.stringify(questionData), | |||
| headers: { | |||
| 'Content-Type': 'application/json', | |||
| }, | |||
| } | |||
| ); | |||
| const data: QuestionResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,30 @@ | |||
| import apiEndpoints from '../apiEndpoints'; | |||
| import { UserData } from '../../utils/interface/userInterface'; | |||
| interface UpdateResponse { | |||
| message: string; | |||
| } | |||
| export const updateUser = async ( | |||
| userData: UserData, | |||
| _id: string | |||
| ): Promise<UpdateResponse> => { | |||
| const response = await fetch( | |||
| `http://localhost:3000${apiEndpoints.userUpdate}`, | |||
| { | |||
| method: 'PATCH', | |||
| body: JSON.stringify({ userData, _id }), | |||
| headers: { | |||
| 'Content-Type': 'application/json', | |||
| }, | |||
| } | |||
| ); | |||
| const data: UpdateResponse = await response.json(); | |||
| if (!response.ok) { | |||
| throw new Error(data.message || 'Something went wrong!'); | |||
| } | |||
| return data; | |||
| }; | |||
| @@ -0,0 +1,129 @@ | |||
| .container { | |||
| padding: 0 2rem; | |||
| } | |||
| .main { | |||
| min-height: 100vh; | |||
| padding: 4rem 0; | |||
| flex: 1; | |||
| display: flex; | |||
| flex-direction: column; | |||
| justify-content: center; | |||
| align-items: center; | |||
| } | |||
| .footer { | |||
| display: flex; | |||
| flex: 1; | |||
| padding: 2rem 0; | |||
| border-top: 1px solid #eaeaea; | |||
| justify-content: center; | |||
| align-items: center; | |||
| } | |||
| .footer a { | |||
| display: flex; | |||
| justify-content: center; | |||
| align-items: center; | |||
| flex-grow: 1; | |||
| } | |||
| .title a { | |||
| color: #0070f3; | |||
| text-decoration: none; | |||
| } | |||
| .title a:hover, | |||
| .title a:focus, | |||
| .title a:active { | |||
| text-decoration: underline; | |||
| } | |||
| .title { | |||
| margin: 0; | |||
| line-height: 1.15; | |||
| font-size: 4rem; | |||
| } | |||
| .title, | |||
| .description { | |||
| text-align: center; | |||
| } | |||
| .description { | |||
| margin: 4rem 0; | |||
| line-height: 1.5; | |||
| font-size: 1.5rem; | |||
| } | |||
| .code { | |||
| background: #fafafa; | |||
| border-radius: 5px; | |||
| padding: 0.75rem; | |||
| font-size: 1.1rem; | |||
| font-family: Menlo, Monaco, Lucida Console, Liberation Mono, DejaVu Sans Mono, | |||
| Bitstream Vera Sans Mono, Courier New, monospace; | |||
| } | |||
| .grid { | |||
| display: flex; | |||
| align-items: center; | |||
| justify-content: center; | |||
| flex-wrap: wrap; | |||
| max-width: 800px; | |||
| } | |||
| .card { | |||
| margin: 1rem; | |||
| padding: 1.5rem; | |||
| text-align: left; | |||
| color: inherit; | |||
| text-decoration: none; | |||
| border: 1px solid #eaeaea; | |||
| border-radius: 10px; | |||
| transition: color 0.15s ease, border-color 0.15s ease; | |||
| max-width: 300px; | |||
| } | |||
| .card:hover, | |||
| .card:focus, | |||
| .card:active { | |||
| color: #0070f3; | |||
| border-color: #0070f3; | |||
| } | |||
| .card h2 { | |||
| margin: 0 0 1rem 0; | |||
| font-size: 1.5rem; | |||
| } | |||
| .card p { | |||
| margin: 0; | |||
| font-size: 1.25rem; | |||
| line-height: 1.5; | |||
| } | |||
| .logo { | |||
| height: 1em; | |||
| margin-left: 0.5rem; | |||
| } | |||
| @media (max-width: 600px) { | |||
| .grid { | |||
| width: 100%; | |||
| flex-direction: column; | |||
| } | |||
| } | |||
| @media (prefers-color-scheme: dark) { | |||
| .card, | |||
| .footer { | |||
| border-color: #222; | |||
| } | |||
| .code { | |||
| background: #111; | |||
| } | |||
| .logo img { | |||
| filter: invert(1); | |||
| } | |||
| } | |||
| @@ -0,0 +1,26 @@ | |||
| html, | |||
| body { | |||
| padding: 0; | |||
| margin: 0; | |||
| font-family: -apple-system, BlinkMacSystemFont, Segoe UI, Roboto, Oxygen, | |||
| Ubuntu, Cantarell, Fira Sans, Droid Sans, Helvetica Neue, sans-serif; | |||
| } | |||
| a { | |||
| color: inherit; | |||
| text-decoration: none; | |||
| } | |||
| * { | |||
| box-sizing: border-box; | |||
| } | |||
| @media (prefers-color-scheme: dark) { | |||
| html { | |||
| color-scheme: dark; | |||
| } | |||
| body { | |||
| color: white; | |||
| background: black; | |||
| } | |||
| } | |||
| @@ -0,0 +1,20 @@ | |||
| { | |||
| "compilerOptions": { | |||
| "target": "es5", | |||
| "lib": ["dom", "dom.iterable", "esnext"], | |||
| "allowJs": true, | |||
| "skipLibCheck": true, | |||
| "strict": true, | |||
| "forceConsistentCasingInFileNames": true, | |||
| "noEmit": true, | |||
| "esModuleInterop": true, | |||
| "module": "esnext", | |||
| "moduleResolution": "node", | |||
| "resolveJsonModule": true, | |||
| "isolatedModules": true, | |||
| "jsx": "preserve", | |||
| "incremental": true | |||
| }, | |||
| "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"], | |||
| "exclude": ["node_modules"] | |||
| } | |||
| @@ -0,0 +1,18 @@ | |||
| import { ProductData } from './productInterface'; | |||
| import { UserData } from './userInterface'; | |||
| import { ObjectId } from 'mongodb'; | |||
| interface ShippingData extends UserData { | |||
| email: string; | |||
| } | |||
| export interface OrderData { | |||
| products: Array<ProductData>; | |||
| time: Date; | |||
| shippingAddress: ShippingData; | |||
| totalPrice: number; | |||
| numberOfItems: number; | |||
| fulfilled: boolean; | |||
| owner: ObjectId; | |||
| stripeCheckoutId: string; | |||
| } | |||
| @@ -0,0 +1,15 @@ | |||
| export interface ProductData { | |||
| category: string; | |||
| name: string; | |||
| image: string; | |||
| description: string; | |||
| place: string; | |||
| process: string; | |||
| people: string; | |||
| pairing: string; | |||
| available: boolean; | |||
| isFeatured: boolean; | |||
| price: number; | |||
| customID: string; | |||
| stripeID: string; | |||
| } | |||
| @@ -0,0 +1,6 @@ | |||
| export interface QuestionData { | |||
| email: string; | |||
| firstName: string; | |||
| lastName: string; | |||
| message: string; | |||
| } | |||
| @@ -0,0 +1,8 @@ | |||
| export interface UserData { | |||
| address: string; | |||
| address2: string; | |||
| city: string; | |||
| country: string; | |||
| fullName: string; | |||
| postcode: string; | |||
| } | |||