Skip to content

Commit

Permalink
chore: Improve the overall documentation (#16)
Browse files Browse the repository at this point in the history
* Add initial doc comments

* Other doc comments

* More comments

* Moar comments 🔥

* Docs again 🔥

* Document the env variables

* Update README.md

* Create LICENSE

* Update README.md

* Update README.md

* Update README.md

* Update README.md

* Edit `checkout-token` into `checkout-id`

* Add color aliases

* Add agnostic logo

* Remove shipping estimate icon

* Update README.md

* Update README.md

* Update steps
  • Loading branch information
dgopsq authored Sep 7, 2023
1 parent 7f68bdb commit 097d04f
Show file tree
Hide file tree
Showing 86 changed files with 332 additions and 285 deletions.
1 change: 1 addition & 0 deletions .env.local.example
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
NEXT_PUBLIC_GRAPHQL_URL=SALEOR_GRAPHQL_URL_HERE
6 changes: 5 additions & 1 deletion .eslintrc.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,11 @@
"plugins": ["@typescript-eslint"],
"root": true,

"ignorePatterns": ["src/__generated__/*", "next.config.js"],
"ignorePatterns": [
"src/__generated__/*",
"next.config.js",
"tailwind.config.js"
],

"rules": {
"no-unused-vars": ["off"],
Expand Down
3 changes: 0 additions & 3 deletions .vscode/settings.json

This file was deleted.

21 changes: 21 additions & 0 deletions LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
MIT License

Copyright (c) 2023 Diego Pasquali

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
44 changes: 21 additions & 23 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,34 +1,32 @@
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:
[Saleor](https://saleor.io/) storefront built using [Next.js](https://nextjs.org/) 13 and the new **App Router**.

```bash
npm run dev
# or
yarn dev
# or
pnpm dev
```
> [!NOTE]
> This repository is currently **👷‍♀️ WIP 👷** and it's **NOT** a production ready storefront. Feel free to open an issue if you see bugs or sections that could be improved!
Open [http://localhost:3000](http://localhost:3000) with your browser to see the result.
## Features

You can start editing the page by modifying `app/page.tsx`. The page auto-updates as you edit the file.
- 🕺 Fully functional Saleor storefront using the new Next 13 app router
- 💅 Styled using [Tailwind](https://tailwindcss.com/)
- 🛒 Multi steps checkout with Stripe (using the [Saleor Stripe App](https://docs.saleor.io/docs/3.x/developer/app-store/apps/stripe))
- 📚 Out of the box i18n with [next-intl](https://next-intl-docs.vercel.app/)
- 💁‍♀️ User profile page handling the latest orders, all the personal addresses and the security informations
- 🏛️ Fully developed using Apollo with the new [`useFragment`](https://www.apollographql.com/docs/react/api/react/hooks/#usefragment) hook in order to react to data changes

This project uses [`next/font`](https://nextjs.org/docs/basic-features/font-optimization) to automatically optimize and load Inter, a custom Google Font.

## Learn More
## Getting Started

To learn more about Next.js, take a look at the following resources:
**Requirements:**
- An instance of the _Saleor_ backend up and running (the easiest way is probably to use [Saleor Cloud](https://cloud.saleor.io/) and its free tier)
- The [Saleor Stripe App](https://docs.saleor.io/docs/3.x/developer/app-store/apps/stripe) installed in the dashboard

- [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.
**Follow these steps in order to execute the project correctly:**

You can check out [the Next.js GitHub repository](https://github.com/vercel/next.js/) - your feedback and contributions are welcome!
1. Rename the `.env.local.example` into `.env.local` and fill the `NEXT_PUBLIC_GRAPHQL_URL` environment variable with the correct URL to your GraphQL API
2. Start the project in development mode using `pnpm dev`
3. Open [http://localhost:3000](http://localhost:3000) with your browser
4. 🎉

## Deploy on Vercel
## Configuration

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.
You can configure your storefront using the environment variables in [`src/misc/config.ts`](https://github.com/dgopsq/saleor-nextjs-base/blob/main/src/misc/config.ts). The only required configuration is `NEXT_PUBLIC_GRAPHQL_URL`, everything else is optional and has been documented directly in the file.

Check out our [Next.js deployment documentation](https://nextjs.org/docs/deployment) for more details.
2 changes: 1 addition & 1 deletion src/components/checkout/Cart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ import { useTranslations } from "next-intl";
import { useRouter } from "next/navigation";

/**
*
* The cart page.
*/
export const Cart: React.FC = () => {
const t = useTranslations("Checkout");
Expand Down
7 changes: 4 additions & 3 deletions src/components/checkout/CartButton.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,18 @@ import { CartIcon } from "@/components/core/Icon";
import { useCheckoutInfo } from "@/misc/hooks/useCheckoutInfo";

/**
*
* The cart button composed by an icon and the
* number of items in the cart.
*/
export const CartButton: React.FC = () => {
const { data } = useCheckoutInfo();
const totalItems = data?.lines.length ?? 0;

return (
<div className="group -m-2 flex items-center p-2">
<CartIcon className="h-6 w-6 flex-shrink-0 text-gray-400 group-hover:text-gray-500" />
<CartIcon className="h-6 w-6 flex-shrink-0 text-secondary-400 group-hover:text-secondary-500" />

<span className="ml-2 text-sm font-medium text-gray-700 group-hover:text-gray-800">
<span className="ml-2 text-sm font-medium text-secondary-700 group-hover:text-secondary-800">
{totalItems}
</span>
</div>
Expand Down
8 changes: 4 additions & 4 deletions src/components/checkout/CartProducts.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ type Props = {
};

/**
*
* The list of products in the cart.
*/
export const CartProducts: React.FC<Props> = ({
products,
Expand Down Expand Up @@ -51,7 +51,7 @@ export const CartProducts: React.FC<Props> = ({
);

return (
<ul role="list" className="divide-y divide-gray-100">
<ul role="list" className="divide-y divide-secondary-100">
{products.map((line, index) => {
const imageUrl = line.variant.images[0]?.url ?? null;
const imageAlt = line.variant.images[0]?.alt ?? "";
Expand Down Expand Up @@ -101,7 +101,7 @@ export const CartProducts: React.FC<Props> = ({
{line.variant.attributes.map(({ attribute, values }) => (
<p
key={attribute.id}
className="mt-2 text-sm font-medium text-gray-400"
className="mt-2 text-sm font-medium text-secondary-400"
>
{`${attribute.name}: ${values
.map((value) => value.name)
Expand All @@ -114,7 +114,7 @@ export const CartProducts: React.FC<Props> = ({
<p
className={classNames(
compact ? "text-sm" : "",
"font-semibold text-gray-900"
"font-semibold text-secondary-900"
)}
>
{line.variant.price
Expand Down
25 changes: 9 additions & 16 deletions src/components/checkout/CartSummary.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import { QuestionIcon } from "@/components/core/Icon";
import { formatPrice } from "@/misc/currencies";
import { Checkout } from "@/queries/checkout/data";
import { useTranslations } from "next-intl";
Expand All @@ -8,7 +7,7 @@ type Props = {
};

/**
*
* The summary of the cart used in the checkout.
*/
export const CartSummary: React.FC<Props> = ({ checkout }) => {
const t = useTranslations("Checkout");
Expand All @@ -17,8 +16,8 @@ export const CartSummary: React.FC<Props> = ({ checkout }) => {
<dl className="mt-6 space-y-4">
{checkout.subtotalPrice ? (
<div className="flex items-center justify-between">
<dt className="text-sm text-gray-600">{t("Subtotal")}</dt>
<dd className="text-sm font-medium text-gray-900">
<dt className="text-sm text-secondary-600">{t("Subtotal")}</dt>
<dd className="text-sm font-medium text-secondary-900">
{formatPrice(
checkout.subtotalPrice.amount,
checkout.subtotalPrice.currency
Expand All @@ -28,17 +27,11 @@ export const CartSummary: React.FC<Props> = ({ checkout }) => {
) : undefined}

{checkout.shippingPrice ? (
<div className="flex items-center justify-between border-t border-gray-200 pt-4">
<dt className="flex items-center text-sm text-gray-600">
<div className="flex items-center justify-between border-t border-secondary-200 pt-4">
<dt className="flex items-center text-sm text-secondary-600">
<span>{t("Shipping estimate")}</span>
<a
href="#"
className="ml-2 flex-shrink-0 text-gray-400 hover:text-gray-500"
>
<QuestionIcon className="h-5 w-5" />
</a>
</dt>
<dd className="text-sm font-medium text-gray-900">
<dd className="text-sm font-medium text-secondary-900">
{formatPrice(
checkout.shippingPrice.amount,
checkout.shippingPrice.currency
Expand All @@ -48,11 +41,11 @@ export const CartSummary: React.FC<Props> = ({ checkout }) => {
) : undefined}

{checkout.totalPrice ? (
<div className="flex items-center justify-between border-t border-gray-200 pt-4">
<dt className="text-base font-medium text-gray-900">
<div className="flex items-center justify-between border-t border-secondary-200 pt-4">
<dt className="text-base font-medium text-secondary-900">
{t("Order total")}
</dt>
<dd className="text-base font-medium text-gray-900">
<dd className="text-base font-medium text-secondary-900">
{formatPrice(
checkout.totalPrice.amount,
checkout.totalPrice.currency
Expand Down
2 changes: 1 addition & 1 deletion src/components/checkout/CheckoutAddAddress.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ type Props = {
};

/**
*
* The form to add a new address in the checkout.
*/
export const CheckoutAddAddress: React.FC<Props> = ({
onCancel,
Expand Down
2 changes: 1 addition & 1 deletion src/components/checkout/CheckoutAddressUser.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ type Props = {
};

/**
*
* The list of addresses of the user in the checkout.
*/
export const CheckoutAddressUser: React.FC<Props> = ({
addresses,
Expand Down
6 changes: 3 additions & 3 deletions src/components/checkout/CheckoutComplete.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { useGuestOrderAccountStore } from "@/misc/states/guestOrderAccount";
import { useTranslations } from "next-intl";

/**
*
* The checkout complete page.
*/
export const CheckoutComplete: React.FC = () => {
const t = useTranslations("Checkout");
Expand All @@ -23,7 +23,7 @@ export const CheckoutComplete: React.FC = () => {
</div>

<div className="mt-4">
<p className="text-xl text-gray-600">
<p className="text-xl text-secondary-600">
{t("You will receive an email confirmation shortly")}
</p>
</div>
Expand All @@ -46,7 +46,7 @@ export const CheckoutComplete: React.FC = () => {
) : (
<div>
<div className="mt-14">
<p className="text-md text-gray-500">
<p className="text-md text-secondary-500">
{t.rich(
"Keep track of your order in your Profile Page or Continue your shopping",
{
Expand Down
2 changes: 1 addition & 1 deletion src/components/checkout/CheckoutDeliveryMethods.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ type Props = {
};

/**
*
* The list of shipping methods in the checkout.
*/
export const CheckoutDeliveryMethod: React.FC<Props> = ({
deliveryMethods,
Expand Down
2 changes: 1 addition & 1 deletion src/components/checkout/CheckoutPaymentGateway.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ type Props = {
};

/**
*
* The list of payment gateways in the checkout.
*/
export const CheckoutPaymentGateway: React.FC<Props> = ({
paymentGateways,
Expand Down
26 changes: 17 additions & 9 deletions src/components/checkout/CheckoutSteps.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { CheckIcon, SuccessIcon } from "@/components/core/Icon";
import { Route } from "next";
import { useTranslations } from "next-intl";
import Link from "next/link";
Expand All @@ -18,7 +19,7 @@ type Props = {
};

/**
*
* The steps component used during the checkout.
*/
export const CheckoutSteps: React.FC<Props> = ({ currentStep }) => {
const t = useTranslations("Checkout");
Expand All @@ -38,26 +39,33 @@ export const CheckoutSteps: React.FC<Props> = ({ currentStep }) => {
<li key={step.name} className="md:flex-1">
{currentStep > index ? (
<Link href={step.route}>
<span className="group flex flex-col border-l-4 border-indigo-600 py-2 pl-4 hover:border-indigo-800 md:border-l-0 md:border-t-4 md:pb-0 md:pl-0 md:pt-4">
<span className="text-sm font-medium text-indigo-600 group-hover:text-indigo-800">
{formatStepIndex(index)}
<span className="group flex flex-col p-4 border border-primary-600 bg-primary-600 rounded-lg">
<div className="flex flex-row items-center justify-between">
<span className="text-sm font-medium text-white">
{formatStepIndex(index)}
</span>

<SuccessIcon className="text-white w-5 h-5" />
</div>

<span className="text-sm font-medium text-white">
{step.name}
</span>
<span className="text-sm font-medium">{step.name}</span>
</span>
</Link>
) : currentStep === index ? (
<span
className="flex flex-col border-l-4 border-indigo-600 py-2 pl-4 md:border-l-0 md:border-t-4 md:pb-0 md:pl-0 md:pt-4"
className="flex flex-col p-4 bg-secondary-50 border border-secondary-50 rounded-lg"
aria-current="step"
>
<span className="text-sm font-medium text-indigo-600">
<span className="text-sm font-medium text-primary-600">
{formatStepIndex(index)}
</span>
<span className="text-sm font-medium">{step.name}</span>
</span>
) : (
<span className="group flex flex-col border-l-4 border-gray-200 py-2 pl-4 hover:border-gray-300 md:border-l-0 md:border-t-4 md:pb-0 md:pl-0 md:pt-4">
<span className="text-sm font-medium text-gray-500 group-hover:text-gray-700">
<span className="group flex flex-col p-4 border border-secondary-100 rounded-lg">
<span className="text-sm font-medium text-secondary-500 group-hover:text-secondary-700">
{formatStepIndex(index)}
</span>
<span className="text-sm font-medium">{step.name}</span>
Expand Down
2 changes: 1 addition & 1 deletion src/components/checkout/CheckoutSummary.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ type Props = {
};

/**
*
* The order's summary in the checkout.
*/
export const CheckoutSummary: React.FC<Props> = ({
checkout,
Expand Down
4 changes: 3 additions & 1 deletion src/components/checkout/Informations.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@ import { useCheckoutGuard } from "@/misc/hooks/useCheckoutGuard";
import { useUserInfo } from "@/misc/hooks/useUserInfo";

/**
*
* Hub component for the checkout informations.
* It will render the guest or user informations
* depending on the user state.
*/
export const Informations: React.FC = () => {
const userInfo = useUserInfo();
Expand Down
Loading

0 comments on commit 097d04f

Please sign in to comment.