4 State Management

State Management

Deadline: Saturday, May 9, 2026.

Plagiarism is theft and is unacceptable. It undermines creativity, damages intellectual integrity, and destroys the purpose of learning. This also applies to contract cheating (opens in a new tab) and the mindless use of chatbots/agents.1

<Collection>
<Deck>
<Slide>
<Card>
</Card>
</Slide>
</Deck>
</Collection>

Requirements

Continuing the flashcards application, implement the client application from 2 Client Rendering using React and Next.js, including filtering and shuffling. Use exclusively the API interface from 3 RESTful Interfaces for all data operations, without web storage.

Components

Reuse the styles.css stylesheet from 2 Client Rendering and import (opens in a new tab) it in the root layout, app/layout.jsx, so its CSS classes are available globally across all components. Use the Lucide React (opens in a new tab) package to include the icons.

UML state diagram for a drills and callbacksPageCollectionDeckSlideCarddecks,callbackcallback()deck,callbackcallback()slide,callbackcallback()card,callbackcallback()

The root layout is always a server component (RSC). Mark your page, app/page.jsx, as a client component (RCC) and create the following four client components to render the collection:

  • Collection renders the tags and decks.
  • Deck renders the title, tags, a form to create a new slide, and slides.
  • Slide renders the title, tags, a form to create a new card, and cards.
  • Card renders the type-specific content and tags.

The tags will be dynamically generated and rendered in the Collection, Deck, and Slide components. You can either use state and effect hooks to generate and store them, or use a memoization (opens in a new tab) hook to compute them from the current state:

components/deck.jsx
export default function Deck({ deck }) {
  const tags = useMemo(() => •••, [deck]);
}

Define a NEXT_PUBLIC_API_BASE environment (opens in a new tab) variable to store the base path of the external RESTful API that hosts the collection:

.env
NEXT_PUBLIC_API_BASE=https://queue.qa/cmps350/assignments/03-restful-interfaces/api

Use process.env.NEXT_PUBLIC_API_BASE when specifying the URL for the Fetch API. You will have to update all your fetch() calls to include credentials, as the API uses cookies and tokens (JWT (opens in a new tab)) to support multiple users:

const response = await fetch(`${process.env.NEXT_PUBLIC_API_BASE}/•••`, {
  •••
  credentials: "include",
});

Synchronization

The collection will be fetched in page.jsx when it first mounts and passed to a child component to be rendered. The collection is then fetched, on demand, whenever an operation successfully mutates the server state, for example, creating a deck/slide or deleting a card.

Use state and effect hooks, based on 9 Synchronized State, to keep the client application state synchronized with the server state.

Actions

Create and use a server action to add or remove a card from a list of favorites. This list is independent of the external API, managed by your server, and stored as a local variable in the server actions module (it is not persistent).

Define a separate state variable in page.jsx to store the list of favorites, as was done previously for the collection of decks, and update it whenever necessary. This state must also be drilled down to the Card component so that favorited cards can be displayed differently using inline styles.

Guidelines

  1. Push your solution to your private repository under assignments/04-state-management.
  2. Commit often and use meaningful message summaries and descriptions.
  3. Complete your work before the deadline; no late submissions.

Codebase

The following structure should be used to organize the codebase. There is no need to create additional top-level directories/files, but more directories/files can be created under app and results.

      • actions.js
      • layout.jsx
      • page.jsx
      • styles.css
      • card.jsx
      • collection.jsx
      • deck.jsx
      • slide.jsx
    • .env
    • .gitignore
    • biome.json
    • jsconfig.json
    • next.config.mjs
    • package.json
    • postcss.config.mjs
    • readme.md
  • Report

    Include a screenshot of the rendered page under results and push it along with the assignment.

    Complete the readme.md report and push it along with the assignment.

    readme.md
    # Report
     
    Xane Doe [email protected]
     
    ## 4 State Management
     
    | Task            | Done? | Comments             |
    | :-------------- | :---- | :------------------- |
    | Components      | [ ]   |                      |
    | Server          | [ ]   |                      |
    | Client          | [ ]   |                      |
    | Fetching        | [ ]   |                      |
    | Rendering       | [ ]   |                      |
    | Drilling        | [ ]   |                      |
    | Conditionals    | [ ]   |                      |
    | Events          | [ ]   |                      |
    | Hooks           | [ ]   |                      |
    | Callbacks       | [ ]   |                      |
    | Synchronization | [ ]   |                      |
    | Actions         | [ ]   |                      |
    | Screenshots     | [ ]   |                      |
    | Report          | [x]   | Markdown is the way. |
    | Plagiarism      | [ ]   |                      |

    Rubric

    TaskPointsDetails
    Components+80Fetching, Rendering, Drilling, Conditionals, Events, Hooks
    Synchronization+20Hooks, Callbacks
    Actions+20Bonus
    Screenshots+5
    Quality+5Clean, structured, well-organized, indented code
    Report-20Evaluation, Comments
    Plagiarism-∞
    Total110

    Footnotes

    1. Student Code of Conduct Policy (opens in a new tab) / Article (1) — سياسة النظام الطلابي (opens in a new tab) \ البند (١).