You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
Web-Dev-For-Beginners/translations/pcm/7-bank-project/4-state-management
localizeflow[bot] 9e661e295d
chore(i18n): sync translations with latest source changes (chunk 1/1, 291 changes)
7 months ago
..
README.md chore(i18n): sync translations with latest source changes (chunk 1/1, 291 changes) 7 months ago
assignment.md chore(i18n): sync translations with latest source changes (chunk 1/1, 291 changes) 7 months ago

README.md

Build a Banking App Part 4: Concepts of State Management

Wetin You Fit Do for Di Next 5 Minutes

Quick Start Pathway for Busy Developers

flowchart LR
    A[⚡ 5 minutes] --> B[Diagnose state wahala]
    B --> C[Create central state object]
    C --> D[Add updateState function]
    D --> E[See immediate improvements]
  • Minute 1: Test di current state wahala - log in, refresh page, see logout
  • Minute 2: Change let account = null to let state = { account: null }
  • Minute 3: Make one simple updateState() function for controlled updates
  • Minute 4: Change one function to use di new pattern
  • Minute 5: Test di better predictability and debugging power

Quick Diagnostic Test:

// Before: Scatter state
let account = null; // Lost when you refresh!

// After: Centralize state
let state = Object.freeze({ account: null }); // Control and fit track am!

Why This Matters: For 5 minutes, you go experience di change from chaotic state management go predictable, debuggable patterns. Na dis foundation wey make complex apps fit still dey manageable.

🗺️ Your Learning Journey Through State Management Mastery

journey
    title From Scattered State to Professional Architecture
    section Diagnosing Problems
      Identify state loss issues: 3: You
      Understand scattered updates: 4: You
      Recognize architecture needs: 6: You
    section Centralizing Control
      Create unified state object: 5: You
      Implement controlled updates: 7: You
      Add immutable patterns: 8: You
    section Adding Persistence
      Implement localStorage: 6: You
      Handle serialization: 7: You
      Create session continuity: 9: You
    section Balancing Freshness
      Address data staleness: 5: You
      Build refresh systems: 8: You
      Achieve optimal balance: 9: You

Your Journey Destination: By di end of dis lesson, you go build professional-grade state management system wey dey handle persistence, data freshness, and predictable updates - na di same pattern wey production apps dey use.

Pre-Lecture Quiz

Pre-lecture quiz

Introduction

State management be like di navigation system wey dey for Voyager spacecraft when everything dey work smooth, you no go too notice am. But when wahala show, na im go make difference between reaching interstellar space and drifting lost for cosmic void. For web development, state mean everything wey your app need to remember: user login status, form data, navigation history, and temporary interface states.

As your banking app don grow from simple login form to more advanced application, you for already meet some common challenges. You refresh page, users dey logout unexpectedly. You close browser, progress disappear. You want debug problem, you dey search many functions wey dey change di same data in different ways.

Dis no mean say coding bad na nature wahala wey show anytime app reach certain level of complexity. Every developer dey face dis kind challenge as dem app dey change from "proof of concept" to "production ready."

For dis lesson, we go implement centralized state management system wey go turn your banking app to reliable, professional application. You go learn how to manage data flows predictably, keep user sessions correct, and make smooth user experience wey modern web apps need.

Prerequisites

Before you dive into state management concepts, you need get your development environment set up well and your banking app base ready. Dis lesson dey build directly on concepts and code wey dey previous parts of dis series.

Make sure say you get dis things ready before you continue:

Required Setup:

  • Complete di data fetching lesson - your app suppose fit load and display account data well
  • Install Node.js for your system to run backend API
  • Start di server API locally to handle account data work

Testing Your Environment:

Make sure say your API server dey run correct by running dis command for terminal:

curl http://localhost:5000/api
# -> e suppose return "Bank API v1.0.0" as result

Wetin dis command dey do:

  • Send GET request to your local API server
  • Test connection and check if server dey respond
  • Return API version info if everything dey work right

🧠 State Management Architecture Overview

mindmap
  root((State Management))
    Current Problems
      Session Loss
        Page Refresh Issues
        Browser Close Impact
        Variable Reset Problems
      Scattered Updates
        Multiple Modification Points
        Debugging Challenges
        Unpredictable Behavior
      Incomplete Cleanup
        Logout State Issues
        Memory Leaks
        Security Concerns
    Centralized Solutions
      Unified State Object
        Single Source of Truth
        Predictable Structure
        Scalable Foundation
      Controlled Updates
        Immutable Patterns
        Object.freeze Usage
        Function-Based Changes
      State Tracking
        History Management
        Debug Visibility
        Change Auditing
    Persistence Strategies
      localStorage Integration
        Session Continuity
        JSON Serialization
        Automatic Sync
      Data Freshness
        Server Refresh
        Stale Data Handling
        Balance Optimization
      Storage Optimization
        Minimal Data
        Performance Focus
        Security Considerations

Core Principle: Professional state management dey balance predictability, persistence, and performance to create reliable user experiences wey fit scale from simple interactions to complex app workflows.


Diagnosing the Current State Issues

Like Sherlock Holmes wey dey inspect crime scene, we need understand wetin exactly dey happen for current implementation before we fit solve di mystery of disappearing user sessions.

Make we do simple experiment wey go show di main state management wahala:

🧪 Try This Diagnostic Test:

  1. Log into your banking app and go dashboard
  2. Refresh browser page
  3. Observe wetin happen to your login status

If you carry you redirect back to login screen, you don find di classic state persistence problem. Dis one happen because our current implementation dey store user data for JavaScript variables wey dey reset anytime page load.

Current Implementation Problems:

Di simple account variable wey we get for our previous lesson dey cause three big wahala wey affect both user experience and code maintainability:

Wahala Technical Cause User Impact
Session Loss Page refresh dey clear JavaScript variables Users go dey re-authenticate every now and then
Scattered Updates Many functions dey change state directly Debugging go dey harder and harder
Incomplete Cleanup Logout no dey clear all state references Potential security and privacy wahala

The Architectural Challenge:

Like how Titanic get compartment system wey look strong until plenty compartments fill with water at once, to fix dis problems one by one no go solve di main architectural problem. We need big state management solution.

💡 Wetin we really dey try do here?

State management na to solve two main puzzles:

  1. Where's My Data?: Make we sabi wetin information we get and where e come from
  2. Is Everyone on the Same Page?: Make sure wetin users see na wetin dey really happen

Our Game Plan:

Instead to dey run round everywhere, we go create centralized state management system. Think am like one organized person wey dey control everything wey important:

Schema showing the data flows between the HTML, user actions and state

flowchart TD
    A[User Action] --> B[Event Handler]
    B --> C[updateState Function]
    C --> D{State Validation}
    D -->|Valid| E[Create New State]
    D -->|Invalid| F[Error Handling]
    E --> G[Object.freeze]
    G --> H[Update localStorage]
    H --> I[Trigger UI Update]
    I --> J[User Sees Changes]
    F --> K[User Sees Error]
    
    subgraph "State Management Layer"
        C
        E
        G
    end
    
    subgraph "Persistence Layer"
        H
        L[localStorage]
        H -.-> L
    end

Understand dis data flow:

  • Centralize all application state for one place
  • Route all state changes through controlled functions
  • Ensure UI dey synchronized with current state
  • Provide clear, predictable pattern for data management

💡 Professional Insight: Dis lesson na fundamentals. For complex apps, libraries like Redux get more advanced state management features. If you understand core principle dem, you go fit master any state management library.

⚠️ Advanced Topic: We no go talk about automatic UI updates wey dey happen because of state changes, as dis one na Reactive Programming matter. You fit take am as next level for your learning journey!

Task: Centralize State Structure

Make we start to transform our scattered state management into one centralized system. Dis first step go build foundation for all di better things wey dem go follow.

Step 1: Create a Central State Object

Change di simple account declaration for:

let account = null;

To structured state object:

let state = {
  account: null
};

Why dis change matter:

  • Centralize all app data for one place
  • Prepare structure to add more state properties later
  • Create clear boundary between state and other variables
  • Build pattern wey fit grow as your app dey grow

Step 2: Update State Access Patterns

Change your functions to use di new state structure:

For register() and login() functions, change this:

account = ...

To dis one:

state.account = ...

For updateDashboard() function, add dis line for top:

const account = state.account;

Wetin these updates dey do:

  • Maintain existing function but improve structure
  • Prepare your code for advanced state management
  • Create consistent patterns to access state data
  • Build foundation for centralized state updates

💡 Note: Dis refactoring no solve all wahala immediately, but e go build strong foundation for better improvements wey go come!

🎯 Pedagogical Check-in: Centralization Principles

Pause and Reflect: You don just implement foundation for centralized state management. Na important architectural decision be dis.

Quick Self-Assessment:

  • You fit talk why e good to centralize state inside one object, no scatter am for many variables?
  • Wetin go happen if you forget to update function to use state.account?
  • How dis pattern dey prepare your code for more advanced features?

Real-World Connection: Di centralization pattern wey you learn na di foundation for modern frameworks like Redux, Vuex, and React Context. You dey build the same architectural thinking wey big app dem dey use.

Challenge Question: If you want add user preferences (theme, language) for your app, where you go put am for state structure? How e go scale?

Implementing Controlled State Updates

With state already centralized, di next step na to set controlled way for data changes. Dis one go make state changes dey predictable and debugging easy.

Main principle na like air traffic control: no multiple functions dey change state anyhow, but make all changes dey go through one controlled function. Dis pattern dey provide clear oversight of when and how data change.

Immutable State Management:

We go treat our state object as immutable, meaning say we no go dey change am directly. Each time we want change am, we go create new state object with updated data.

Though dis one fit look like e no dey efficient compared to direct change, e get better benefit for debugging, testing, and make app dey predictable.

Benefits of immutable state management:

Benefit Description Impact
Predictability Changes dey happen only through controlled functions Debug and test go easy
History Tracking Each state change get new object Fit do undo/redo functions
Side Effect Prevention No accidental changes Avoid mysterious bugs
Performance Optimization Easy to detect when state really change Fit do efficient UI updates

JavaScript Immutability with Object.freeze():

JavaScript get Object.freeze() wey fit stop object changes:

const immutableState = Object.freeze({ account: userData });
// Any try to change immutableState go throw error

Wetin dey happen here:

  • Stop direct property assignment or deletion
  • Throw error if modification try happen
  • Ensure state changes must enter controlled functions
  • Create clear contract how state go fit update

💡 Deep Dive: Learn difference between shallow and deep immutable objects for MDN documentation. To sabi dis difference na important for complex state structures.

stateDiagram-v2
    [*] --> StateV1: Di fust state
    StateV1 --> StateV2: updateState('account', newData)
    StateV2 --> StateV3: updateState('account', anotherUpdate)
    StateV3 --> StateV4: updateState('preferences', userSettings)
    
    note right of StateV1
        Object.freeze()
        Immutable
        Debuggable
    end note
    
    note right of StateV2
        New object created
        Previous state preserved
        Predictable changes
    end note

Task

Make we create one new updateState() function:

function updateState(property, newData) {
  state = Object.freeze({
    ...state,
    [property]: newData
  });
}

For dis function, we dey create new state object and copy data from old state using spread (...) operator. Then we dey override one particular property of state with new data using bracket notation [property] for assign. Finally, we dey lock the object to prevent change with Object.freeze(). Right now, we only get account property for state, but with dis method, you fit add as many properties as you want.

We also go update state initialization to make sure initial state sef dey frozen:

let state = Object.freeze({
  account: null
});

After that, update register function by replacing state.account = result; with:

updateState('account', result);

Do same thing for login, replace state.account = data; with:

updateState('account', data);

Now, we go take chance fix issue wey account data no dey clear when user click Logout.

Create new function logout():

function logout() {
  updateState('account', null);
  navigate('/login');
}

For updateDashboard(), replace redirection return navigate('/login'); with return logout();

Try register new account, logout, and log back in to check say everything still dey work well.

Tip: You fit see all state changes by putting console.log(state) for bottom of updateState() and open console for your browser development tools.

Implementing Data Persistence

Session loss wahala we identify earlier need persistence solution wey go keep user state across browser sessions. Dis one go turn our app from temporary experience to reliable, professional tool.

Think how atomic clocks dey keep precise time even during power failure by storing important state for non-volatile memory. Likewise, web apps need storage wey fit preserve key user data across browser sessions and page refresh.

Strategic Questions for Data Persistence:

Before you do persistence, reason these main questions:

Question Banking App Context Decision Impact
Is the data sensitive? Account balance, transaction history Choose secure storage methods
How long e go last? Login state vs. temporary UI preferences Choose correct storage duration
Server need am? Authentication tokens vs. UI settings Decide if e go share

Browser Storage Options:

Modern browsers get different storage ways wey dem build for different use:

Primary Storage APIs:

  1. localStorage: Persistent Key/Value storage

    • Data dey stay across browser sessions forever
    • No lost when browser or computer clear or restart
    • Na for that one website domain only
    • Good for user preferences and login states
  2. sessionStorage: Temporary session storage

    • Works the same as localStorage when session dey
    • Clear when browser tab close
    • Perfect for temporary data wey no suppose last
  3. HTTP Cookies: Server-shared storage

    • Send automatically with every server request
    • Good for authentication tokens
    • Small size and fit slow performance

Data Serialization Requirement:

Both localStorage and sessionStorage dey store only strings:

// Change objects to JSON strings make e fit store
const accountData = { user: 'john', balance: 150 };
localStorage.setItem('account', JSON.stringify(accountData));

// Turn JSON strings back to objects wen you dey find am out
const savedAccount = JSON.parse(localStorage.getItem('account'));

How serialization dey work:

  • Converts JavaScript objects to JSON strings with JSON.stringify()
  • Transforms back objects from JSON with JSON.parse()
  • Fit handle complex nested objects and arrays automatically
  • No fit handle functions, undefined values, and circular references

💡 Advanced Option: For complex offline apps with big data, try IndexedDB API. E be full client-side database but e need more complex implementation.

quadrantChart
    title Browser Storage Options
    x-axis Low Complexity --> High Complexity
    y-axis Short Duration --> Long Duration
    
    quadrant-1 Proffesionol Tools
    quadrant-2 Simple Persistence
    quadrant-3 Temporary Storage
    quadrant-4 Advanced Systems
    
    localStorage: [0.3, 0.8]
    sessionStorage: [0.2, 0.2]
    HTTP Cookies: [0.6, 0.7]
    IndexedDB: [0.9, 0.9]
    Memory Variables: [0.1, 0.1]

Task: Build localStorage Persistence

Make we build persistent storage so people no go log out until dem do am purposely. We go use localStorage to store account data across browser sessions.

Step 1: Define Storage Configuration

const storageKey = 'savedAccount';

What dis constant dey do:

  • Create sure identifier for our stored data
  • Help avoid typos for storage key
  • Easy to change storage key if we need
  • Follow good code practice

Step 2: Add Automatic Persistence

Put this line for the end of updateState() function:

localStorage.setItem(storageKey, JSON.stringify(state.account));

Wetin dis line dey do:

  • Change account object to JSON string for storage
  • Save data with our storage key
  • Run anytime state change happen
  • Make sure stored data always correct with state

💡 Architecture Benefit: Because all state update na through updateState(), only one line of code to add persistence. This show how good architecture work!

Step 3: Restore State on App Load

Make initialization function to bring back saved data:

function init() {
  const savedAccount = localStorage.getItem(storageKey);
  if (savedAccount) {
    updateState('account', JSON.parse(savedAccount));
  }

  // Our previous initialization code na di one webin we start wit bifo
  window.onpopstate = () => updateRoute();
  updateRoute();
}

init();

How initialization dey work:

  • Get any saved account data inside localStorage
  • Parse JSON string back to JavaScript object
  • Update state with controlled update function
  • Restore user session automatically on page load
  • Run before route changes to make state ready

Step 4: Optimize Default Route

Update default route to use persistence well:

For updateRoute(), replace:

// Replace: return waka go('/login');
return navigate('/dashboard');

Why this change dey okay:

  • Use new persistence system correctly
  • Let dashboard handle authentication checks
  • Automatically redirect to login if no session saved
  • Create better user experience

Testing Your Implementation:

  1. Login your banking app
  2. Refresh browser page
  3. Confirm say you still dey logged in and dashboard dey show
  4. Close and open your browser again
  5. Go back your app and check say you still dey logged in

🎉 You Don Do Am!: You don build correct persistent state management! Your app dey behave like professional web app now.

🎯 Pedagogical Check-in: Persistence Architecture

Architecture Understanding: You don create strong persistence layer wey balance user experience and data management.

Key Concepts Mastered:

  • JSON Serialization: How to change complex objects to strings wey fit store
  • Automatic Synchronization: State changes trigger storage save
  • Session Recovery: App fit restore user context after interruption
  • Centralized Persistence: One function handle all storage

Industry Connection: This persistence style na core for Progressive Web Apps (PWAs), offline-first apps, and modern mobile web apps. You dey build pro functionality.

Reflection Question: How you go take adjust am to handle many user accounts on one device? Think about privacy and security.

Balancing Persistence with Data Freshness

Our persistence system dey keep user session well, but e bring wahala: data fit stale. When many users or apps change same server data, local cache go old.

Na like Viking sailors wey rely both on stored star charts and current sky observation. The charts give steady info but sailors still need fresh sight to dey correct for changes. Same way, our app need both persistent user state and current server data.

🧪 Discovering Data Freshness Problem:

  1. Login dashboard with test account
  2. Run dis command for terminal to simulate other source transaction:
curl --request POST \
     --header "Content-Type: application/json" \
     --data "{ \"date\": \"2020-07-24\", \"object\": \"Bought book\", \"amount\": -20 }" \
     http://localhost:5000/api/accounts/test/transactions
  1. Refresh your dashboard page for browser
  2. See if new transaction show

Wetin this test show:

  • Show how local storage fit become "stale" (old)
  • Simulate real life wen data change comot for app
  • Show tension between persistence and data freshness

The Data Staleness Challenge:

Problem Cause User Impact
Stale Data localStorage no dey expire automatically Users dey see old info
Server Changes Other users/apps modify same data Views no dey consistent for different platform
Cache vs. Reality Local cache no match server state Bad user experience and confusion

Solution Strategy:

We go do "refresh on load" pattern to balance persistence benefits with fresh data need. This go keep smooth experience and make sure data correct.

sequenceDiagram
    participant U as User
    participant A as App
    participant L as localStorage
    participant S as Server
    
    U->>A: Open app
    A->>L: Load di saved state
    L-->>A: Return cached data
    A->>U: Show UI sharp sharp
    A->>S: Fetch fresh data
    S-->>A: Return current data
    A->>L: Update cache
    A->>U: Update UI wit fresh data

Task: Implement Data Refresh System

We go create system wey go automatically fetch fresh data from server while still keep our persistent state benefits.

Step 1: Create Account Data Updater

async function updateAccountData() {
  const account = state.account;
  if (!account) {
    return logout();
  }

  const data = await getAccount(account.user);
  if (data.error) {
    return logout();
  }

  updateState('account', data);
}

How this function work:

  • Check if user logged in (state.account dey)
  • Redirect to logout if no correct session
  • Fetch fresh account data with existing getAccount() function
  • Handle server errors softly by logging out invalid session
  • Update state with fresh data using our controlled update way
  • Trigger automatic localStorage save through updateState()

Step 2: Create Dashboard Refresh Handler

async function refresh() {
  await updateAccountData();
  updateDashboard();
}

What this refresh function do:

  • Manage data refresh and UI update
  • Wait fresh data before update display
  • Make sure dashboard dey show latest info
  • Keep data management and UI updates separate

Step 3: Integrate with Route System

Change your route config to trigger refresh automatically:

const routes = {
  '/login': { templateId: 'login' },
  '/dashboard': { templateId: 'dashboard', init: refresh }
};

How this integration work:

  • Run refresh function every time dashboard route load
  • Make sure fresh data dey any time user open dashboard
  • Keep old route structure and add data freshness
  • Set solid pattern for route init

Testing Your Data Refresh System:

  1. Login your banking app
  2. Run curl command earlier to add new transaction
  3. Refresh dashboard page or go away come back
  4. Confirm new transaction show sharp sharp

🎉 Perfect Balance! Your app combine smooth persistent state with fresh server data accuracy now!

📈 Your State Management Mastery Timeline

timeline
    title Professional State Management Journey
    
    section Problem Recognition
        State Issues Diagnosis
            : Identify session loss problems
            : Understand scattered update issues
            : Recognize architectural needs
    
    section Architecture Foundation
        Centralized State Design
            : Create unified state objects
            : Implement controlled update patterns
            : Establish immutable principles
        
        Predictable Updates
            : Master Object.freeze() usage
            : Build debug-friendly systems
            : Create scalable patterns
    
    section Persistence Mastery
        localStorage Integration
            : Handle JSON serialization
            : Implement automatic synchronization
            : Create session continuity
        
        Data Freshness Balance
            : Address staleness challenges
            : Build refresh mechanisms
            : Optimize performance vs accuracy
    
    section Professional Patterns
        Production-Ready Systems
            : Implement error handling
            : Create maintainable architectures
            : Follow industry best practices
        
        Advanced Capabilities
            : Ready for framework integration
            : Prepared for complex state needs
            : Foundation for real-time features

🎓 Graduation Milestone: You don strong build complete state management system like Redux, Vuex, and other pro libraries. These patterns fit small app to big enterprise app.

🔄 Next Level Skills:

  • Ready to master Redux, Zustand, Pinia and other state frameworks
  • Prepared to do real-time with WebSockets
  • Ready to build offline-first Progressive Web Apps
  • Steady for advanced patterns like state machines and observers

GitHub Copilot Agent Challenge 🚀

Use Agent mode to solve dis challenge:

Description: Build strong state management system wey get undo/redo for banking app. The challenge go help you practice advanced state ideas like history tracking, immutable updates, and UI sync.

Prompt: Make better state system wey get: 1) state history array to track past states, 2) undo/redo functions to reverse states, 3) UI buttons for undo/redo on dashboard, 4) max history limit of 10 to control memory, 5) clear history on logout. Make undo/redo work with account balance changes and still keep after browser refresh.

More info about agent mode dey this link.

🚀 Challenge: Storage Optimization

Your build dey handle user sessions, data refresh, and state management well. But think if our current method really balance storage use with functionality.

Like chess players wey sabi pick important pieces and leave pawns, good state management go need to sabi which data must persist and which data better to always fresh from server.

Optimization Analysis:

Check your localStorage now and ask yourself:

  • Which minimum info wey suppose hold user authentication?
  • Which data dey change often wey local cache no really help?
  • How storage optimization fit make performance better without spoil user experience?

Dis kind architectural thinking dey separate senior devs wey dey consider functionality and efficiency well.

Implementation Strategy:

  • Find essential data wey must persist (usually just user id)
  • Change localStorage to store only important session data
  • Make sure fresh data fetch from server anytime dashboard open
  • Test say your optimized method still give good user experience

Advanced Consideration:

  • Compare storing full account data vs. only auth tokens
  • Write down your choices and reasons for others later

Dis challenge go train you to think like professional dev wey sabi balance user experience and app efficiency. Take your time try different ways!

Post-Lecture Quiz

Post-lecture quiz

Assignment

Implement "Add transaction" dialog

Here na example result after you finish the assignment:

Screenshot showing an example "Add transaction" dialog


Disclaimer: Dis document na toktok wey AI translation service Co-op Translator help do. Even though we try make am correct, abeg sabi say automatic translation fit get some mistakes or error. Di original document wey dem write for im own language na di real correct one. If na serious matter, make person wey sabi do translation well do am. We no go fit carry any gbege or wahala if pesin no understand well or get wrong meaning from dis translation.