powsybl / powsybl-core

A framework to build power system oriented software
https://www.powsybl.org
Mozilla Public License 2.0
126 stars 41 forks source link

Security analysis with remedial actions #2015

Open flo-dup opened 2 years ago

flo-dup commented 2 years ago
flo-dup commented 2 years ago

What do we call a remedial action? We could see it as a Scenario or RemedialScenario object containing

(note that each networkModification can itself be a list of modifications through NetworkModificationList)

flo-dup commented 2 years ago

We need to map a list of remedial actions to any LimitViolation encountered. A way to do that would be to have a ScenarioProvider single extra argument in SecurityAnalysis::run. The two following methods are then needed for that provider:

List<Scenario> getPreContingencyScenarios(LimitViolation limitViolation);
List<Scenario> getPostContingencyScenarios(LimitViolation limitViolation, Contingency contingency);
sylvlecl commented 2 years ago

Entry point Indeed we should add an argument to the run method of security analysis providers, something like:

interface SecurityAnalysisProvider {
    CompletableFuture<SecurityAnalysisReport> run(...., List<Scenario> scenarios);
}

Modelling principles

Since one of the primary goal will be to be able to translate all the logic to an external tool, and to exchange that logic between applications, we cannot rely on a java interface such as the ScenarioProvider, we really need to have basic models (POJOs) that we can convert to another data model or format.

So a basic model of scenarios could be:

class Scenario {
    String id;  // is it needed, in addition to the contingency ? we could have different scenarios for 1 contingency
    Contingency contingency;
    Action action;  // Do we need a list here or do we consider a list of actions
                // must be formulated as an aggregated action?
}

class Action {  // Not an interface, it's really a base class for our action models
    String id;
    NetworkModification toNetworkModification();  // Not obvious it should be here:
            // could be used by a java implementation, but could also be outside of that class
}

class OpenSwitchAction { // An exemple of actual action
    String switchId;
}

It already raises some questions:

Condition modelling

Since we want remedial actions to be applied only under certain circumstances, we not only need to have action models, but also models for the condition that will trigger or not the implementation of the action. Here again, we need data objects, not an interface.

The condition modelling from powsybl-action-dsl, based on an expression tree, could almost be re-used as is.

However, we may need to replace the Network***Node in particular the method nodes, which are aimed towards use with reflection.

A condition would be part of a scenario:

class Scenario {
    String id;  // is it needed, in addition to the contingency ? we could have different scenarios for 1 contingency
    Contingency contingency;
    Condition condition;  // under which circumstances do I want to trigger my action
    Action action;  // Do we need a list here or do we consider a list of actions
                // must be formulated as an aggregated action?
}

Serialization

All the models described above must be serializable to/from a versioned JSON format, like contingencies already are.

Extensibility

Do we want third-party users to be able to extend the model with their own types of actions and conditions ? If so, we probably just need to take care to have an entry-point to define JSON serialization for those additional classes.

It may take the form of services that would define additional jackson modules.

sylvlecl commented 2 years ago

So we have agreed on the following things, mainly going into the simplification direction:

Below are draft models following those principles.

Scenario model

In the end, we would have the following scenario model:

class Scenario {
    String id;
    String contingencyId;
    Condition condition;  // under which circumstances do I want to trigger my action
    String actionId;
}

Action model We could start with:

class Action {  // Not an interface, it's really a base class for our action models
    String id;
}

class SwitchAction extends Action {
    String switchId;
    boolean open;
}

class ActionList extends Action {
    List<Action> actions;
}

Conditions model

For now we will only have very simple conditions:

class Condition {
    String getType();  // if needed, or maybe an enum ?
}

class TrueCondition extends Condition {
// always simulate the associated action
}

class AnyViolationCondition extends Condition {
// simulate the associated action as soon there is any violation
}

class ViolationCondition extends Condition {
    // simulate the associated action if there is a violation on any of those network elements
    List<String> subjectIds; 
}

Simulation function

The run method will thus receive 2 additional arguments:

interface SecurityAnalysisProvider {
    CompletableFuture<SecurityAnalysisReport> run(...., List<Action> actions, List<Scenario> scenarios);
}

Result

The result will contain a new list of result for scenarios:

class SecurityAnalysisResult {
    ....
    List<ScenarioResult> getScenariosResults();
    ScenarioResult getScenarioResult(String scenarioId);
}

class ScenarioResult {
    // Same fields as post contingency result but:
    Scenario scenario; // instead of contingency
}
Hadrien-Godard commented 2 years ago

Hello everyone,

Some of us are very interested by this issue and want to add some thoughts about it.

Regarding the actions, it could be useful to have various action types such as redispatching of generation/load, PST tap position switch and HVDC set point switch. It implies that actions are very different from one another, and not limited to topological actions. Of course it is compatible with the current proposed framework with something like:

class GenerationRedispatchingAction extends Action { Map<String, double> generationSwitchById; }

For the conditions model, it could be useful if some conditions are linked to violations and also to the specific status of some network elements. For example the load through a line is above a given threshold. Maybe something like that could extend proposed model:

class LineThresholdViolationCondition extends ViolationCondition{ // simulate the associated action if there is a violation on any of those network elements and if another set of conditions is satisfied List<String> subjectIds; Map<String, double> thresholdById; }

To conclude, it could be useful to have a solution that does not imply that actions have to be switches opening/closure and that conditions have to be line outages.

Hadrien