This Repo serves as an exercise in using Vue 3 with Nuxt to create a TV show application using the TV Maze API.
- Application Overview
- Features & Functionality
- Approach
- Setup & Run Application
- Code & Type checks & Tests
- CSR (Client Side Rendering) App
- Vue 3
- Nuxt - used for paged routing & SSG (Static Site Generation)
- Tailwind CSS - for rapid fast css styling
- Vitest - for writing unit tests
- Nuxt
- Icon - Easy add icons
- UI - Easy add UI components
- Image - Responsive image handeling
- Eslint - Linting code quality
- API
- Nuxt API Party - Generates composables to do cached REST API calls
- Tanstack - Easily make paged REST API calls
- First view of TV Shows on Home which are categorized and sorted by highest rating first
- View overview of all TV Show in a grid or list
- Search for TV Shows
- View TV Show details
- More unit tests
- State Management with Pinia for storing favourite shows
- Use more of Vue / Nuxt, like:
- Provide / Inject
- Reactive
- LazyComponents
Clear separation of concerns within components, composables and utils.
- Components
- Logical components (contextual) - Compositions
/components/shows
&/components/show
-><Shows />
&<Show />
- API calls, data transformation and rendering are being handled in its own components. These components could be standalone and used in many other contexts (pages, other components, sharable within apps as packages).
- Generic Components (common) - Inheritance
/components/common
-><Common[ComponentName] />
- Generic components without contextual knowledge about TV Shows or API structures. It used the generic
Data
type to render data and uses some inheritance. - Mainly for UI.
- We use components in
components/common/overview
&components/common/overview-item
to render the transformed data to display the TV Shows in different layouts. - Outside of components we determine things like data handling, which HTML5 elements we wrap them, margins and spacings
- Logical components (contextual) - Compositions
- Composables
/composables/shows
&/composables/show
are used to fetch the data from the API and transform the data to a generic format.
- Utils
/utils/data
helps transform the API Data to a generic data format. This helps to get the data in a fixed format so we can easily sort, map, filter and reduce data, i.e. sort and categorize the TV shows based on their genres.
DRY, Single Responsibility Principle, Composition over inheritance, Separation of concerns, Abstraction, Future-proofing, Scalability, Reusability & Maintainability.
I agree, this is over-engineerd for what it needs to do for such a small application.
The data didn't need to be transformed and logic didn't need to be abstracted.
The rationale behind this is that I want to display my thought process and how I would normally approach a project, by thinking more abstract and steps ahead.
Because what if we would:
- use other api services to get additional information about a show or we would like to also display movies later on?
- seperate the data from the view (usually done with a dataLayer from a server)
- get a lot of business logic
- Create a Vue / Nuxt 3 project
- Use the TV Maze API to search for TV shows
- Display search results
- Display TV show details
- Categorize TV Shows
- Sort TV Shows by rating
- Responsive & Fine tune Design
- Create unit tests
- Utils
- Components
- Composables
- Dark mode switcher
- Switch between GRID or LIST view on the
/shows
and/search
page. - Paged TV Shows & Search Results (using
@tanstack/vue-query
) - Componentize the
<Overview />
further into child component - Add a skeleton when fetching data on Home
- Add a loading spinner or skeleton when fetching data on other pages
- Store favourite shows in a state manager like
Pinia
- e2e tests using Playwright
Please use the following instructions to setup and run the application.
These package managers are not tested and might fail when running the application:
# npm
npm install
# pnpm
pnpm install
# yarn
yarn install
# bun
bun install
Start the development server on http://localhost:3000
:
# npm
npm run dev
# pnpm
pnpm run dev
# yarn
yarn dev
# bun
bun run dev
Build the application for production:
# npm
npm run build
# pnpm
pnpm run build
# yarn
yarn build
# bun
bun run build
Locally preview production build:
# npm
npm run preview
# pnpm
pnpm run preview
# yarn
yarn preview
# bun
bun run preview
Check out the Nuxt deployment documentation for more information.
To run the linter, run:
# npm
npm run test
# pnpm
pnpm run preview
# yarn
yarn preview
# bun
bun run preview
Tests are written using Vitest, run:
# npm
npm run test
# pnpm
pnpm run test
# yarn
yarn test
# bun
bun run test