SVTest.java
/**
* 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.util;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
import com.powsybl.iidm.network.*;
import com.powsybl.iidm.network.test.DanglingLineNetworkFactory;
import org.junit.jupiter.api.Test;
import com.powsybl.iidm.network.util.SV;
/**
*
* @author Luma Zamarre��o {@literal <zamarrenolm at aia.es>}
* @author Jos�� Antonio Marqu��s {@literal <marquesja at aia.es>}
*/
class SVTest {
@Test
void testOlfRealNetwork() {
Network network = createNodeBreakerDanglingLineNetwork();
svOlfDataToNetwork(network);
Line line = network.getLine("Line-2-2");
DanglingLine dl = network.getDanglingLine("Dl-3");
Bus bus1 = network.getBusBreakerView().getBus("S1VL1_0");
Bus bus2 = network.getBusBreakerView().getBus("S2VL1_0");
double tol = 0.00001;
SV svL1 = new SV(line.getTerminal1().getP(), line.getTerminal1().getQ(), bus1.getV(), bus1.getAngle(), TwoSides.ONE);
SV svL1other = svL1.otherSide(line);
assertEquals(line.getTerminal2().getP(), svL1other.getP(), tol);
assertEquals(line.getTerminal2().getQ(), svL1other.getQ(), tol);
assertEquals(bus2.getV(), svL1other.getU(), tol);
assertEquals(bus2.getAngle(), svL1other.getA(), tol);
SV svL2 = new SV(line.getTerminal2().getP(), line.getTerminal2().getQ(), bus2.getV(), bus2.getAngle(), TwoSides.TWO);
SV svL2other = svL2.otherSide(line);
assertEquals(line.getTerminal1().getP(), svL2other.getP(), tol);
assertEquals(line.getTerminal1().getQ(), svL2other.getQ(), tol);
assertEquals(bus1.getV(), svL2other.getU(), tol);
assertEquals(bus1.getAngle(), svL2other.getA(), tol);
assertEquals(line.getTerminal1().getP(), svL2.otherSideP(line.getR(), line.getX(), line.getG1(), line.getB1(), line.getG2(), line.getB2(), 1.0, 0.0), tol);
assertEquals(line.getTerminal1().getQ(), svL2.otherSideQ(line.getR(), line.getX(), line.getG1(), line.getB1(), line.getG2(), line.getB2(), 1.0, 0.0), tol);
assertEquals(bus1.getV(), svL2.otherSideU(line.getR(), line.getX(), line.getG1(), line.getB1(), line.getG2(), line.getB2(), 1.0, 0.0), tol);
assertEquals(bus1.getAngle(), svL2.otherSideA(line.getR(), line.getX(), line.getG1(), line.getB1(), line.getG2(), line.getB2(), 1.0, 0.0), tol);
SV svDl1 = new SV(dl.getTerminal().getP(), dl.getTerminal().getQ(), bus2.getV(), bus2.getAngle(), TwoSides.ONE);
SV svDl1other = svDl1.otherSide(dl);
assertEquals(-dl.getP0(), svDl1other.getP(), tol);
assertEquals(-dl.getQ0(), svDl1other.getQ(), tol);
assertEquals(225.1798987500, svDl1other.getU(), tol);
assertEquals(-0.4183680524, svDl1other.getA(), tol);
assertEquals(-dl.getP0(), dl.getBoundary().getP(), tol);
assertEquals(-dl.getQ0(), dl.getBoundary().getQ(), tol);
double expectedI = Math.hypot(-dl.getP0(), -dl.getQ0()) / (Math.sqrt(3.) * dl.getBoundary().getV() / 1000);
assertEquals(expectedI, dl.getBoundary().getI(), tol);
}
@Test
void testDcOlfRealNetwork() {
Network network = createNodeBreakerDanglingLineNetwork();
svDcOlfDataToNetwork(network);
Line line = network.getLine("Line-2-2");
DanglingLine dl = network.getDanglingLine("Dl-3");
Bus bus1 = network.getBusBreakerView().getBus("S1VL1_0");
Bus bus2 = network.getBusBreakerView().getBus("S2VL1_0");
double tol = 0.00001;
SV svL1 = new SV(line.getTerminal1().getP(), line.getTerminal1().getQ(), bus1.getV(), bus1.getAngle(), TwoSides.ONE);
SV svL1other = svL1.otherSide(line);
assertEquals(line.getTerminal2().getP(), svL1other.getP(), tol);
assertEquals(bus2.getAngle(), svL1other.getA(), tol);
SV svL2 = new SV(line.getTerminal2().getP(), line.getTerminal2().getQ(), bus2.getV(), bus2.getAngle(), TwoSides.TWO);
SV svL2other = svL2.otherSide(line);
assertEquals(line.getTerminal1().getP(), svL2other.getP(), tol);
assertEquals(bus1.getAngle(), svL2other.getA(), tol);
SV svDl1 = new SV(dl.getTerminal().getP(), dl.getTerminal().getQ(), bus2.getV(), bus2.getAngle(), TwoSides.ONE);
SV svDl1other = svDl1.otherSide(dl);
assertEquals(-dl.getP0(), svDl1other.getP(), tol);
assertEquals(-0.4187543391573424, svDl1other.getA(), tol);
assertEquals(-dl.getP0(), dl.getBoundary().getP(), tol);
assertEquals(-dl.getQ0(), dl.getBoundary().getQ(), tol);
assertEquals(Double.NaN, dl.getBoundary().getI());
}
private static void svOlfDataToNetwork(Network network) {
Line line = network.getLine("Line-2-2");
DanglingLine dl = network.getDanglingLine("Dl-3");
Bus bus1 = network.getBusBreakerView().getBus("S1VL1_0");
Bus bus2 = network.getBusBreakerView().getBus("S2VL1_0");
// Voltages at the buses
bus1.setV(225.0).setAngle(0.0);
bus2.setV(225.2726820000).setAngle(-0.2603514491);
line.getTerminal1().setP(115.003788).setQ(-56.302621);
line.getTerminal2().setP(-115.000986).setQ(6.176675);
dl.getTerminal().setP(70.000986).setQ(-15.176675);
}
private static void svDcOlfDataToNetwork(Network network) {
Line line = network.getLine("Line-2-2");
DanglingLine dl = network.getDanglingLine("Dl-3");
Bus bus1 = network.getBusBreakerView().getBus("S1VL1_0");
Bus bus2 = network.getBusBreakerView().getBus("S2VL1_0");
// Voltages at the buses
bus1.setAngle(0.0);
bus2.setAngle(-0.26030675136807774);
line.getTerminal1().setP(115.0);
line.getTerminal2().setP(-115.0);
dl.getTerminal().setP(70.0);
}
private static Network createNodeBreakerDanglingLineNetwork() {
return createNodeBreakerDanglingLineNetwork(NetworkFactory.findDefault());
}
private static Network createNodeBreakerDanglingLineNetwork(NetworkFactory networkFactory) {
Network network = networkFactory.createNetwork("twoBusesWithLineAndDanglingLine", "test");
double vn = 225.0;
// First substation
Substation s1 = network.newSubstation()
.setId("S1")
.add();
VoltageLevel s1vl1 = s1.newVoltageLevel()
.setId("S1VL1")
.setNominalV(vn)
.setLowVoltageLimit(vn * 0.9)
.setHighVoltageLimit(vn * 1.1)
.setTopologyKind(TopologyKind.NODE_BREAKER)
.add();
createBusbarSection(s1vl1, "S1VL1_BBS0A", "S1VL1_BBS0A", 0);
createInternalConnection(s1vl1, 0, 1);
createInternalConnection(s1vl1, 0, 2);
createGenerator(s1vl1, "S1VL1-Generator", vn, 80.0, 10.0, 1);
// Second substation
Substation s2 = network.newSubstation()
.setId("S2")
.add();
VoltageLevel s2vl1 = s2.newVoltageLevel()
.setId("S2VL1")
.setNominalV(vn)
.setLowVoltageLimit(vn * 0.9)
.setHighVoltageLimit(vn * 1.1)
.setTopologyKind(TopologyKind.NODE_BREAKER)
.add();
createBusbarSection(s2vl1, "S2VL1_BBS0", "S2VL1_BBS0", 0);
createInternalConnection(s2vl1, 0, 1);
createInternalConnection(s2vl1, 0, 2);
createInternalConnection(s2vl1, 0, 3);
createLoad(s2vl1, "S2VL1-Load", 45.0, 9.0, 1);
createDanglingLine(network, "S2VL1", "Dl-3", 70.0, 10.0, "ucteNode", 3);
// Line between both substations
createLine(network, "S1VL1", "S2VL1", "Line-2-2", 2, 2);
return network;
}
private static void createBusbarSection(VoltageLevel vl, String id, String name, int node) {
vl.getNodeBreakerView().newBusbarSection()
.setId(id)
.setName(name)
.setNode(node)
.add();
}
private static void createInternalConnection(VoltageLevel vl, int node1, int node2) {
vl.getNodeBreakerView().newInternalConnection()
.setNode1(node1)
.setNode2(node2)
.add();
}
private static void createLoad(VoltageLevel vl, String id, double p, double q, int node) {
Load load = vl.newLoad()
.setId(id)
.setLoadType(LoadType.UNDEFINED)
.setP0(p)
.setQ0(q)
.setNode(node)
.add();
load.getTerminal().setP(p).setQ(q);
}
private static void createGenerator(VoltageLevel vl, String id, double targetV, double p, double q, int node) {
Generator generator = vl.newGenerator()
.setId(id)
.setEnergySource(EnergySource.HYDRO)
.setMinP(-500.0)
.setMaxP(500.0)
.setVoltageRegulatorOn(true)
.setTargetP(p)
.setTargetV(targetV)
.setTargetQ(q)
.setNode(node)
.add();
generator.newMinMaxReactiveLimits()
.setMinQ(-500.0)
.setMaxQ(500.0);
generator.getTerminal().setP(-p).setQ(-q);
}
private static void createLine(Network network, String vl1id, String vl2id, String id, int node1, int node2) {
network.newLine()
.setId(id)
.setR(0.01)
.setX(2.0)
.setG1(0.0)
.setB1(0.0005)
.setG2(0.0)
.setB2(0.0005)
.setNode1(node1)
.setVoltageLevel1(vl1id)
.setNode2(node2)
.setVoltageLevel2(vl2id)
.add();
}
private static void createDanglingLine(Network network, String vlId, String id, double p0, double q0, String ucteCode, int node) {
network.getVoltageLevel(vlId).newDanglingLine()
.setId(id)
.setR(0.01)
.setX(2.0)
.setG(0.0)
.setB(0.0005)
.setP0(p0)
.setQ0(q0)
.setPairingKey(ucteCode)
.setNode(node)
.setEnsureIdUnicity(false)
.add();
}
@Test
void testWithGeneration() {
double tol = 0.001;
Network network = DanglingLineNetworkFactory.createWithGeneration();
DanglingLine danglingLine = network.getDanglingLine("DL");
assertTrue(Double.isNaN(danglingLine.getBoundary().getP())); // there is no good solution here.
// we run an DC load flow and fill state variable
danglingLine.getTerminal().setP(-298.937);
danglingLine.getTerminal().setQ(Double.NaN);
danglingLine.getTerminal().getBusView().getBus().setAngle(0.0);
danglingLine.getTerminal().getBusView().getBus().setV(Double.NaN);
assertEquals(298.937, danglingLine.getBoundary().getP(), tol);
assertEquals(1.712783, danglingLine.getBoundary().getAngle(), tol);
// we run an AC load flow
danglingLine.getTerminal().setP(-298.937);
danglingLine.getTerminal().setQ(-7.413);
danglingLine.getTerminal().getBusView().getBus().setAngle(0.0);
danglingLine.getTerminal().getBusView().getBus().setV(100.0);
assertEquals(389.953, danglingLine.getBoundary().getP(), tol);
assertEquals(16.314, danglingLine.getBoundary().getQ(), tol);
assertEquals(130.087, danglingLine.getBoundary().getV(), tol);
assertEquals(0.999, danglingLine.getBoundary().getAngle(), tol);
}
@Test
void testWithZeroImpedanceDanglingLineWithGeneration() {
double tol = 0.001;
Network network = DanglingLineNetworkFactory.createWithGeneration();
DanglingLine danglingLine = network.getDanglingLine("DL");
danglingLine.setR(0.0).setX(0.0);
danglingLine.getTerminal().setP(-298.937);
danglingLine.getTerminal().setQ(-7.413);
danglingLine.getTerminal().getBusView().getBus().setAngle(0.0);
danglingLine.getTerminal().getBusView().getBus().setV(100.0);
assertEquals(298.937, danglingLine.getBoundary().getP(), tol);
assertEquals(7.413, danglingLine.getBoundary().getQ(), tol);
assertEquals(1726.444, danglingLine.getBoundary().getI(), tol);
assertEquals(100.0, danglingLine.getBoundary().getV(), tol);
assertEquals(0.0, danglingLine.getBoundary().getAngle(), tol);
}
@Test
void testWithZeroImpedanceDanglingLineWithoutGeneration() {
double tol = 0.001;
Network network = DanglingLineNetworkFactory.create();
DanglingLine danglingLine = network.getDanglingLine("DL");
danglingLine.setR(0.0).setX(0.0);
danglingLine.getTerminal().setP(50.0);
danglingLine.getTerminal().setQ(30.0);
danglingLine.getTerminal().getBusView().getBus().setAngle(0.0);
danglingLine.getTerminal().getBusView().getBus().setV(100.0);
assertEquals(-50.0, danglingLine.getBoundary().getP(), tol);
assertEquals(-30.0, danglingLine.getBoundary().getQ(), tol);
assertEquals(336.650, danglingLine.getBoundary().getI(), tol);
assertEquals(100.0, danglingLine.getBoundary().getV(), tol);
assertEquals(0.0, danglingLine.getBoundary().getAngle(), tol);
}
@Test
void testWithZeroImpedanceDanglingLineWithoutGenerationWithNaNV() {
double tol = 0.001;
Network network = DanglingLineNetworkFactory.create();
DanglingLine danglingLine = network.getDanglingLine("DL");
danglingLine.setR(0.0).setX(0.0);
danglingLine.getTerminal().setP(50.0);
danglingLine.getTerminal().setQ(30.0);
danglingLine.getTerminal().getBusView().getBus().setAngle(0.5);
danglingLine.getTerminal().getBusView().getBus().setV(Double.NaN);
assertEquals(-50.0, danglingLine.getBoundary().getP(), tol);
assertEquals(-30.0, danglingLine.getBoundary().getQ(), tol);
assertEquals(Double.NaN, danglingLine.getBoundary().getI());
assertEquals(Double.NaN, danglingLine.getBoundary().getV());
assertEquals(Double.NaN, danglingLine.getBoundary().getAngle());
}
}