API Reference

Modeling Tools

Constructors for ND Models

Those functions help you to bridge from MTK models to NetworkDynamics.jl Models:

OpPoDyn.BusFunction
Bus(sys::ODESystem; verbose=false, name=getname(sys), kwargs...)

Create a VertexModel from an ODESystem that satisfies the bus model interface.

Arguments

  • sys::ODESystem: The system must satisfy the bus model interface (see isbusmodel)
  • verbose::Bool=false: Enable verbose output during creation
  • name: Name for the bus (defaults to system name)
  • kwargs...: Additional keyword arguments passed to the Bus constructor

Returns


                                          ╔═════════════════════════╗
                                          ║ VertexModel (compiled)  ║
    ┌────────────────────┐      Network   ║  ┌────────────────────┐ ║
    │MTKBus   ┌─────────┐│     interface  ║  │MTKBus   ┌─────────┐│ ║
    │        ┌┤Generator││                ║  │        ┌┤Generator││ ║
    │┌──────┐│└─────────┘│      current ────→│┌──────┐│└─────────┘│ ║
Bus(││BusBar├o           │) =>            ║  ││BusBar├o           │ ║
    │└──────┘│┌────┐     │      voltage ←────│└──────┘│┌────┐     │ ║
    │        └┤Load│     │                ║  │        └┤Load│     │ ║
    │         └────┘     │                ║  │         └────┘     │ ║
    └────────────────────┘                ║  └────────────────────┘ ║
                                          ╚═════════════════════════╝

See also: MTKBus

source
OpPoDyn.LineFunction
Line(sys::ODESystem; verbose=false, name=getname(sys), kwargs...)

Create an EdgeModel from an ODESystem that satisfies the line model interface.

Arguments

  • sys::ODESystem: The system must satisfy the line model interface (see islinemodel)
  • verbose::Bool=false: Enable verbose output during creation
  • name: Name for the line (defaults to system name)
  • kwargs...: Additional keyword arguments passed to the Line constructor

Returns


                                             ╔══════════════════════════════╗
                                             ║ EdgeModel (compiled)         ║
     ┌─────────────────────────────┐     src ║ ┌──────────────────────────┐ ║ dst
     │MTKLine   ┌───────┐          │  vertex ║ │MTKLine   ┌────┐          │ ║ vertex
     │         ┌┤BranchA├┐         │         ║ │         ┌┤    ├┐         │ ║
     │┌───────┐│└───────┘│┌───────┐│     u ───→│┌───────┐│└────┘│┌───────┐│←─── u
Line(││LineEnd├o         o┤LineEnd││) =>     ║ ││LineEnd├o      o┤LineEnd││ ║
     │└───────┘│┌───────┐│└───────┘│     i ←───│└───────┘│┌────┐│└───────┘│───→ i
     │  :src   └┤BranchB├┘  :dst   │         ║ │         └┤    ├┘         │ ║
     │          └───────┘          │         ║ │          └────┘          │ ║
     └─────────────────────────────┘         ║ └──────────────────────────┘ ║
                                             ╚══════════════════════════════╝

See also: MTKLine

source

Basic Component Modeling

OpPoDyn.TerminalConstant
Terminal

A ModelingToolkit connector for electrical terminals in power system components.

Represents an electrical connection point with complex voltage and current in dq coordinates. The terminal defines the interface between power system components like buses, lines, and machines.

Variables

  • u_r(t): d-axis voltage component
  • u_i(t): q-axis voltage component
  • i_r(t): d-axis current component (flow variable)
  • i_i(t): q-axis current component (flow variable)

Notes

Current variables are defined as flow variables, meaning they sum to zero at connection points according to Kirchhoff's current law.

See also: BusBar, LineEnd

source
OpPoDyn.BusBarConstant
@named busbar = BusBar()

A ModelingToolkit model representing the physical connection point within a bus in power systems. It represents the physical busbar where all injectors and lines attach.

Within OpPoDyn.jl, it serves as an interface between the MTK world and the NetworkDynamics world: A MTK model containing a BusBar the highest level is consdered a busmodel (see isbusmodel) and describes the dynamics of an entire bus. It can be transformed in a VertexModel by calling Bus.

See also: Terminal, MTKBus, Bus

source
OpPoDyn.LineEndConstant
LineEnd

A ModelingToolkit model representing one end of a transmission line in power systems. It represents the physical connection point at the end of a transmission line.

Within OpPoDyn.jl, it serves as an interface between the MTK world and the NetworkDynamics world: A MTK model containing two LineEnds (named :src and :dst) at the highest level is considered a linemodel (see islinemodel) and describes the dynamics of an entire line. It can be transformed in an EdgeModel by calling Line.

See also: Terminal, MTKLine, Line

source
OpPoDyn.MTKBusFunction
MTKBus(injectors...; name=:bus)

Create a ModelingToolkit bus system by connecting multiple injector components.

Constructs a bus ODESystem by connecting all provided injector components to a central BusBar. Each injector component must satisfy the injector model interface (see isinjectormodel).

Arguments

  • injectors...: Variable number of injector components (generators, loads, etc.)
  • name=:bus: Name for the resulting bus system

Returns

  • An ODESystem representing the complete bus with all connected injectors
                                 ┌────────────────────┐
                                 │MTKBus   ┌─────────┐│
                                 │        ┌┤Generator││
        ┌─────────┐   ┌────┐     │┌──────┐│└─────────┘│
MTKBus(o┤Generator│, o┤Load│) => ││BusBar├o           │
        └─────────┘   └────┘     │└──────┘│┌────┐     │
                                 │        └┤Load│     │
                                 │         └────┘     │
                                 └────────────────────┘

See also: Bus, BusBar, isinjectormodel

source
OpPoDyn.MTKLineFunction
MTKLine(branches...; name=:line)

Create a ModelingToolkit line system by connecting multiple branch components.

Constructs a line ODESystem by connecting all provided branch components between source and destination line ends in parallel. Each branch component must satisfy the branch model interface.

Arguments

  • branches...: Variable number of branch components (transmission lines, transformers, etc.)
  • name=:line: Name for the resulting line system

Returns

  • An ODESystem representing the complete line with all connected branches
                                     ┌─────────────────────────────┐
                                     │MTKLine   ┌───────┐          │
                                     │         ┌┤BranchA├┐         │
         ┌───────┐    ┌───────┐      │┌───────┐│└───────┘│┌───────┐│
MTKLine(o┤BranchA├o, o┤BranchB├o) => ││LineEnd├o         o┤LineEnd││
         └───────┘    └───────┘      │└───────┘│┌───────┐│└───────┘│
                                     │  :src   └┤BranchB├┘  :dst   │
                                     │          └───────┘          │
                                     └─────────────────────────────┘

See also: Line, LineEnd, isbranchmodel

source
OpPoDyn.CompositeInjectorFunction
CompositeInjector(systems, eqs=autoconnections(systems); name=Symbol(join(getname.(systems), "_")))

Create an injector object which contains several subsystems. Every subsystem which has a terminal will be connected to a newly created terminal of the composite injector. The subsystems are namespaced within the composite injector.

There are two options for additional connections between the subsystems:

  • interconnections will be created automatically using some name-matching heuristics using autoconnections(systems): It searches all Blocks.RealOutput and Blocks.RealInput, and tries to find a single matching output for each input.
  • alternatively pass connecting equations of the form [connect(sys1.output, sys2.input)] explicitly

For example, one could create a composite injector with three subsystems:

  • a generator,
  • a controller, and
  • a load;

which is augmented with 2 connection equations

  • one for the measurements (generator -> controller), and
  • one for the actuation (controller -> generator).

The returned model contains a new terminal :terminal at the toplevel, thus satisfying the injector interface, see isinjectormodel). It can be used as such in the MTKBus constructor.

    ┌────────────────────────────────────┐
    │ CompositeInjector                  │
    │              ╭───→───╮ measurements│
    │    ┌─────────┴─┐   ┌─┴──────────┐  │
(t) │  o─┤ Generator │   │ Controller │  │
 o──┼──┤ └─────────┬─┘   └─┬──────────┘  │
    │  │           ╰───←───╯ actuation   │
    │  │ ┌──────┐                        │
    │  o─┤ Load │                        │
    │    └──────┘                        │
    └────────────────────────────────────┘
source

Helpers

OpPoDyn.isbusmodelFunction
isbusmodel(sys::ODESystem)

Check if an ODESystem satisfies the bus model interface.

A bus model must contain a component named :busbar that satisfies the busbar interface. Bus models represent the complete dynamics of a power system bus and can be transformed into a VertexModel using Bus.

┌───────────────────────────┐
│BusModel     ┌────────────┐│
│           ┌─┤ Injector 1 ││
│┌────────┐ │ └────────────┘│
││ BusBar ├─o               │
│└────────┘ │               │
│ :busbar   └ ...           │
│                           │
└───────────────────────────┘

Note: The BusModel musst contain exaclty one BusBar, the rest of the structure is free. For example, you could also put a Brach between an injector and a Busbar or have multiple injectors and controllers connected.

See also: Bus, BusBar, MTKBus

source
OpPoDyn.isinjectormodelFunction
isinjectormodel(sys::ODESystem)

Check if an ODESystem satisfies the injector model interface.

An injector model must contain a Terminal named :terminal. Injector models represent components like generators, loads, and other devices that connect to a single bus. They can have arbitrary internal complexity as long as they have exactly one terminal.

   (t)    ┌──────────┐
    o─────┤ Injector │
:terminal └──────────┘

See also: Terminal

source
OpPoDyn.islinemodelFunction
islinemodel(sys::ODESystem)

Check if an ODESystem satisfies the line model interface.

A line model must contain two components named :src and :dst that both satisfy the line end interface. Line models represent transmission lines and can be transformed into an EdgeModel using Line.

┌──────────────────────────────────────┐
│LineModel     ┌────────┐              │
│            ┌─┤ Branch ├─┐            │
│┌─────────┐ │ └────────┘ │ ┌─────────┐│
││ LineEnd ├─o            o─┤ LineEnd ││
│└─────────┘ │            │ └─────────┘│
│   :src     └    ....    ┘    :dst    │
│                                      │
└──────────────────────────────────────┘

Note: Between the LineEnds there can be arbeitrary structures, for example branches in series or parallel.

See also: Line, LineEnd, MTKBus

source
OpPoDyn.isbranchmodelFunction
isbranchmodel(sys::ODESystem)

Check if an ODESystem satisfies the branch model interface.

A branch model must contain two Terminal components named :src and :dst. Branch models represent two-port network elements like transmission lines, transformers, and other connecting devices.

 (t) ┌────────┐ (t)
  o──┤ Branch ├──o
:src └────────┘ :dst

See also: Terminal

source

Powerflow Tools

Powerflow Components

OpPoDyn.pfSlackFunction
pfSlack(; V=missing, δ=missing, u_r=missing, u_i=missing)

Create a slack bus for power flow analysis.

A slack bus maintains constant voltage magnitude and phase angle (or real and imaginary voltage components). Either provide voltage magnitude V and phase angle δ, or provide real and imaginary voltage components u_r and u_i.

source
OpPoDyn.pfPVFunction
pfPV(; P, V)

Create a PV bus for power flow analysis.

A PV bus maintains constant active power injection and voltage magnitude. The reactive power and voltage phase angle are determined by the power flow solution.

source
OpPoDyn.pfPQFunction
pfPQ(; P=0, Q=0)

Create a PQ bus for power flow analysis.

A PQ bus has specified active and reactive power injections. The voltage magnitude and phase angle are determined by the power flow solution.

source

Powerflow Helpers

OpPoDyn.solve_powerflowFunction
solve_powerflow(nw::Network;
                pfnw = powerflow_model(nw),
                pfs0 = NWState(nw),
                verbose=true)

Solve the power flow equations for a given network.

Uses find_fixpoint from NetworkDynamics to solve the algebraic power flow equations.

Parameters

  • nw: The dynamic network model
  • pfnw: The power flow network model (default: created from nw)
  • pfs0: Initial state for the power flow calculation
  • verbose: Whether to print the power flow solution

Returns

  • A NWState containing the solved power flow solution

See also initialize_from_pf.

source
OpPoDyn.initialize_from_pfFunction
initialize_from_pf[!](
    nw::Network;
    verbose = true,
    subverbose = false,
    pfnw = powerflow_model(nw),
    pfs0 = NWState(pfnw),
    pfs = solve_powerflow(pfnw; pfs0, verbose),
    kwargs...
)

Initialize a dynamic network model from a power flow solution.

This function performs a two-step initialization process:

  1. Solve the power flow equations for the network
  2. Use the power flow solution to initialize the dynamic model

There are two versions of this function: a mutating one (!-at the end of name) and a non-mutating version. The mutating version uses initialize_componentwise! internally, the non-mutating one initialize_componentwise. When the mutating version is used, NWState(nw) after initialization will return the same initialized state again, as it is stored in the metadata.

Parameters

  • nw: The dynamic network model to initialize
  • verbose: Whether to print information about the power flow solution (default: true)
  • subverbose: Whether to print detailed information during component initialization (default: false). Can be Vector [VIndex(1), EIndex(3), ...] for selective output
  • pfnw: Power flow network model (default: created from nw using powerflow_model)
  • pfs0: Initial state for power flow calculation (default: created from pfnw)
  • pfs: Power flow solution (default: calculated using solve_powerflow)
  • Additional keyword arguments are passed to initialize_componentwise[!]

Returns

  • A fully initialized network state

See also: solve_powerflow, initialize_componentwise, interface_values

source
OpPoDyn.show_powerflowFunction
show_powerflow(s::NWState/Network)

Display power flow results in a tabular format.

Extract and format power flow solution data from a network state, showing bus-level information including voltage magnitudes, phase angles, active power, and reactive power.

source
OpPoDyn.powerflow_modelFunction
powerflow_model(cf::NetworkDynamics.ComponentModel)

Extract or create a power flow component model from a dynamic component model.

  1. If the component has :pfmodel metadata, use that model (after validation)
  2. If the component is already a valid power flow model (i.e. no ODE, just constraints), return it as-is

Returns

  • A component model suitable for power flow analysis (no dynamics)

Validation

The returned model must satisfy ispfmodel criteria:

  • Either no states or zero mass matrix (no dynamics)

See also: ispfmodel, pfSlack, pfPV, pfPQ

source
powerflow_model(nw::Network)

Create a power flow network model from a dynamic network model.

This method applies powerflow_model to all vertex and edge components in the network, creating a new network suitable for steady-state power flow analysis.

Returns a new Network with the same graph structure but power flow component models

See also: solve_powerflow

source
OpPoDyn.ispfmodelFunction
ispfmodel(cf::NetworkDynamics.ComponentModel)

Check if a component model is suitable for power flow analysis.

A component model is considered a valid power flow model if it has no dynamics, i.e., either no states or a zero mass matrix.

Returns

  • true if the component is suitable for power flow analysis
  • false otherwise
source

Initialization

Powerflow dependent constraints and formulas

OpPoDyn.PFInitConstraintType
struct PFInitConstraint{F}
PFInitConstraint(f, sym, pfsym, dim)

A representation of an additional constraint that is applied during the initialization phase of a component. In contrast to a InitConstraint, this constraint may access additional variables which are available in the full NWState of the solved power flow!

Crucially, this is only necessary for constraints, which cannot be expressed in terms of the interface variables (voltages and currents).

See also: @pfinitconstraint for a macro to create such constraints, PFInitConstraint, set_pfinitconstraint!, add_pfinitconstraint!

source
OpPoDyn.PFInitFormulaType
struct PFInitFormula{F}
PFInitFormula(f, outsym, sym, pfsym)

A representation of an initialization formula that is applied during the initialization phase of a component. In contrast to a InitFormula, this formula may access additional variables which are available in the full NWState of the solved power flow!

Crucially, this is only necessary for formulas, which cannot be expressed in terms of the interface variables (voltages and currents).

Similar to InitFormula, this sets defaults rather than adding constraint equations. The formula is applied early in the initialization pipeline before constraints are solved.

See also: @pfinitformula for a macro to create such formulas, PFInitFormula, set_pfinitformula!, add_pfinitformula!

source
OpPoDyn.@pfinitformulaMacro
@pfinitformula expr
@pfinitformula begin
    :var1 = expr1
    :var2 = expr2
end

Create a PFInitFormula using macro syntax. Component variables are accessed with :symbol and power flow state variables with @pf :symbol. Multiple formulas can be defined in a begin...end block.

Unlike constraints, formulas use assignment syntax (:var = expression) to set variable values during initialization. The left-hand side specifies output variables, and the right-hand side can access both component variables and power flow state variables.

See also: PFInitFormula, set_pfinitformula!, add_pfinitformula!

source

Metadata Accesors

OpPoDyn.add_pfinitformula!Function
add_pfinitformula!(c::NetworkDynamics.ComponentModel, formula::PFInitFormula) -> Bool
add_pfinitformula!(nw::Network, idx::Union{VIndex,EIndex}, formula) -> Bool

Adds a new initialization formula which depends on the powerflow solution to the component. If formulas already exist, the new formula is added to the existing ones. If no formulas exist, this is equivalent to set_pfinitformula!.

Returns true if the formula was successfully added, false if it already exists.

See also set_pfinitformula!, delete_pfinitformulas!.

source
OpPoDyn.set_pfinitformula!Function
set_pfinitformula!(c::NetworkDynamics.ComponentModel, formula; check=true)
set_pfinitformula!(nw::Network, idx::Union{VIndex,EIndex}, formula; check=true)

Sets initialization formulas which depend on the powerflow solution to the component. Accepts either a single PFInitFormula or a tuple of PFInitFormula objects. Overwrites any existing pf formulas. See also delete_pfinitformulas!, add_pfinitformula!.

source
OpPoDyn.get_pfinitformulasFunction
get_pfinitformulas(c::NetworkDynamics.ComponentModel)
get_pfinitformulas(nw::Network, idx::Union{VIndex,EIndex})

Retrieves the initialization formulas which depend on pf state for the component model. Returns a tuple of formulas, even if only one formula is present. May error if no formulas are present. Use has_pfinitformula to check first.

See also: has_pfinitformula, set_pfinitformula!.

source
OpPoDyn.delete_pfinitformulas!Function
delete_pfinitformulas!(c::NetworkDynamics.ComponentModel)
delete_pfinitformulas!(nw::Network, idx::Union{VIndex,EIndex})

Removes the powerflow dependent initialization formula from the component model, or from a component referenced by idx in a network. Returns true if the formula existed and was removed, false otherwise.

See also: set_pfinitformula!.

source
OpPoDyn.add_pfinitconstraint!Function
add_pfinitconstraint!(c::NetworkDynamics.ComponentModel, constraint::PFInitConstraint) -> Bool
add_pfinitconstraint!(nw::Network, idx::Union{VIndex,EIndex}, constraint) -> Bool

Adds a new initialization constraint which depends on the powerflow solution to the component. If constraints already exist, the new constraint is added to the existing ones. If no constraints exist, this is equivalent to set_pfinitconstraint!.

Returns true if the constraint was successfully added, false if it already exists.

See also set_pfinitconstraint!, delete_pfinitconstraints!.

source
OpPoDyn.set_pfinitconstraint!Function
set_pfinitconstraint!(c::NetworkDynamics.ComponentModel, constraint; check=true)
set_pfinitconstraint!(nw::Network, idx::Union{VIndex,EIndex}, constraint; check=true)

Sets initialization constraints which depend on the powerflow solution to the component. Accepts either a single PFInitConstraint or a tuple of PFInitConstraint objects. Overwrites any existing pf constraints. See also delete_pfinitconstraints!, add_pfinitconstraint!.

source
OpPoDyn.get_pfinitconstraintsFunction
get_pfinitconstraints(c::NetworkDynamics.ComponentModel)
get_pfinitconstraints(nw::Network, idx::Union{VIndex,EIndex})

Retrieves the initialization constraints which depend on pf state for the component model. Returns a tuple of constraints, even if only one constraint is present. May error if no constraints are present. Use has_pfinitconstraint to check first.

See also: has_pfinitconstraint, set_pfinitconstraint!.

source
OpPoDyn.delete_pfinitconstraints!Function
delete_pfinitconstraints!(c::NetworkDynamics.ComponentModel)
delete_pfinitconstraints!(nw::Network, idx::Union{VIndex,EIndex})

Removes the powerflow dependent initialization constraint from the component model, or from a component referenced by idx in a network. Returns true if the constraint existed and was removed, false otherwise.

See also: set_pfinitconstraint!.

source