flow

Execution flow of a composed app

!!! abstract “”

How data flows through a composed pipeline, step by step.

Consider two apps composed into a pipeline:

```python { notest } from scinexus import define_app

@define_app(app_type=“loader”) def read_json(path: str) -> dict: import json

with open(path) as f:
    return json.load(f)

@define_app def validate(data: dict, required_field: str) -> dict: if required_field not in data: raise ValueError(f”missing {required_field!r} field”) return data

app = read_json() + validate(required_field=“name”)


Composing with `+` creates a new app where `validate` is the outermost app and `read_json` is stored as its `.input` attribute. When you call `app(filepath)`, execution begins at the outermost app and works inward.

## The execution flow when you call `app(filepath)`

```mermaid
flowchart TD
    entry["Executes scinexus __call__(val)"] --> none{val is None?}
    none -- yes --> nc_none[create and return NotCompleted ERROR, recording current app as origin]
    none -- no --> nc{val is NotCompleted?}
    nc -- yes --> nc_return[returns same NotCompleted]
    nc -- no --> has_input{has an input app?}
    has_input -- yes --> call_input["call input(val), which enters the top of this chart"]
    call_input --> input_nc{result is NotCompleted?}
    input_nc -- yes --> nc_input[return same NotCompleted]
    input_nc -- no --> type_check
    has_input -- no --> type_check{val type is valid for self}
    type_check -- fail --> nc_type[create and return NotCompleted ERROR]
    type_check -- pass --> main["main(val)"]
    main -- exception --> nc_main[NotCompleted ERROR]
    main -- success --> result["return result (which may be NotCompleted FAIL)"]

    classDef errorNode fill:#fde0c8,stroke:#333
    classDef successNode fill:#c8e0fd,stroke:#333
    class nc_none,nc_return,nc_input,nc_type,nc_main errorNode
    class result successNode

This is the same sequence for every composed app, regardless of pipeline length. Each app in the chain runs the same __call__ checks, so NotCompleted propagation and exception handling are consistent throughout. See Runtime type checking for details on how type validation works and how to disable it.