This is my study notes, which guide you through creating a voting application to help you get familiar with Next.js. By following this tutorial, you will complete the implementation of both the front-end and back-end, establish the database, deploy it online, and integrate linting and unit tests. The following is a detailed document introduction, including product introduction, installation guide, technical selection considerations, and the amount of time I spent on this exercise.
This is a popular product voting list that allows you to log in using your GitHub account.
Basic Information:
- Administrators have the ability to add and remove products.
- Both administrators and regular users are able to cast votes.
- The product list will be sorted by the number of votes from high to low.
Here are some detailed introductions:
- Administrator's Perspective: (with add product and remove)
- Common User's Perspective:
- Administrators have the capability to publish products and edit the product title, description, image, and product URL.
- During the editing process, the validity of the parameters for the administrator's input will be verified.
Technique Stack | |
---|---|
Language | TypeScript |
Framework | Next.js |
Styling | Tailwind |
Database | Upstash |
Auth | next-auth |
Data Fetching | SWR |
Unit Test | Jest |
Lint | ESLint |
-
Set up project
Unzip the Yu.Tian file, open your terminal, and enter the Yu.Tian folder, then install all the dependencies.
You can use
npm install
to install all required dependencies, but it is recommended to useyarn
instead for faster installation and consistency. -
Set your environment variables
To set up your environment variables, follow these steps:
-
Copy the
.env.local.example
file to.env.local
:cp .env.local.example .env.local
-
The
.env.local.example
file contains a description of all the environment variables. Here is a brief overview of each variable:# A URL for the Redis REST API UPSTASH_REDIS_REST_URL= # Redis REST API token that verifies that the sender of the request has access to the Redis REST API. UPSTASH_REDIS_REST_TOKEN= # Authentication ID of GitHub GITHUB_ID= # Authentication secret of GitHub GITHUB_SECRET= # A list of administrator GitHub emails, separated by ',' NEXT_PUBLIC_ADMIN_EMAILS=ceadatian@gmail.com # Secret key of NextAuth # generate one here: https://generate-secret.vercel.app/32 NEXTAUTH_SECRET= # Mandatory NextAuth URL for localhost NEXTAUTH_URL=http://localhost:3000
-
-
Register database
To access Upstash, log in to the Upstash Console using your GitHub account. Create a new database and retrieve the
UPSTASH_REDIS_REST_URL
andUPSTASH_REDIS_REST_TOKEN
. -
Set up user authentication by next-auth
To set up GitHub OAuth using the next-auth library, follow these steps:
- Navigate to the GitHub Developer Settings on GitHub.
- Click on "New GitHub App”.
- Name your "GitHub App name”.
- Set the "Homepage URL” (or just a placeholder, if you don't have a website yet).
- Add the "Callback URL”, and put
http://localhost:3000
. The "Callback URL" is crucial as it is where the user will be redirected after logging in with their GitHub account. If deploying the website online, don't forget to update the "Callback URL" to the online domain. In my case, I changed it tohttps://yu-tian-woven.vercel.app/
. - Generate a new client secret by clicking on the button after successfully creating your app. Copy the client secret you generated and paste it under the
GITHUB_SECRET
value in your.env
file. - Copy the Client ID and paste it under the
GITHUB_ID
value in your.env
file.
-
Run Your Project
- To run the project locally, open the project folder and run either
npm run dev
oryarn dev
. - To run the lint and automatically fix lint errors, use either
npm run lint
oryarn lint
. To fix lint errors, use eithernpm run lint:fix
oryarn lint:fix
. - To build the project, run either
npm run build
oryarn build
.
- To run the project locally, open the project folder and run either
-
Add Administrators
Only administrators can add and remove products. To specify the administrator's GitHub email, set the environment variable
NEXT_PUBLIC_ADMIN_EMAILS
with a comma-separated list of emails. -
Deploy to Vercel
To deploy the project to Vercel, first create a new GitHub repository and push your local changes. Then, follow the instructions in Vercel's documentation for Deploying a Git Repository. Make sure to add all the necessary Environment Variables.
-
Tailwind CSS
Tailwind CSS is an advanced CSS framework that utilizes a set of CSS classes to define styles. I chose it for the following reasons:
- Atomic CSS: Tailwind adopts a highly granular and atomic approach to styling, enabling maximum customization and versatility.
- Design System: Tailwind offers a consistent design system, ensuring a uniform look and reducing the need to spend time thinking about styling and design.
In conclusion, Tailwind CSS is a robust and flexible CSS framework that enables fast and effortless application development.
-
Database: Upstash
Upstash provides a serverless architecture for managing and maintaining all your database services. With Upstash, you can easily integrate its SDK into your project, configure the request URL in your environment variables, and you're ready to go. All server management and maintenance work is completed by Upstash. If I use a traditional way like express + MySQL, I need to write GitHub Action deployment, write my own container orchestration solution, and finally ship it to a container service. So Upstash is much more convenient and lets me focus on the main logic of the product itself.
Serverless databases like Upstash boast strong performance as evidenced by articles like "One Million Queries Per Second with MySQL - PlanetScale (Serverless MySQL)".
-
Fetching data: SWR
In my project, I centralized the management of data requests by abstracting the API and data layers in the store/index file. I chose SWR as my data-fetching library for many advantages. SWR provides faster updates by serving stale data while fetching fresh data in the background. It also ensures that users have a seamless experience, even when offline, by automatically caching the data. Additionally, SWR revalidates the data whenever it becomes stale, keeping the user's information up-to-date. SWR is also lightweight and efficient, with a small size and a simple, intuitive API that is easy to use, even for developers new to data-fetching libraries.
-
Full-stack framework: Next.js
Next.js is a full-stack JavaScript framework. I chose Next.js as it provides a better way of organizing front-end and back-end code compared to traditional front-end and back-end separation development methods. It combines the benefits of both front-end UI frameworks and back-end Node.js server frameworks and provides a streamlined solution for building full-stack applications. With Next.js, you can enjoy server-side rendering, built-in optimizations, and a simple and intuitive API. This allows developers to focus on building their applications in a very fast and easy way. In Next.js, the pages directory acts as the application's router, automatically creating a route for each
.tsx
file. The file name is the route path, for instance,pages/index.tsx
is the root path of the application, that is "/". The_app.tsx
file in Next.js is a special file that is used to customize the overall behavior of the application, serving as a wrapper for all pages and providing common functionality.When reviewing the code, be sure to pay attention to both
pages/index.tsx
andpages/_app.tsx
.
- Technique stack selection: 6 hours
- Setting up the database and implementing both front-end and back-end: 12 hours
- Integrating lint and unit tests, deploying online: 6 hours
-
If you meet Jest SyntaxError: Unexpected token
<
Changing
tsconfig.json
:"jsx": "preserve" -> "jsx": "react"