From 334ab50e31065389b3d1049d2fef4d98d0ab97cf Mon Sep 17 00:00:00 2001 From: Pauline Jean-Marie Date: Mon, 27 Nov 2023 18:10:27 +0100 Subject: [PATCH] WIP: Replace the 3 OperationalLimits Current, ApparentPower and ActivePower by a Group of OperationalLimits in a set of Group indexed by and Id and with a default Group which will act as the 3 OperationalLimits in a retro compatible way Signed-off-by: Pauline Jean-Marie --- .../java/com/powsybl/iidm/network/Branch.java | 39 ++++- .../iidm/network/FlowsLimitsHolder.java | 17 +- .../iidm/network/OperationalLimits.java | 5 +- .../iidm/network/OperationalLimitsGroup.java | 33 ++++ .../impl/AbstractConnectableBranch.java | 92 +++++++--- .../network/impl/AbstractLoadingLimits.java | 11 +- .../impl/AbstractLoadingLimitsAdder.java | 31 ++-- .../impl/AbstractOperationalLimits.java | 10 +- .../impl/ActivePowerLimitsAdderImpl.java | 14 +- .../ActivePowerLimitsAndGroupAdderImpl.java | 41 +++++ .../network/impl/ActivePowerLimitsImpl.java | 9 +- .../impl/ApparentPowerLimitsAdderImpl.java | 15 +- .../ApparentPowerLimitsAndGroupAdderImpl.java | 41 +++++ .../network/impl/ApparentPowerLimitsImpl.java | 9 +- .../network/impl/CurrentLimitsAdderImpl.java | 19 ++- .../impl/CurrentLimitsAndGroupAdderImpl.java | 42 +++++ .../iidm/network/impl/CurrentLimitsImpl.java | 10 +- .../iidm/network/impl/DanglingLineImpl.java | 58 ++++--- .../impl/OperationalLimitsGroupImpl.java | 101 +++++++++++ .../network/impl/OperationalLimitsGroups.java | 39 +++++ .../impl/OperationalLimitsGroupsImpl.java | 160 ++++++++++++++++++ .../impl/OperationalLimitsHolderImpl.java | 78 --------- .../network/impl/OperationalLimitsOwner.java | 21 --- .../impl/ThreeWindingsTransformerImpl.java | 40 +++-- .../iidm/network/impl/TieLineImpl.java | 69 ++++++-- .../iidm/serde/ConnectableSerDeUtil.java | 14 -- .../tck/AbstractCurrentLimitsTest.java | 108 +++++++++++- .../AbstractThreeWindingsTransformerTest.java | 1 - .../matpower/converter/MatpowerExporter.java | 25 +++ 29 files changed, 894 insertions(+), 258 deletions(-) create mode 100644 iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimitsGroup.java create mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAndGroupAdderImpl.java create mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAndGroupAdderImpl.java create mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAndGroupAdderImpl.java create mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupImpl.java create mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroups.java create mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupsImpl.java delete mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsHolderImpl.java delete mode 100644 iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsOwner.java diff --git a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/Branch.java b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/Branch.java index a83debcc491..6431f58b272 100644 --- a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/Branch.java +++ b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/Branch.java @@ -8,6 +8,7 @@ import java.util.Collection; import java.util.Collections; +import java.util.List; import java.util.Optional; /** @@ -116,11 +117,15 @@ public interface Branch> extends Identifiable { TwoSides getSide(Terminal terminal); - default Collection getOperationalLimits1() { - return getCurrentLimits1() - .map(l -> Collections.singletonList((OperationalLimits) l)) - .orElseGet(Collections::emptyList); - } + List getOperationalLimitsGroups1(); + + Optional getOperationalLimitsGroup1(String id); + + Optional getDefaultOperationalLimitsGroup1(); + + OperationalLimitsGroup newOperationalLimitsGroup1(String id); + + void setDefaultOperationalLimitsGroup1To(String id); Optional getCurrentLimits1(); @@ -140,6 +145,16 @@ default Collection getOperationalLimits1() { ApparentPowerLimitsAdder newApparentPowerLimits1(); + List getOperationalLimitsGroups2(); + + Optional getOperationalLimitsGroup2(String id); + + Optional getDefaultOperationalLimitsGroup2(); + + OperationalLimitsGroup newOperationalLimitsGroup2(String id); + + void setDefaultOperationalLimitsGroup2To(String id); + default Collection getOperationalLimits2() { return getCurrentLimits2() .map(l -> Collections.singletonList((OperationalLimits) l)) @@ -256,6 +271,20 @@ default LoadingLimits getNullableLimits(LimitType type, TwoSides side) { } } + default List getOperationalLimitsGroups(TwoSides side) { + return switch (side) { + case ONE -> this.getOperationalLimitsGroups1(); + case TWO -> this.getOperationalLimitsGroups2(); + }; + } + + default Optional getDefaultOperationalLimitsGroup(TwoSides side) { + return switch (side) { + case ONE -> this.getDefaultOperationalLimitsGroup1(); + case TWO -> this.getDefaultOperationalLimitsGroup2(); + }; + } + /** * Only checks overloading for LimitType.Current and permanent limits */ diff --git a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/FlowsLimitsHolder.java b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/FlowsLimitsHolder.java index 86d5b57259b..cc9cc9d7fd7 100644 --- a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/FlowsLimitsHolder.java +++ b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/FlowsLimitsHolder.java @@ -6,8 +6,7 @@ */ package com.powsybl.iidm.network; -import java.util.Collection; -import java.util.Collections; +import java.util.List; import java.util.Optional; /** @@ -15,11 +14,15 @@ */ public interface FlowsLimitsHolder { - default Collection getOperationalLimits() { - return getCurrentLimits() - .map(l -> Collections.singletonList((OperationalLimits) l)) - .orElseGet(Collections::emptyList); - } + List getOperationalLimitsGroups(); + + Optional getOperationalLimitsGroup(String id); + + Optional getDefaultOperationalLimitsGroup(); + + OperationalLimitsGroup newOperationalLimitsGroup(String id); + + void setDefaultOperationalLimitsGroupTo(String id); Optional getCurrentLimits(); diff --git a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimits.java b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimits.java index e1ec3259693..27fe3040a51 100644 --- a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimits.java +++ b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimits.java @@ -11,12 +11,11 @@ * @author Thibaut Vermeulen {@literal } */ public interface OperationalLimits { + /** * Get the operational limits' type (can be APPARENT_POWER, CURRENT or VOLTAGE) */ LimitType getLimitType(); - default void remove() { - // do nothing - } + void remove(); } diff --git a/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimitsGroup.java b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimitsGroup.java new file mode 100644 index 00000000000..42fc51d8ec8 --- /dev/null +++ b/iidm/iidm-api/src/main/java/com/powsybl/iidm/network/OperationalLimitsGroup.java @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2023, RTE (http://www.rte-france.com/) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * SPDX-License-Identifier: MPL-2.0 + */ + +package com.powsybl.iidm.network; +import java.util.Optional; + +public interface OperationalLimitsGroup { + + String getId(); + + Optional getCurrentLimits(); + + Optional getActivePowerLimits(); + + Optional getApparentPowerLimits(); + + CurrentLimitsAdder newCurrentLimits(); + + ActivePowerLimitsAdder newActivePowerLimits(); + + ApparentPowerLimitsAdder newApparentPowerLimits(); + + void removeCurrentLimits(); + + void removeActivePowerLimits(); + + void removeApparentPowerLimits(); +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractConnectableBranch.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractConnectableBranch.java index c8cfd4729bd..95f94f6293d 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractConnectableBranch.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractConnectableBranch.java @@ -10,7 +10,7 @@ import com.powsybl.iidm.network.impl.util.Ref; import com.powsybl.iidm.network.util.LimitViolationUtils; -import java.util.Collection; +import java.util.List; import java.util.Optional; /** @@ -18,14 +18,14 @@ */ abstract class AbstractConnectableBranch & Connectable> extends AbstractConnectable implements Branch { - protected final OperationalLimitsHolderImpl operationalLimitsHolder1; + protected final OperationalLimitsGroupsImpl operationalLimitsHolder1; - protected final OperationalLimitsHolderImpl operationalLimitsHolder2; + protected final OperationalLimitsGroupsImpl operationalLimitsHolder2; AbstractConnectableBranch(Ref network, String id, String name, boolean fictitious) { super(network, id, name, fictitious); - operationalLimitsHolder1 = new OperationalLimitsHolderImpl(this, "limits1"); - operationalLimitsHolder2 = new OperationalLimitsHolderImpl(this, "limits2"); + operationalLimitsHolder1 = new OperationalLimitsGroupsImpl(this, "limits1"); + operationalLimitsHolder2 = new OperationalLimitsGroupsImpl(this, "limits2"); } @Override @@ -53,18 +53,38 @@ public TwoSides getSide(Terminal terminal) { } @Override - public Collection getOperationalLimits1() { - return operationalLimitsHolder1.getOperationalLimits(); + public List getOperationalLimitsGroups1() { + return operationalLimitsHolder1.getAllOperationalLimitsGroup(); + } + + @Override + public Optional getOperationalLimitsGroup1(String id) { + return operationalLimitsHolder1.getOperationalLimitsGroup(id); + } + + @Override + public Optional getDefaultOperationalLimitsGroup1() { + return operationalLimitsHolder1.getDefaultOperationalLimitsGroup(); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup1(String id) { + return operationalLimitsHolder1.newOperationalLimitsGroup(id); + } + + @Override + public void setDefaultOperationalLimitsGroup1To(String id) { + operationalLimitsHolder1.setDefaultTo(id); } @Override public Optional getCurrentLimits1() { - return operationalLimitsHolder1.getOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + return getDefaultOperationalLimitsGroup1().flatMap(OperationalLimitsGroup::getCurrentLimits); } @Override public CurrentLimits getNullableCurrentLimits1() { - return operationalLimitsHolder1.getNullableOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + return getCurrentLimits1().orElse(null); } @Override @@ -74,12 +94,12 @@ public CurrentLimitsAdder newCurrentLimits1() { @Override public Optional getApparentPowerLimits1() { - return operationalLimitsHolder1.getOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + return getDefaultOperationalLimitsGroup1().flatMap(OperationalLimitsGroup::getApparentPowerLimits); } @Override public ApparentPowerLimits getNullableApparentPowerLimits1() { - return operationalLimitsHolder1.getNullableOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + return getApparentPowerLimits1().orElse(null); } @Override @@ -87,19 +107,14 @@ public ApparentPowerLimitsAdder newApparentPowerLimits1() { return operationalLimitsHolder1.newApparentPowerLimits(); } - @Override - public Collection getOperationalLimits2() { - return operationalLimitsHolder2.getOperationalLimits(); - } - @Override public Optional getActivePowerLimits1() { - return operationalLimitsHolder1.getOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + return getDefaultOperationalLimitsGroup1().flatMap(OperationalLimitsGroup::getActivePowerLimits); } @Override public ActivePowerLimits getNullableActivePowerLimits1() { - return operationalLimitsHolder1.getNullableOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + return getActivePowerLimits1().orElse(null); } @Override @@ -107,14 +122,39 @@ public ActivePowerLimitsAdder newActivePowerLimits1() { return operationalLimitsHolder1.newActivePowerLimits(); } + @Override + public List getOperationalLimitsGroups2() { + return operationalLimitsHolder2.getAllOperationalLimitsGroup(); + } + + @Override + public Optional getOperationalLimitsGroup2(String id) { + return operationalLimitsHolder2.getOperationalLimitsGroup(id); + } + + @Override + public Optional getDefaultOperationalLimitsGroup2() { + return operationalLimitsHolder2.getDefaultOperationalLimitsGroup(); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup2(String id) { + return operationalLimitsHolder2.newOperationalLimitsGroup(id); + } + + @Override + public void setDefaultOperationalLimitsGroup2To(String id) { + operationalLimitsHolder2.setDefaultTo(id); + } + @Override public Optional getCurrentLimits2() { - return operationalLimitsHolder2.getOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + return getDefaultOperationalLimitsGroup2().flatMap(OperationalLimitsGroup::getCurrentLimits); } @Override public CurrentLimits getNullableCurrentLimits2() { - return operationalLimitsHolder2.getNullableOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + return getCurrentLimits2().orElse(null); } @Override @@ -124,12 +164,12 @@ public CurrentLimitsAdder newCurrentLimits2() { @Override public Optional getApparentPowerLimits2() { - return operationalLimitsHolder2.getOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + return getDefaultOperationalLimitsGroup2().flatMap(OperationalLimitsGroup::getApparentPowerLimits); } @Override public ApparentPowerLimits getNullableApparentPowerLimits2() { - return operationalLimitsHolder2.getNullableOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + return getApparentPowerLimits2().orElse(null); } @Override @@ -139,12 +179,12 @@ public ApparentPowerLimitsAdder newApparentPowerLimits2() { @Override public Optional getActivePowerLimits2() { - return operationalLimitsHolder2.getOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + return getDefaultOperationalLimitsGroup2().flatMap(OperationalLimitsGroup::getActivePowerLimits); } @Override public ActivePowerLimits getNullableActivePowerLimits2() { - return operationalLimitsHolder2.getNullableOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + return getActivePowerLimits2().orElse(null); } @Override @@ -167,11 +207,11 @@ public Optional getApparentPowerLimits(TwoSides side) { return BranchUtil.getFromSide(side, this::getApparentPowerLimits1, this::getApparentPowerLimits2); } - OperationalLimitsHolderImpl getLimitsHolder1() { + OperationalLimitsGroupsImpl getLimitsHolder1() { return operationalLimitsHolder1; } - OperationalLimitsHolderImpl getLimitsHolder2() { + OperationalLimitsGroupsImpl getLimitsHolder2() { return operationalLimitsHolder2; } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimits.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimits.java index 7856ab7c29e..0937f77c40f 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimits.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimits.java @@ -6,8 +6,7 @@ */ package com.powsybl.iidm.network.impl; -import com.powsybl.iidm.network.LoadingLimits; -import com.powsybl.iidm.network.ValidationUtil; +import com.powsybl.iidm.network.*; import java.util.Collection; import java.util.Objects; @@ -17,9 +16,7 @@ * @author Miora Ralambotiana {@literal } */ abstract class AbstractLoadingLimits> extends AbstractOperationalLimits implements LoadingLimits { - private double permanentLimit; - private final TreeMap temporaryLimits; static class TemporaryLimitImpl implements TemporaryLimit { @@ -60,7 +57,7 @@ public boolean isFictitious() { } } - AbstractLoadingLimits(OperationalLimitsOwner owner, double permanentLimit, TreeMap temporaryLimits) { + AbstractLoadingLimits(OperationalLimitsGroupImpl owner, double permanentLimit, TreeMap temporaryLimits) { super(owner); this.permanentLimit = permanentLimit; this.temporaryLimits = Objects.requireNonNull(temporaryLimits); @@ -73,10 +70,10 @@ public double getPermanentLimit() { @Override public L setPermanentLimit(double permanentLimit) { - ValidationUtil.checkPermanentLimit(owner, permanentLimit); + ValidationUtil.checkPermanentLimit(group.getValidable(), permanentLimit); double oldValue = this.permanentLimit; this.permanentLimit = permanentLimit; - owner.notifyUpdate(getLimitType(), "permanentLimit", oldValue, this.permanentLimit); + group.notifyUpdateIfDefaultLimits(getLimitType(), "permanentLimit", oldValue, this.permanentLimit); return (L) this; } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimitsAdder.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimitsAdder.java index 1090d994942..d2621bb31bc 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimitsAdder.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractLoadingLimitsAdder.java @@ -6,14 +6,12 @@ */ package com.powsybl.iidm.network.impl; -import com.powsybl.iidm.network.LoadingLimits; -import com.powsybl.iidm.network.LoadingLimitsAdder; -import com.powsybl.iidm.network.ValidationException; -import com.powsybl.iidm.network.ValidationUtil; +import com.powsybl.iidm.network.*; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import java.util.Comparator; +import java.util.Objects; import java.util.Optional; import java.util.TreeMap; import java.util.stream.Collectors; @@ -22,12 +20,11 @@ * @author Miora Ralambotiana {@literal } */ abstract class AbstractLoadingLimitsAdder> implements LoadingLimitsAdder { - private static final Logger LOGGER = LoggerFactory.getLogger(AbstractLoadingLimitsAdder.class); private static final Comparator ACCEPTABLE_DURATION_COMPARATOR = (acceptableDuration1, acceptableDuration2) -> acceptableDuration2 - acceptableDuration1; - protected final OperationalLimitsOwner owner; + protected final Validable validable; protected double permanentLimit = Double.NaN; @@ -78,16 +75,16 @@ public TemporaryLimitAdder ensureNameUnicity() { @Override public B endTemporaryLimit() { if (Double.isNaN(value)) { - throw new ValidationException(owner, "temporary limit value is not set"); + throw new ValidationException(validable, "temporary limit value is not set"); } if (value <= 0) { - throw new ValidationException(owner, "temporary limit value must be > 0"); + throw new ValidationException(validable, "temporary limit value must be > 0"); } if (acceptableDuration == null) { - throw new ValidationException(owner, "acceptable duration is not set"); + throw new ValidationException(validable, "acceptable duration is not set"); } if (acceptableDuration < 0) { - throw new ValidationException(owner, "acceptable duration must be >= 0"); + throw new ValidationException(validable, "acceptable duration must be >= 0"); } checkAndGetUniqueName(); temporaryLimits.put(acceptableDuration, new AbstractLoadingLimits.TemporaryLimitImpl(name, value, acceptableDuration, fictitious)); @@ -96,7 +93,7 @@ public B endTemporaryLimit() { private void checkAndGetUniqueName() { if (name == null) { - throw new ValidationException(owner, "name is not set"); + throw new ValidationException(validable, "name is not set"); } if (ensureNameUnicity) { int i = 0; @@ -114,8 +111,8 @@ private boolean nameExists(String name) { } } - AbstractLoadingLimitsAdder(OperationalLimitsOwner owner) { - this.owner = owner; + AbstractLoadingLimitsAdder(Validable validable) { + this.validable = Objects.requireNonNull(validable); } @Override @@ -149,12 +146,12 @@ private void checkTemporaryLimits() { double previousLimit = Double.NaN; for (LoadingLimits.TemporaryLimit tl : temporaryLimits.values()) { // iterate in ascending order if (tl.getValue() <= permanentLimit) { - LOGGER.debug("{}, temporary limit should be greater than permanent limit", owner.getMessageHeader()); + LOGGER.debug("{}, temporary limit should be greater than permanent limit", validable.getMessageHeader()); } if (Double.isNaN(previousLimit)) { previousLimit = tl.getValue(); } else if (tl.getValue() <= previousLimit) { - LOGGER.debug("{} : temporary limits should be in ascending value order", owner.getMessageHeader()); + LOGGER.debug("{} : temporary limits should be in ascending value order", validable.getMessageHeader()); } } // check name unicity @@ -162,13 +159,13 @@ private void checkTemporaryLimits() { .collect(Collectors.groupingBy(LoadingLimits.TemporaryLimit::getName)) .forEach((name, temporaryLimits1) -> { if (temporaryLimits1.size() > 1) { - throw new ValidationException(owner, temporaryLimits1.size() + "temporary limits have the same name " + name); + throw new ValidationException(validable, temporaryLimits1.size() + "temporary limits have the same name " + name); } }); } protected void checkLoadingLimits() { - ValidationUtil.checkPermanentLimit(owner, permanentLimit); + ValidationUtil.checkPermanentLimit(validable, permanentLimit); checkTemporaryLimits(); } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractOperationalLimits.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractOperationalLimits.java index 7165afac061..c7227f92fcf 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractOperationalLimits.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/AbstractOperationalLimits.java @@ -15,13 +15,9 @@ */ abstract class AbstractOperationalLimits implements OperationalLimits { - protected final OperationalLimitsOwner owner; + protected final OperationalLimitsGroupImpl group; - AbstractOperationalLimits(OperationalLimitsOwner owner) { - this.owner = Objects.requireNonNull(owner); - } - - public void remove() { - owner.setOperationalLimits(getLimitType(), null); + AbstractOperationalLimits(OperationalLimitsGroupImpl group) { + this.group = Objects.requireNonNull(group); } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAdderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAdderImpl.java index 670864259d5..dc0c124b8e4 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAdderImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAdderImpl.java @@ -6,24 +6,24 @@ */ package com.powsybl.iidm.network.impl; -import com.powsybl.iidm.network.ActivePowerLimits; -import com.powsybl.iidm.network.ActivePowerLimitsAdder; -import com.powsybl.iidm.network.LimitType; +import com.powsybl.iidm.network.*; /** * @author Miora Ralambotiana {@literal } */ class ActivePowerLimitsAdderImpl extends AbstractLoadingLimitsAdder implements ActivePowerLimitsAdder { + OperationalLimitsGroupImpl group; - ActivePowerLimitsAdderImpl(OperationalLimitsOwner owner) { - super(owner); + public ActivePowerLimitsAdderImpl(OperationalLimitsGroupImpl group, Validable validable) { + super(validable); + this.group = group; } @Override public ActivePowerLimits add() { checkLoadingLimits(); - ActivePowerLimits limits = new ActivePowerLimitsImpl(owner, permanentLimit, temporaryLimits); - owner.setOperationalLimits(LimitType.ACTIVE_POWER, limits); + ActivePowerLimitsImpl limits = new ActivePowerLimitsImpl(group, permanentLimit, temporaryLimits); + group.setActivePowerLimits(limits); return limits; } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAndGroupAdderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAndGroupAdderImpl.java new file mode 100644 index 00000000000..96c20d5d34c --- /dev/null +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsAndGroupAdderImpl.java @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2023, RTE (http://www.rte-france.com/) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * SPDX-License-Identifier: MPL-2.0 + */ +package com.powsybl.iidm.network.impl; + +import com.powsybl.iidm.network.*; + +import java.util.Optional; + +/** + */ +class ActivePowerLimitsAndGroupAdderImpl extends AbstractLoadingLimitsAdder implements ActivePowerLimitsAdder { + + OperationalLimitsGroups owner; + + public ActivePowerLimitsAndGroupAdderImpl(OperationalLimitsGroups owner, Validable validable) { + super(validable); + this.owner = owner; + } + + @Override + public ActivePowerLimits add() { + checkLoadingLimits(); + OperationalLimitsGroupImpl group; + Optional optGroup = owner.getDefaultOperationalLimitsGroup(); + if (optGroup.isEmpty()) { + // NB. owner.newOperationalLimitsGroup("") erase previous group with id "" if any and create a new one + group = (OperationalLimitsGroupImpl) owner.newOperationalLimitsGroup(""); + owner.setDefaultTo(""); + } else { + group = (OperationalLimitsGroupImpl) optGroup.get(); + } + ActivePowerLimitsImpl limits = new ActivePowerLimitsImpl(group, permanentLimit, temporaryLimits); + group.setActivePowerLimits(limits); + return limits; + } +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsImpl.java index 9e6f9b46182..c19e824a983 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ActivePowerLimitsImpl.java @@ -15,7 +15,12 @@ */ class ActivePowerLimitsImpl extends AbstractLoadingLimits implements ActivePowerLimits { - ActivePowerLimitsImpl(OperationalLimitsOwner owner, double permanentLimit, TreeMap temporaryLimits) { - super(owner, permanentLimit, temporaryLimits); + ActivePowerLimitsImpl(OperationalLimitsGroupImpl group, double permanentLimit, TreeMap temporaryLimits) { + super(group, permanentLimit, temporaryLimits); + } + + @Override + public void remove() { + group.removeActivePowerLimits(); } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAdderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAdderImpl.java index 61e5b9f6ca1..39f8eb0ef46 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAdderImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAdderImpl.java @@ -6,24 +6,25 @@ */ package com.powsybl.iidm.network.impl; -import com.powsybl.iidm.network.ApparentPowerLimits; -import com.powsybl.iidm.network.ApparentPowerLimitsAdder; -import com.powsybl.iidm.network.LimitType; +import com.powsybl.iidm.network.*; /** * @author Miora Ralambotiana {@literal } */ class ApparentPowerLimitsAdderImpl extends AbstractLoadingLimitsAdder implements ApparentPowerLimitsAdder { - ApparentPowerLimitsAdderImpl(OperationalLimitsOwner owner) { - super(owner); + OperationalLimitsGroupImpl group; + + public ApparentPowerLimitsAdderImpl(OperationalLimitsGroupImpl group, Validable validable) { + super(validable); + this.group = group; } @Override public ApparentPowerLimits add() { checkLoadingLimits(); - ApparentPowerLimits limits = new ApparentPowerLimitsImpl(owner, permanentLimit, temporaryLimits); - owner.setOperationalLimits(LimitType.APPARENT_POWER, limits); + ApparentPowerLimitsImpl limits = new ApparentPowerLimitsImpl(group, permanentLimit, temporaryLimits); + group.setApparentPowerLimits(limits); return limits; } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAndGroupAdderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAndGroupAdderImpl.java new file mode 100644 index 00000000000..62f6259c6d5 --- /dev/null +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsAndGroupAdderImpl.java @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2023, RTE (http://www.rte-france.com/) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * SPDX-License-Identifier: MPL-2.0 + */ +package com.powsybl.iidm.network.impl; + +import com.powsybl.iidm.network.*; + +import java.util.Optional; + +/** + */ +class ApparentPowerLimitsAndGroupAdderImpl extends AbstractLoadingLimitsAdder implements ApparentPowerLimitsAdder { + + OperationalLimitsGroups owner; + + public ApparentPowerLimitsAndGroupAdderImpl(OperationalLimitsGroups owner, Validable validable) { + super(validable); + this.owner = owner; + } + + @Override + public ApparentPowerLimits add() { + checkLoadingLimits(); + OperationalLimitsGroupImpl group; + Optional optGroup = owner.getDefaultOperationalLimitsGroup(); + if (optGroup.isEmpty()) { + // NB. owner.newOperationalLimitsGroup("") erase previous group with id "" if any and create a new one + group = (OperationalLimitsGroupImpl) owner.newOperationalLimitsGroup(""); + owner.setDefaultTo(""); + } else { + group = (OperationalLimitsGroupImpl) optGroup.get(); + } + ApparentPowerLimitsImpl limits = new ApparentPowerLimitsImpl(group, permanentLimit, temporaryLimits); + group.setApparentPowerLimits(limits); + return limits; + } +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsImpl.java index 75e89351ab2..06c041e556d 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ApparentPowerLimitsImpl.java @@ -15,7 +15,12 @@ */ class ApparentPowerLimitsImpl extends AbstractLoadingLimits implements ApparentPowerLimits { - ApparentPowerLimitsImpl(OperationalLimitsOwner owner, double permanentLimit, TreeMap temporaryLimits) { - super(owner, permanentLimit, temporaryLimits); + ApparentPowerLimitsImpl(OperationalLimitsGroupImpl group, double permanentLimit, TreeMap temporaryLimits) { + super(group, permanentLimit, temporaryLimits); + } + + @Override + public void remove() { + group.removeApparentPowerLimits(); } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAdderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAdderImpl.java index 9895fb1214f..fb5fff8031f 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAdderImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAdderImpl.java @@ -6,23 +6,28 @@ */ package com.powsybl.iidm.network.impl; -import com.powsybl.iidm.network.*; +import com.powsybl.iidm.network.CurrentLimits; +import com.powsybl.iidm.network.CurrentLimitsAdder; +import com.powsybl.iidm.network.Validable; /** * * @author Geoffroy Jamgotchian {@literal } */ -public class CurrentLimitsAdderImpl extends AbstractLoadingLimitsAdder implements CurrentLimitsAdder { +class CurrentLimitsAdderImpl extends AbstractLoadingLimitsAdder implements CurrentLimitsAdder { - public CurrentLimitsAdderImpl(OperationalLimitsOwner owner) { - super(owner); + OperationalLimitsGroupImpl group; + + public CurrentLimitsAdderImpl(OperationalLimitsGroupImpl group, Validable validable) { + super(validable); + this.group = group; } @Override - public CurrentLimitsImpl add() { + public CurrentLimits add() { checkLoadingLimits(); - CurrentLimitsImpl limits = new CurrentLimitsImpl(owner, permanentLimit, temporaryLimits); - owner.setOperationalLimits(LimitType.CURRENT, limits); + CurrentLimitsImpl limits = new CurrentLimitsImpl(group, permanentLimit, temporaryLimits); + group.setCurrentLimits(limits); return limits; } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAndGroupAdderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAndGroupAdderImpl.java new file mode 100644 index 00000000000..1674e7af78f --- /dev/null +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsAndGroupAdderImpl.java @@ -0,0 +1,42 @@ +/* + * Copyright (c) 2023, RTE (http://www.rte-france.com/) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * SPDX-License-Identifier: MPL-2.0 + */ +package com.powsybl.iidm.network.impl; + +import com.powsybl.iidm.network.*; + +import java.util.Optional; + +/** + * */ +class CurrentLimitsAndGroupAdderImpl extends AbstractLoadingLimitsAdder implements CurrentLimitsAdder { + + OperationalLimitsGroups owner; + + public CurrentLimitsAndGroupAdderImpl(OperationalLimitsGroups owner, Validable validable) { + super(validable); + this.owner = owner; + } + + @Override + public CurrentLimits add() { + checkLoadingLimits(); + OperationalLimitsGroupImpl group; + Optional optGroup = owner.getDefaultOperationalLimitsGroup(); + if (optGroup.isEmpty()) { + // NB. owner.newOperationalLimitsGroup("") erase previous group with id "" if any and create a new one + group = (OperationalLimitsGroupImpl) owner.newOperationalLimitsGroup(""); + owner.setDefaultTo(""); + } else { + group = (OperationalLimitsGroupImpl) optGroup.get(); + } + CurrentLimitsImpl limits = new CurrentLimitsImpl(group, permanentLimit, temporaryLimits); + group.setCurrentLimits(limits); + return limits; + } + +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsImpl.java index a7d2c78dd9b..a5aa756048c 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/CurrentLimitsImpl.java @@ -7,6 +7,7 @@ package com.powsybl.iidm.network.impl; import com.powsybl.iidm.network.CurrentLimits; + import java.util.TreeMap; /** @@ -15,7 +16,12 @@ */ public class CurrentLimitsImpl extends AbstractLoadingLimits implements CurrentLimits { - CurrentLimitsImpl(OperationalLimitsOwner owner, double permanentLimit, TreeMap temporaryLimits) { - super(owner, permanentLimit, temporaryLimits); + CurrentLimitsImpl(OperationalLimitsGroupImpl group, double permanentLimit, TreeMap temporaryLimits) { + super(group, permanentLimit, temporaryLimits); + } + + @Override + public void remove() { + group.removeCurrentLimits(); } } diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/DanglingLineImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/DanglingLineImpl.java index 8dad09eb268..75fc69cf74c 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/DanglingLineImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/DanglingLineImpl.java @@ -249,7 +249,7 @@ void allocateVariantArrayElement(int[] indexes, int sourceIndex) { private final GenerationImpl generation; - private final OperationalLimitsHolderImpl operationalLimitsHolder; + private final OperationalLimitsGroupsImpl operationalLimitsHolder; // attributes depending on the variant private final TDoubleArrayList p0; @@ -273,7 +273,7 @@ void allocateVariantArrayElement(int[] indexes, int sourceIndex) { this.g = g; this.b = b; this.pairingKey = pairingKey; - this.operationalLimitsHolder = new OperationalLimitsHolderImpl(this, "limits"); + this.operationalLimitsHolder = new OperationalLimitsGroupsImpl(this, "limits"); this.boundary = new DanglingLineBoundaryImpl(this); this.generation = generation != null ? generation.attach(this) : null; } @@ -286,7 +286,7 @@ void replaceId(String newId) { network.get().getIndex().checkAndAdd(this); } - OperationalLimitsHolderImpl getLimitsHolder() { + OperationalLimitsGroupsImpl getLimitsHolder() { return operationalLimitsHolder; } @@ -425,38 +425,38 @@ public Generation getGeneration() { } @Override - public Collection getOperationalLimits() { - return operationalLimitsHolder.getOperationalLimits(); + public List getOperationalLimitsGroups() { + return operationalLimitsHolder.getAllOperationalLimitsGroup(); } @Override - public Optional getCurrentLimits() { - return operationalLimitsHolder.getOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + public Optional getOperationalLimitsGroup(String id) { + return operationalLimitsHolder.getOperationalLimitsGroup(id); } @Override - public CurrentLimits getNullableCurrentLimits() { - return operationalLimitsHolder.getNullableOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + public Optional getDefaultOperationalLimitsGroup() { + return operationalLimitsHolder.getDefaultOperationalLimitsGroup(); } @Override - public Optional getActivePowerLimits() { - return operationalLimitsHolder.getOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + public OperationalLimitsGroup newOperationalLimitsGroup(String id) { + return operationalLimitsHolder.newOperationalLimitsGroup(id); } @Override - public ActivePowerLimits getNullableActivePowerLimits() { - return operationalLimitsHolder.getNullableOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + public void setDefaultOperationalLimitsGroupTo(String id) { + operationalLimitsHolder.setDefaultTo(id); } @Override - public Optional getApparentPowerLimits() { - return operationalLimitsHolder.getOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + public Optional getCurrentLimits() { + return getDefaultOperationalLimitsGroup().flatMap(OperationalLimitsGroup::getCurrentLimits); } @Override - public ApparentPowerLimits getNullableApparentPowerLimits() { - return operationalLimitsHolder.getNullableOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + public CurrentLimits getNullableCurrentLimits() { + return getCurrentLimits().orElse(null); } @Override @@ -465,8 +465,13 @@ public CurrentLimitsAdder newCurrentLimits() { } @Override - public ActivePowerLimitsAdder newActivePowerLimits() { - return operationalLimitsHolder.newActivePowerLimits(); + public Optional getApparentPowerLimits() { + return getDefaultOperationalLimitsGroup().flatMap(OperationalLimitsGroup::getApparentPowerLimits); + } + + @Override + public ApparentPowerLimits getNullableApparentPowerLimits() { + return getApparentPowerLimits().orElse(null); } @Override @@ -474,6 +479,21 @@ public ApparentPowerLimitsAdder newApparentPowerLimits() { return operationalLimitsHolder.newApparentPowerLimits(); } + @Override + public Optional getActivePowerLimits() { + return getDefaultOperationalLimitsGroup().flatMap(OperationalLimitsGroup::getActivePowerLimits); + } + + @Override + public ActivePowerLimits getNullableActivePowerLimits() { + return getActivePowerLimits().orElse(null); + } + + @Override + public ActivePowerLimitsAdder newActivePowerLimits() { + return operationalLimitsHolder.newActivePowerLimits(); + } + @Override public Boundary getBoundary() { return boundary; diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupImpl.java new file mode 100644 index 00000000000..76a8454d7a7 --- /dev/null +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupImpl.java @@ -0,0 +1,101 @@ +/* + * Copyright (c) 2023, RTE (http://www.rte-france.com/) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * SPDX-License-Identifier: MPL-2.0 + */ +package com.powsybl.iidm.network.impl; + +import com.powsybl.iidm.network.*; + +import java.util.*; + +class OperationalLimitsGroupImpl implements OperationalLimitsGroup { + + private final OperationalLimitsGroups.GroupsValidable validable; + private final String id; + private CurrentLimits currentLimits; + private ActivePowerLimits activePowerLimits; + private ApparentPowerLimits apparentPowerLimits; + + OperationalLimitsGroupImpl(String id, OperationalLimitsGroups.GroupsValidable validable) { + this.validable = Objects.requireNonNull(validable); + this.id = Objects.requireNonNull(id); + this.currentLimits = null; + this.activePowerLimits = null; + this.apparentPowerLimits = null; + } + + @Override + public String getId() { + return id; + } + + @Override + public Optional getCurrentLimits() { + return Optional.ofNullable(currentLimits); + } + + @Override + public Optional getActivePowerLimits() { + return Optional.ofNullable(activePowerLimits); + } + + @Override + public Optional getApparentPowerLimits() { + return Optional.ofNullable(apparentPowerLimits); + } + + @Override + public CurrentLimitsAdder newCurrentLimits() { + return new CurrentLimitsAdderImpl(this, validable); + } + + @Override + public ActivePowerLimitsAdder newActivePowerLimits() { + return new ActivePowerLimitsAdderImpl(this, validable); + } + + @Override + public ApparentPowerLimitsAdder newApparentPowerLimits() { + return new ApparentPowerLimitsAdderImpl(this, validable); + } + + @Override + public void removeCurrentLimits() { + this.currentLimits = null; + } + + @Override + public void removeActivePowerLimits() { + this.activePowerLimits = null; + } + + @Override + public void removeApparentPowerLimits() { + this.apparentPowerLimits = null; + } + + public Validable getValidable() { + return validable; + } + + public void notifyUpdateIfDefaultLimits(LimitType limitType, String attribute, double oldValue, double newValue) { + validable.notifyUpdateIfDefaultLimits(getId(), limitType, attribute, oldValue, newValue); + } + + // For retro-compatibility: + public void setCurrentLimits(CurrentLimits limits) { + this.currentLimits = limits; + } + + public void setActivePowerLimits(ActivePowerLimits limits) { + this.activePowerLimits = limits; + } + + public void setApparentPowerLimits(ApparentPowerLimits limits) { + this.apparentPowerLimits = limits; + } + +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroups.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroups.java new file mode 100644 index 00000000000..7fafdac7d9d --- /dev/null +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroups.java @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2023, RTE (http://www.rte-france.com/) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * SPDX-License-Identifier: MPL-2.0 + */ +package com.powsybl.iidm.network.impl; + +import com.powsybl.iidm.network.LimitType; +import com.powsybl.iidm.network.OperationalLimitsGroup; +import com.powsybl.iidm.network.Validable; + +import java.util.List; +import java.util.Optional; + +/** + * @author Miora Ralambotiana {@literal } + */ +public interface OperationalLimitsGroups { + + List getAllOperationalLimitsGroup(); + + OperationalLimitsGroup newOperationalLimitsGroup(String id); + + Optional getOperationalLimitsGroup(String id); + + void removeOperationalLimitsGroup(String id); + + void setDefaultTo(String id); + + void cancelDefault(); + + Optional getDefaultOperationalLimitsGroup(); + + interface GroupsValidable extends Validable { + void notifyUpdateIfDefaultLimits(String id, LimitType limitType, String attribute, double oldValue, double newValue); + } +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupsImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupsImpl.java new file mode 100644 index 00000000000..b9a56ab857c --- /dev/null +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsGroupsImpl.java @@ -0,0 +1,160 @@ +/** + * Copyright (c) 2020, RTE (http://www.rte-france.com) + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ +package com.powsybl.iidm.network.impl; + +import com.powsybl.commons.PowsyblException; +import com.powsybl.iidm.network.*; + +import javax.annotation.Nullable; +import java.util.*; + +/** + * @author Miora Ralambotiana {@literal } + */ +class OperationalLimitsGroupsImpl implements OperationalLimitsGroups { + + private String defaultLimitsId = null; + + class ValidableImpl implements GroupsValidable { + + private final AbstractIdentifiable identifiable; + private final String attributeName; + + ValidableImpl(AbstractIdentifiable identifiable, String attributeName) { + this.identifiable = Objects.requireNonNull(identifiable); + this.attributeName = Objects.requireNonNull(attributeName); + } + + @Override + public String getMessageHeader() { + return identifiable.getMessageHeader(); + } + + private void notifyUpdate(@Nullable OperationalLimitsGroup oldValue, @Nullable OperationalLimitsGroup newValue) { + // NB. Normally only called for default limits + if (newValue == null) { + Objects.requireNonNull(oldValue); + + } + CurrentLimits oldCurrentValue = oldValue == null ? null : oldValue.getCurrentLimits().orElse(null); + CurrentLimits newCurrentValue = newValue == null ? null : newValue.getCurrentLimits().orElse(null); + if (!Objects.equals(oldCurrentValue, newCurrentValue)) { + identifiable.getNetwork().getListeners().notifyUpdate(identifiable, attributeName + "_" + LimitType.CURRENT, oldCurrentValue, newCurrentValue); + } + ActivePowerLimits oldActivePowerLimits = oldValue == null ? null : oldValue.getActivePowerLimits().orElse(null); + ActivePowerLimits newActivePowerLimits = newValue == null ? null : newValue.getActivePowerLimits().orElse(null); + if (!Objects.equals(oldActivePowerLimits, newActivePowerLimits)) { + identifiable.getNetwork().getListeners().notifyUpdate(identifiable, attributeName + "_" + LimitType.ACTIVE_POWER, oldActivePowerLimits, newActivePowerLimits); + } + ApparentPowerLimits oldApparentPowerLimits = oldValue == null ? null : oldValue.getApparentPowerLimits().orElse(null); + ApparentPowerLimits newApparentPowerLimits = newValue == null ? null : newValue.getApparentPowerLimits().orElse(null); + if (!Objects.equals(oldApparentPowerLimits, newApparentPowerLimits)) { + identifiable.getNetwork().getListeners().notifyUpdate(identifiable, attributeName + "_" + LimitType.APPARENT_POWER, oldApparentPowerLimits, newApparentPowerLimits); + } + } + + @Override + public void notifyUpdateIfDefaultLimits(String id, LimitType limitType, String attribute, double oldValue, double newValue) { + if (defaultLimitsId != null && defaultLimitsId.equals(id)) { + identifiable.getNetwork().getListeners().notifyUpdate(identifiable, attributeName + "_" + limitType + "." + attribute, oldValue, newValue); + } + } + } + + private final Map operationalLimitsGroupById = new HashMap<>(); + private final ValidableImpl validable; + + OperationalLimitsGroupsImpl(AbstractIdentifiable identifiable, String attributeName) { + this.validable = new ValidableImpl(identifiable, attributeName); + } + + @Override + public List getAllOperationalLimitsGroup() { + return new ArrayList<>(operationalLimitsGroupById.values()); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup(String id) { + // NB. Do not check if id exist but replace + // NB. Notify only for default limits change (can be changed) + Objects.requireNonNull(id); + OperationalLimitsGroup newLimits = new OperationalLimitsGroupImpl(id, validable); + OperationalLimitsGroup oldLimits = operationalLimitsGroupById.put(id, newLimits); + if (defaultLimitsId != null && defaultLimitsId.equals(id)) { + validable.notifyUpdate(oldLimits, newLimits); + } + return newLimits; + } + + private OperationalLimitsGroup getDefault() { + Objects.requireNonNull(defaultLimitsId); + OperationalLimitsGroup defaultLimits = operationalLimitsGroupById.get(defaultLimitsId); + if (defaultLimits == null) { + throw new PowsyblException("Default id exist and is " + defaultLimitsId + " but associated operational limits group do not exist"); + } + return defaultLimits; + } + + @Override + public Optional getOperationalLimitsGroup(String id) { + Objects.requireNonNull(id); + /*if (limits == null) { + throw new PowsyblException("Limits with id " + id + " do not exist in the operational limits set." + + "Availabled ids are: " + operationalLimitsGroupById.keySet()); + }*/ + return Optional.ofNullable(operationalLimitsGroupById.get(id)); + } + + public void removeOperationalLimitsGroup(String id) { + Objects.requireNonNull(id); + OperationalLimitsGroup oldLimits = operationalLimitsGroupById.remove(id); + if (defaultLimitsId != null && Objects.equals(defaultLimitsId, id)) { + defaultLimitsId = null; + validable.notifyUpdate(oldLimits, null); + } + } + + @Override + public void setDefaultTo(String id) { + Objects.requireNonNull(id); + OperationalLimitsGroup newDefaultLimits = operationalLimitsGroupById.get(id); + if (newDefaultLimits == null) { + throw new PowsyblException("No operational limits group is associated to id " + id + " so this id can't be the default one"); + } + OperationalLimitsGroup oldDefaultLimits = defaultLimitsId != null ? getDefault() : null; + defaultLimitsId = id; + validable.notifyUpdate(oldDefaultLimits, newDefaultLimits); + } + + @Override + public void cancelDefault() { + if (defaultLimitsId != null) { + OperationalLimitsGroup oldDefaultLimits = getDefault(); + defaultLimitsId = null; + validable.notifyUpdate(oldDefaultLimits, null); + } + } + + @Override + public Optional getDefaultOperationalLimitsGroup() { + return defaultLimitsId == null ? Optional.empty() : Optional.of(getDefault()); + } + + // For retro-compatibility: + CurrentLimitsAdder newCurrentLimits() { + return new CurrentLimitsAndGroupAdderImpl(this, validable); + } + + ActivePowerLimitsAdder newActivePowerLimits() { + return new ActivePowerLimitsAndGroupAdderImpl(this, validable); + } + + ApparentPowerLimitsAdder newApparentPowerLimits() { + return new ApparentPowerLimitsAndGroupAdderImpl(this, validable); + } + +} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsHolderImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsHolderImpl.java deleted file mode 100644 index d8a74115c1a..00000000000 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsHolderImpl.java +++ /dev/null @@ -1,78 +0,0 @@ -/** - * Copyright (c) 2020, RTE (http://www.rte-france.com) - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - */ -package com.powsybl.iidm.network.impl; - -import com.powsybl.iidm.network.*; - -import java.util.*; - -/** - * @author Miora Ralambotiana {@literal } - */ -class OperationalLimitsHolderImpl implements OperationalLimitsOwner { - - private final EnumMap operationalLimits = new EnumMap<>(LimitType.class); - private final AbstractIdentifiable identifiable; - private final String attributeName; - - OperationalLimitsHolderImpl(AbstractIdentifiable identifiable, String attributeName) { - this.identifiable = Objects.requireNonNull(identifiable); - this.attributeName = Objects.requireNonNull(attributeName); - } - - @Override - public void setOperationalLimits(LimitType limitType, OperationalLimits operationalLimits) { - OperationalLimits oldValue; - if (operationalLimits == null) { - oldValue = this.operationalLimits.remove(limitType); - } else { - oldValue = this.operationalLimits.put(limitType, operationalLimits); - } - identifiable.getNetwork().getListeners().notifyUpdate(identifiable, attributeName + "_" + limitType, oldValue, operationalLimits); - } - - @Override - public void notifyUpdate(LimitType limitType, String attribute, double oldValue, double newValue) { - identifiable.getNetwork().getListeners().notifyUpdate(identifiable, attributeName + "_" + limitType + "." + attribute, oldValue, newValue); - } - - Collection getOperationalLimits() { - return Collections.unmodifiableCollection(operationalLimits.values()); - } - - Optional getOperationalLimits(LimitType type, Class limitClazz) { - return Optional.ofNullable(getNullableOperationalLimits(type, limitClazz)); - } - - L getNullableOperationalLimits(LimitType type, Class limitClazz) { - if (type == null) { - throw new IllegalArgumentException("limit type is null"); - } - OperationalLimits ol = this.operationalLimits.get(type); - if (ol == null || limitClazz.isInstance(ol)) { - return (L) ol; - } - throw new IllegalStateException("Unexpected class for operational limits of type " + type + ". Expected: " + ol.getClass().getName() + ", actual: " + limitClazz.getName() + "."); - } - - CurrentLimitsAdder newCurrentLimits() { - return new CurrentLimitsAdderImpl(this); - } - - ApparentPowerLimitsAdder newApparentPowerLimits() { - return new ApparentPowerLimitsAdderImpl(this); - } - - ActivePowerLimitsAdder newActivePowerLimits() { - return new ActivePowerLimitsAdderImpl(this); - } - - @Override - public String getMessageHeader() { - return identifiable.getMessageHeader(); - } -} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsOwner.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsOwner.java deleted file mode 100644 index 85a40d7931a..00000000000 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/OperationalLimitsOwner.java +++ /dev/null @@ -1,21 +0,0 @@ -/** - * Copyright (c) 2020, RTE (http://www.rte-france.com) - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - */ -package com.powsybl.iidm.network.impl; - -import com.powsybl.iidm.network.LimitType; -import com.powsybl.iidm.network.OperationalLimits; -import com.powsybl.iidm.network.Validable; - -/** - * @author Miora Ralambotiana {@literal } - */ -public interface OperationalLimitsOwner extends Validable { - - void setOperationalLimits(LimitType limitType, OperationalLimits operationalLimits); - - void notifyUpdate(LimitType limitType, String attribute, double oldValue, double newValue); -} diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ThreeWindingsTransformerImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ThreeWindingsTransformerImpl.java index e27cfc29d41..e7deb6ffbde 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ThreeWindingsTransformerImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/ThreeWindingsTransformerImpl.java @@ -36,7 +36,7 @@ static class LegImpl private double ratedS; - private OperationalLimitsHolderImpl operationalLimitsHolder; + private OperationalLimitsGroupsImpl operationalLimitsHolder; private RatioTapChangerImpl ratioTapChanger; @@ -56,7 +56,7 @@ static class LegImpl void setTransformer(ThreeWindingsTransformerImpl transformer) { this.transformer = transformer; - operationalLimitsHolder = new OperationalLimitsHolderImpl(transformer, "limits" + legNumber); + operationalLimitsHolder = new OperationalLimitsGroupsImpl(transformer, "limits" + legNumber); } public TerminalExt getTerminal() { @@ -166,18 +166,38 @@ public void setPhaseTapChanger(PhaseTapChangerImpl phaseTapChanger) { } @Override - public Collection getOperationalLimits() { - return operationalLimitsHolder.getOperationalLimits(); + public List getOperationalLimitsGroups() { + return operationalLimitsHolder.getAllOperationalLimitsGroup(); + } + + @Override + public Optional getOperationalLimitsGroup(String id) { + return operationalLimitsHolder.getOperationalLimitsGroup(id); + } + + @Override + public Optional getDefaultOperationalLimitsGroup() { + return operationalLimitsHolder.getDefaultOperationalLimitsGroup(); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup(String id) { + return operationalLimitsHolder.newOperationalLimitsGroup(id); + } + + @Override + public void setDefaultOperationalLimitsGroupTo(String id) { + operationalLimitsHolder.setDefaultTo(id); } @Override public Optional getCurrentLimits() { - return operationalLimitsHolder.getOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + return getDefaultOperationalLimitsGroup().flatMap(OperationalLimitsGroup::getCurrentLimits); } @Override public CurrentLimits getNullableCurrentLimits() { - return operationalLimitsHolder.getNullableOperationalLimits(LimitType.CURRENT, CurrentLimits.class); + return getCurrentLimits().orElse(null); } @Override @@ -187,12 +207,12 @@ public CurrentLimitsAdder newCurrentLimits() { @Override public Optional getApparentPowerLimits() { - return operationalLimitsHolder.getOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + return getDefaultOperationalLimitsGroup().flatMap(OperationalLimitsGroup::getApparentPowerLimits); } @Override public ApparentPowerLimits getNullableApparentPowerLimits() { - return operationalLimitsHolder.getNullableOperationalLimits(LimitType.APPARENT_POWER, ApparentPowerLimits.class); + return getApparentPowerLimits().orElse(null); } @Override @@ -202,12 +222,12 @@ public ApparentPowerLimitsAdder newApparentPowerLimits() { @Override public Optional getActivePowerLimits() { - return operationalLimitsHolder.getOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + return getDefaultOperationalLimitsGroup().flatMap(OperationalLimitsGroup::getActivePowerLimits); } @Override public ActivePowerLimits getNullableActivePowerLimits() { - return operationalLimitsHolder.getNullableOperationalLimits(LimitType.ACTIVE_POWER, ActivePowerLimits.class); + return getActivePowerLimits().orElse(null); } @Override diff --git a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/TieLineImpl.java b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/TieLineImpl.java index c26fd615364..ecaadf74357 100644 --- a/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/TieLineImpl.java +++ b/iidm/iidm-impl/src/main/java/com/powsybl/iidm/network/impl/TieLineImpl.java @@ -12,11 +12,10 @@ import com.powsybl.iidm.network.util.LimitViolationUtils; import com.powsybl.iidm.network.util.TieLineUtil; -import java.util.Collection; +import java.util.List; import java.util.Optional; /** - * * @author Geoffroy Jamgotchian {@literal } * @author Luma Zamarreño {@literal } * @author José Antonio Marqués {@literal } @@ -187,13 +186,33 @@ public TwoSides getSide(Terminal terminal) { } @Override - public Collection getOperationalLimits1() { - return danglingLine1.getOperationalLimits(); + public List getOperationalLimitsGroups1() { + return danglingLine1.getOperationalLimitsGroups(); + } + + @Override + public Optional getOperationalLimitsGroup1(String id) { + return danglingLine1.getOperationalLimitsGroup(id); + } + + @Override + public Optional getDefaultOperationalLimitsGroup1() { + return danglingLine1.getDefaultOperationalLimitsGroup(); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup1(String id) { + return danglingLine1.newOperationalLimitsGroup(id); + } + + @Override + public void setDefaultOperationalLimitsGroup1To(String id) { + danglingLine1.setDefaultOperationalLimitsGroupTo(id); } @Override public Optional getCurrentLimits1() { - return danglingLine1.getCurrentLimits(); + return getDefaultOperationalLimitsGroup1().flatMap(OperationalLimitsGroup::getCurrentLimits); } @Override @@ -208,7 +227,7 @@ public CurrentLimitsAdder newCurrentLimits1() { @Override public Optional getApparentPowerLimits1() { - return danglingLine1.getApparentPowerLimits(); + return getDefaultOperationalLimitsGroup1().flatMap(OperationalLimitsGroup::getApparentPowerLimits); } @Override @@ -221,14 +240,9 @@ public ApparentPowerLimitsAdder newApparentPowerLimits1() { return danglingLine1.newApparentPowerLimits(); } - @Override - public Collection getOperationalLimits2() { - return danglingLine2.getOperationalLimits(); - } - @Override public Optional getActivePowerLimits1() { - return danglingLine1.getActivePowerLimits(); + return getDefaultOperationalLimitsGroup1().flatMap(OperationalLimitsGroup::getActivePowerLimits); } @Override @@ -241,9 +255,34 @@ public ActivePowerLimitsAdder newActivePowerLimits1() { return danglingLine1.newActivePowerLimits(); } + @Override + public List getOperationalLimitsGroups2() { + return danglingLine2.getOperationalLimitsGroups(); + } + + @Override + public Optional getOperationalLimitsGroup2(String id) { + return danglingLine2.getOperationalLimitsGroup(id); + } + + @Override + public Optional getDefaultOperationalLimitsGroup2() { + return danglingLine2.getDefaultOperationalLimitsGroup(); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup2(String id) { + return danglingLine2.newOperationalLimitsGroup(id); + } + + @Override + public void setDefaultOperationalLimitsGroup2To(String id) { + danglingLine2.setDefaultOperationalLimitsGroupTo(id); + } + @Override public Optional getCurrentLimits2() { - return danglingLine2.getCurrentLimits(); + return getDefaultOperationalLimitsGroup2().flatMap(OperationalLimitsGroup::getCurrentLimits); } @Override @@ -258,7 +297,7 @@ public CurrentLimitsAdder newCurrentLimits2() { @Override public Optional getApparentPowerLimits2() { - return danglingLine2.getApparentPowerLimits(); + return getDefaultOperationalLimitsGroup2().flatMap(OperationalLimitsGroup::getApparentPowerLimits); } @Override @@ -273,7 +312,7 @@ public ApparentPowerLimitsAdder newApparentPowerLimits2() { @Override public Optional getActivePowerLimits2() { - return danglingLine2.getActivePowerLimits(); + return getDefaultOperationalLimitsGroup2().flatMap(OperationalLimitsGroup::getActivePowerLimits); } @Override diff --git a/iidm/iidm-serde/src/main/java/com/powsybl/iidm/serde/ConnectableSerDeUtil.java b/iidm/iidm-serde/src/main/java/com/powsybl/iidm/serde/ConnectableSerDeUtil.java index c13548153a6..0a96fc5a922 100644 --- a/iidm/iidm-serde/src/main/java/com/powsybl/iidm/serde/ConnectableSerDeUtil.java +++ b/iidm/iidm-serde/src/main/java/com/powsybl/iidm/serde/ConnectableSerDeUtil.java @@ -43,20 +43,6 @@ private static String indexToString(Integer index) { return index != null ? index.toString() : ""; } - public static boolean hasValidOperationalLimits(Branch branch, NetworkSerializerContext context) { - if (context.getVersion().compareTo(IidmVersion.V_1_5) >= 0) { - return !branch.getOperationalLimits1().isEmpty() || !branch.getOperationalLimits2().isEmpty(); - } - return branch.getCurrentLimits1().isPresent() || branch.getCurrentLimits2().isPresent(); - } - - public static boolean hasValidOperationalLimits(FlowsLimitsHolder limitsHolder, NetworkSerializerContext context) { - if (context.getVersion().compareTo(IidmVersion.V_1_5) >= 0) { - return !limitsHolder.getOperationalLimits().isEmpty(); - } - return limitsHolder.getCurrentLimits().isPresent(); - } - public static void writeNodeOrBus(Integer index, Terminal t, NetworkSerializerContext context) { if (index != null) { context.getWriter().writeStringAttribute("voltageLevelId" + index, context.getAnonymizer().anonymizeString(t.getVoltageLevel().getId())); diff --git a/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractCurrentLimitsTest.java b/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractCurrentLimitsTest.java index e339229f1c2..f72c6476524 100644 --- a/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractCurrentLimitsTest.java +++ b/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractCurrentLimitsTest.java @@ -16,7 +16,7 @@ */ public abstract class AbstractCurrentLimitsTest { - private static Network createNetwork() { + private static Network createNetworkCommons() { Network network = Network.create("test", "test"); Substation s1 = network.newSubstation() .setId("S1") @@ -57,6 +57,12 @@ private static Network createNetwork() { .setB1(0.0) .setB2(0.0) .add(); + return network; + } + + private static Network createNetwork() { + Network network = createNetworkCommons(); + Line l = network.getLine("L"); l.newCurrentLimits1() .setPermanentLimit(1000.0) .beginTemporaryLimit() @@ -196,6 +202,61 @@ private static Network createNetworkForThreeWindingsTransformer() { return network; } + private static Network createNetworkWithCurrentLimitsSet() { + Network network = createNetworkCommons(); + Line l = network.getLine("L"); + l.newOperationalLimitsGroup1("1") + .newCurrentLimits() + .setPermanentLimit(900.0) + .beginTemporaryLimit() + .setName("20'") + .setAcceptableDuration(20 * 60) + .setValue(1100.0) + .endTemporaryLimit() + .beginTemporaryLimit() + .setName("5'") + .setAcceptableDuration(5 * 60) + .setValue(1300.0) + .endTemporaryLimit() + .beginTemporaryLimit() + .setName("1'") + .setAcceptableDuration(60) + .setValue(1500.0) + .endTemporaryLimit() + .add(); + l.newOperationalLimitsGroup1("2"); + l.getOperationalLimitsGroup1("2").ifPresent(olg -> + olg.newCurrentLimits() + .setPermanentLimit(1000.0) + .beginTemporaryLimit() + .setName("20'") + .setAcceptableDuration(20 * 60) + .setValue(1200.0) + .endTemporaryLimit() + .beginTemporaryLimit() + .setName("5'") + .setAcceptableDuration(5 * 60) + .setValue(1400.0) + .endTemporaryLimit() + .beginTemporaryLimit() + .setName("1'") + .setAcceptableDuration(60) + .setValue(1600.0) + .endTemporaryLimit() + .add()); + l.newOperationalLimitsGroup1("3") + .newCurrentLimits() + .setPermanentLimit(800.0) + .add(); + l.newOperationalLimitsGroup2("1") + .newCurrentLimits() + .setPermanentLimit(850.0) + .add(); + l.getOperationalLimitsGroup2("1").flatMap(OperationalLimitsGroup::getCurrentLimits).ifPresent(cl -> cl.setPermanentLimit(800.0)); + l.setDefaultOperationalLimitsGroup2To("1"); + return network; + } + @Test public void test() { Network network = createNetwork(); @@ -475,4 +536,49 @@ public void ensureNameUnicity() { assertEquals("TL#0", currentLimits.getTemporaryLimit(10 * 60).getName()); assertEquals("TL#1", currentLimits.getTemporaryLimit(5 * 60).getName()); } + + @Test + public void testForCurrentLimitsSet() { + Network network = createNetworkWithCurrentLimitsSet(); + Line l = network.getLine("L"); + l.getTerminal1().getBusBreakerView().getBus().setV(390.0); + l.getTerminal1().setP(800.0).setQ(400.0); // i = 1324.0969 + assertFalse(Double.isNaN(l.getTerminal1().getI())); + + // No limits enabled so no limits so everything is false or not-equals + assertFalse(l.isOverloaded()); + assertNotEquals(5 * 60L, l.getOverloadDuration()); + assertFalse(l.checkPermanentLimit1(LimitType.CURRENT)); + assertNull(l.checkTemporaryLimits1(LimitType.CURRENT)); + + l.setDefaultOperationalLimitsGroup1To("2"); + assertTrue(l.isOverloaded()); + assertEquals(5 * 60L, l.getOverloadDuration()); + assertTrue(l.checkPermanentLimit1(LimitType.CURRENT)); + assertNotNull(l.checkTemporaryLimits1(LimitType.CURRENT)); + assertEquals(5 * 60L, l.checkTemporaryLimits1(LimitType.CURRENT).getTemporaryLimit().getAcceptableDuration()); + assertEquals(1200.0, l.checkTemporaryLimits1(LimitType.CURRENT).getPreviousLimit(), 0.0); + + l.setDefaultOperationalLimitsGroup1To("3"); + assertTrue(l.isOverloaded()); + assertTrue(l.checkPermanentLimit1(LimitType.CURRENT)); + assertNull(l.checkTemporaryLimits1(LimitType.CURRENT)); + + //l.getOrCreateCurrentLimitsSet1().removeLimitsFromSet("2"); + //assertTrue(l.isOverloaded()); + //assertTrue(l.checkPermanentLimit1(LimitType.CURRENT)); + + //l.getOrCreateCurrentLimitsSet1().removeLimitsFromSet("3"); + //assertFalse(l.isOverloaded()); + //assertFalse(l.checkPermanentLimit1(LimitType.CURRENT)); + + l.getTerminal2().getBusBreakerView().getBus().setV(390.0); + l.getTerminal2().setP(900.0).setQ(500.0); // i = 1524.1499 + assertFalse(Double.isNaN(l.getTerminal2().getI())); + + assertTrue(l.checkPermanentLimit2(LimitType.CURRENT)); + + //l.getOrCreateCurrentLimitsSet2().cancelDefaultLimits(); + //assertFalse(l.checkPermanentLimit2(LimitType.CURRENT)); + } } diff --git a/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractThreeWindingsTransformerTest.java b/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractThreeWindingsTransformerTest.java index e98497a8c0f..16c48064e65 100644 --- a/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractThreeWindingsTransformerTest.java +++ b/iidm/iidm-tck/src/test/java/com/powsybl/iidm/network/tck/AbstractThreeWindingsTransformerTest.java @@ -136,7 +136,6 @@ public void baseTests() { .setPermanentLimit(2.4) .add(); assertSame(apparentPowerLimits1, leg1.getApparentPowerLimits().orElse(null)); - assertEquals(3, leg1.getOperationalLimits().size()); RatioTapChanger ratioTapChangerInLeg2 = createRatioTapChanger(leg2, transformer.getTerminal(ThreeSides.TWO)); diff --git a/matpower/matpower-converter/src/main/java/com/powsybl/matpower/converter/MatpowerExporter.java b/matpower/matpower-converter/src/main/java/com/powsybl/matpower/converter/MatpowerExporter.java index 1fdf717a334..63f4ccd3a7e 100644 --- a/matpower/matpower-converter/src/main/java/com/powsybl/matpower/converter/MatpowerExporter.java +++ b/matpower/matpower-converter/src/main/java/com/powsybl/matpower/converter/MatpowerExporter.java @@ -323,6 +323,31 @@ public FlowsLimitsHolderBranchAdapter(Branch branch, TwoSides side) { this.side = side; } + @Override + public List getOperationalLimitsGroups() { + throw new UnsupportedOperationException(); + } + + @Override + public Optional getOperationalLimitsGroup(String id) { + throw new UnsupportedOperationException(); + } + + @Override + public Optional getDefaultOperationalLimitsGroup() { + throw new UnsupportedOperationException(); + } + + @Override + public OperationalLimitsGroup newOperationalLimitsGroup(String id) { + throw new UnsupportedOperationException(); + } + + @Override + public void setDefaultOperationalLimitsGroupTo(String id) { + throw new UnsupportedOperationException(); + } + @Override public Optional getCurrentLimits() { return branch.getCurrentLimits(side);