liveBook · Manning

Data source

As explained in Pro Angular 16

A data source is a component that supplies application data independently of where that data originates.

A data source supplies application data without requiring the rest of the application to know where that data originates. It may initially return in-memory products and later obtain them through HTTP. Keeping that choice behind a data source makes the change easier to manage. section 5.3.2 section 9.6.1

A typical model separates three jobs: a descriptive class defines a product, a data source loads or saves data, and a repository gives application features access to it. The repository mediates access so components do not need to handle the details of obtaining data. section 9.6.1 section 5.3.3

Listing 9.20. The contents of the datasource.model.ts file in the src/app folder
import { Product } from "./product.model";
 
export class SimpleDataSource {
    private data: Product[];
 
    constructor() {
        this.data = new Array<Product>(
            new Product(1, "Kayak", "Watersports", 275),
            new Product(2, "Lifejacket", "Watersports", 48.95),
            new Product(3, "Soccer Ball", "Soccer", 19.50),
            new Product(4, "Corner Flags", "Soccer", 34.95),
            new Product(5, "Thinking Cap", "Chess", 16));
    }
 
    getData(): Product[] {
        return this.data;
    }
}

This in-memory implementation stores Product objects and returns them through getData(). It is enough to develop against before adding server requests. section 9.6.1

The repository can read those products, find one by ID, and expose operations for changing the model. In a signal-based version, a static data source exposes Signal<Product[]>; the repository reads it by calling products() and derives a category list with computed(). That derived list is recalculated when the product signal changes. section 5.3.3 section 9.6.1

Listing 5.13. The contents of the product.repository.ts file in the src/app/model folder
import { Injectable, Signal, computed } from "@angular/core";
import { Product } from "./product.model";
import { StaticDataSource } from "./static.datasource";
 
@Injectable()
export class ProductRepository {
    products: Signal<Product[]>;
    categories: Signal<string[]>;
 
    constructor(private dataSource: StaticDataSource) {
        this.products = dataSource.products;
        this.categories = computed(() => {
            return this.dataSource.products()
                .map(p => p.category ?? "(None)")
                .filter((c, index, array) => 
                    array.indexOf(c) == index).sort();
        })
    }
 
    getProduct(id: number): Product | undefined {
        return this.dataSource.products().find(p => p.id == id);
    }
}

The repository receives StaticDataSource through its constructor, exposes its product signal, and derives categories without making components depend directly on the source. section 5.3.3

For server-backed data, register RestDataSource and HttpClientModule, then update repositories to use the new source. HTTP results arrive as observables; toSignal converts a product observable to the signal expected by the repository, with an empty array as its initial value. Order saving can delegate to the REST source and retain an observable result. This swap changes model-layer wiring rather than requiring the rest of the application to know the data’s origin. section 6.6.1 section 23.3.2

Do not confuse the model’s data-source service with the “data source” in *ngFor syntax*. In `*ngFor="let item of products()"`, the term means the collection being enumerated to produce template rows, not the service that loaded the products. section 12.2.3

How Pro Angular 16 covers it

How deep it goes
Works through in-memory and REST-backed implementations, repository wiring, provider configuration, and observable-to-signal conversion; defers fuller signal interoperability detail.
Examples
Uses in-memory product arrays, derived product categories, and a REST switch that fetches products and saves checkout orders.
What it assumes
Introduces the model’s descriptive-class, data-source, and repository roles; gives brief signal and dependency-injection explanations before using them.
What you can do after
Build it from scratch with an in-memory source, then configure repositories and providers to use a REST-backed source.
How it connects
Connects data models and repositories with dependency injection, signals, computed signals, HttpClient, observables, and RESTful web services.

Also explained in

Compare how 13 books explain data source →

Related concepts

This explainer was generated by Manning's knowledge graph from the text of Pro Angular 16. The section links point to the parts of the book it draws on.