From 8fab54fdb129dff7044d8021fe67ca37d6d09340 Mon Sep 17 00:00:00 2001 From: Nipuna Fernando Date: Fri, 13 Oct 2023 18:11:47 +0530 Subject: [PATCH 01/14] Fix invalid hashing in TupleValueImpl --- .../internal/values/TupleValueImpl.java | 8 ++++++ .../types/table/TableKeyFieldValueTest.java | 3 +- .../table/table_key_field_value_test.bal | 28 +++++++++++++++++++ 3 files changed, 38 insertions(+), 1 deletion(-) diff --git a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java index 1283cf5a11cc..88af4baee77b 100644 --- a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java +++ b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java @@ -43,6 +43,7 @@ import java.util.Arrays; import java.util.List; import java.util.Map; +import java.util.Objects; import java.util.StringJoiner; import java.util.stream.IntStream; @@ -92,6 +93,13 @@ public boolean equals(Object o) { Arrays.equals(refValues, that.refValues); } + @Override + public int hashCode() { + int result = Objects.hash(type, tupleType); + result = 31 * result + Arrays.hashCode(refValues); + return result; + } + public TupleValueImpl(Object[] values, TupleType type) { this.refValues = values; this.type = this.tupleType = type; diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java index 735b6d4b5501..a7af076c9ec0 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java @@ -72,7 +72,8 @@ public Object[] dataToTestTableKeyFieldValue() { "testGroupExprAsKeyValue", "testKeyCollision", "testRegExpAsKeyValue", - "testKeyCollisionWithStringAndRegExpAsKeyValues" + "testKeyCollisionWithStringAndRegExpAsKeyValues", + "testTupleAsKeyValue" }; } diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal b/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal index cf791af60083..97970c02e1e1 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal @@ -583,6 +583,34 @@ function testKeyCollisionWithStringAndRegExpAsKeyValues() { assertEqual(tbl, tbl5); } +type Employee record {| + readonly string orgId; + readonly string appId; + string company; +|}; + +function testTupleAsKeyValue() { + table key(orgId, appId) tbl = table [ + {orgId: "1", appId: "1", company: "xxx"} + ]; + + tbl.put({ + orgId: "1", + appId: "1", + company: "yyy" + }); + + table tbl1 = from Employee r in tbl + where r.orgId == "1" && r.appId == "1" + select r; + + table tbl2 = table [ + {orgId: "1", appId: "1", company: "yyy"} + ]; + + assertEqual(tbl1, tbl2); +} + function assertEqual(any expected, any actual) { if expected is anydata && actual is anydata && expected == actual { return; From bf3c55eadbea5acb161ea9dd5fc402ae0e21b3c4 Mon Sep 17 00:00:00 2001 From: Nipuna Fernando Date: Mon, 16 Oct 2023 15:14:57 +0530 Subject: [PATCH 02/14] Remove duplicate keys in TableValueImpl --- .../internal/values/TableValueImpl.java | 24 ++++++++++--------- .../internal/values/TupleValueImpl.java | 8 ------- 2 files changed, 13 insertions(+), 19 deletions(-) diff --git a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java index ed1fe926fb60..2ac6b6cc8a56 100644 --- a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java +++ b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java @@ -46,6 +46,7 @@ import io.ballerina.runtime.internal.types.BTupleType; import io.ballerina.runtime.internal.types.BTypeReferenceType; import io.ballerina.runtime.internal.types.BUnionType; +import org.apache.commons.lang3.tuple.Pair; import java.util.AbstractMap; import java.util.ArrayList; @@ -94,9 +95,9 @@ public class TableValueImpl implements TableValue { private long maxIntKey = 0; //These are required to achieve the iterator behavior - private LinkedHashMap indexToKeyMap; + private LinkedHashMap indexToKeyMap; private LinkedHashMap keyToIndexMap; - private LinkedHashMap keyValues; + private LinkedHashMap> keyValues; private long noOfAddedEntries = 0; private boolean nextKeySupported; @@ -478,9 +479,11 @@ private class TableIterator implements IteratorValue { @Override public Object next() { - K key = (K) indexToKeyMap.get(cursor); - if (key != null) { - V value = (V) keyValues.get(key); + Long hash = indexToKeyMap.get(cursor); + if (hash != null) { + Pair keyValuePair = (Pair) keyValues.get(hash); + K key = keyValuePair.getKey(); + V value = keyValuePair.getValue(); List types = new ArrayList<>(); types.add(TypeChecker.getType(key)); @@ -534,7 +537,7 @@ public V putData(V data) { entries.put(hash, entryList); updateIndexKeyMappings((K) data, hash); values.put(hash, newData); - keyValues.put((K) data, data); + keyValues.put(hash, Pair.of((K) data, data)); return data; } @@ -588,7 +591,7 @@ public void addData(V data) { extEntries.add(entry); List extValues = values.get(hash); extValues.add(data); - keyValues.put(key, data); + keyValues.put(hash, Pair.of(key, data)); updateIndexKeyMappings(key, hash); return; } @@ -630,14 +633,13 @@ public V putData(K key, V data) { } private V putData(K key, V value, List data, Map.Entry entry, Long hash) { - List> entryList = new ArrayList<>(); entryList.add(entry); entries.put(hash, entryList); keys.put(hash, key); updateIndexKeyMappings(key, hash); values.put(hash, data); - keyValues.put(key, value); + keyValues.put(hash, Pair.of(key, value)); return data.get(0); } @@ -655,8 +657,8 @@ public V putData(V data) { } public V remove(K key) { - keyValues.remove(key); Long hash = TableUtils.hash(key, null); + keyValues.remove(hash); List> entryList = entries.get(hash); if (entryList != null && entryList.size() > 1) { for (Map.Entry entry: entryList) { @@ -751,7 +753,7 @@ public K wrapKey(MapValue data) { private void updateIndexKeyMappings(K key, Long hash) { if (!keyToIndexMap.containsKey(hash)) { keyToIndexMap.put(hash, noOfAddedEntries); - indexToKeyMap.put(noOfAddedEntries, key); + indexToKeyMap.put(noOfAddedEntries, hash); noOfAddedEntries++; } } diff --git a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java index 88af4baee77b..1283cf5a11cc 100644 --- a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java +++ b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TupleValueImpl.java @@ -43,7 +43,6 @@ import java.util.Arrays; import java.util.List; import java.util.Map; -import java.util.Objects; import java.util.StringJoiner; import java.util.stream.IntStream; @@ -93,13 +92,6 @@ public boolean equals(Object o) { Arrays.equals(refValues, that.refValues); } - @Override - public int hashCode() { - int result = Objects.hash(type, tupleType); - result = 31 * result + Arrays.hashCode(refValues); - return result; - } - public TupleValueImpl(Object[] values, TupleType type) { this.refValues = values; this.type = this.tupleType = type; From 8baf12c068f7f6de2d9a038f5ef3c32903a90b2f Mon Sep 17 00:00:00 2001 From: Nipuna Fernando Date: Tue, 17 Oct 2023 11:24:27 +0530 Subject: [PATCH 03/14] Add single key-ed test --- .../types/table/TableKeyFieldValueTest.java | 3 ++- .../table/table_key_field_value_test.bal | 22 +++++++++++++++++++ 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java index a7af076c9ec0..cb06d58044d9 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java @@ -73,7 +73,8 @@ public Object[] dataToTestTableKeyFieldValue() { "testKeyCollision", "testRegExpAsKeyValue", "testKeyCollisionWithStringAndRegExpAsKeyValues", - "testTupleAsKeyValue" + "testTupleAsKeyValue", + "testStringAsKeyValue" }; } diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal b/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal index 97970c02e1e1..01a2fef2cbee 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal @@ -611,6 +611,28 @@ function testTupleAsKeyValue() { assertEqual(tbl1, tbl2); } +function testStringAsKeyValue() { + table key(orgId) tbl = table [ + {orgId: "1", appId: "1", company: "xxx"} + ]; + + tbl.put({ + orgId: "1", + appId: "1", + company: "yyy" + }); + + table tbl1 = from Employee r in tbl + where r.orgId == "1" && r.appId == "1" + select r; + + table tbl2 = table [ + {orgId: "1", appId: "1", company: "yyy"} + ]; + + assertEqual(tbl1, tbl2); +} + function assertEqual(any expected, any actual) { if expected is anydata && actual is anydata && expected == actual { return; From e2aa923a95b72a1ab5b8887ddff600099761266b Mon Sep 17 00:00:00 2001 From: Nipuna Fernando Date: Tue, 17 Oct 2023 14:07:57 +0530 Subject: [PATCH 04/14] Implement a Pair structure for TableValueImpl --- .../internal/values/TableValueImpl.java | 33 +++++++++++++++---- 1 file changed, 27 insertions(+), 6 deletions(-) diff --git a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java index 2ac6b6cc8a56..ad12cdea86bb 100644 --- a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java +++ b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/TableValueImpl.java @@ -46,7 +46,6 @@ import io.ballerina.runtime.internal.types.BTupleType; import io.ballerina.runtime.internal.types.BTypeReferenceType; import io.ballerina.runtime.internal.types.BUnionType; -import org.apache.commons.lang3.tuple.Pair; import java.util.AbstractMap; import java.util.ArrayList; @@ -97,7 +96,7 @@ public class TableValueImpl implements TableValue { //These are required to achieve the iterator behavior private LinkedHashMap indexToKeyMap; private LinkedHashMap keyToIndexMap; - private LinkedHashMap> keyValues; + private LinkedHashMap> keyValues; private long noOfAddedEntries = 0; private boolean nextKeySupported; @@ -481,7 +480,7 @@ private class TableIterator implements IteratorValue { public Object next() { Long hash = indexToKeyMap.get(cursor); if (hash != null) { - Pair keyValuePair = (Pair) keyValues.get(hash); + KeyValuePair keyValuePair = (KeyValuePair) keyValues.get(hash); K key = keyValuePair.getKey(); V value = keyValuePair.getValue(); @@ -537,7 +536,7 @@ public V putData(V data) { entries.put(hash, entryList); updateIndexKeyMappings((K) data, hash); values.put(hash, newData); - keyValues.put(hash, Pair.of((K) data, data)); + keyValues.put(hash, KeyValuePair.of((K) data, data)); return data; } @@ -591,7 +590,7 @@ public void addData(V data) { extEntries.add(entry); List extValues = values.get(hash); extValues.add(data); - keyValues.put(hash, Pair.of(key, data)); + keyValues.put(hash, KeyValuePair.of(key, data)); updateIndexKeyMappings(key, hash); return; } @@ -639,7 +638,7 @@ private V putData(K key, V value, List data, Map.Entry entry, Long hash keys.put(hash, key); updateIndexKeyMappings(key, hash); values.put(hash, data); - keyValues.put(hash, Pair.of(key, value)); + keyValues.put(hash, KeyValuePair.of(key, value)); return data.get(0); } @@ -749,6 +748,28 @@ public K wrapKey(MapValue data) { } } + private static final class KeyValuePair { + private K key; + private V value; + + public KeyValuePair(K key, V value) { + this.key = key; + this.value = value; + } + + public static KeyValuePair of(K key, V value) { + return new KeyValuePair<>(key, value); + } + + public K getKey() { + return key; + } + + public V getValue() { + return value; + } + } + // This method updates the indexes and the order required by the iterators private void updateIndexKeyMappings(K key, Long hash) { if (!keyToIndexMap.containsKey(hash)) { From 916ba70e7eeb18cf8351bee77cba3504dea1c7fc Mon Sep 17 00:00:00 2001 From: Mohamed Ishad Date: Wed, 18 Oct 2023 15:12:52 +0530 Subject: [PATCH 05/14] Correct help text for command `bal help` --- misc/formatter/modules/formatter-cli/README.md | 16 ++++++++-------- .../ballerinalang/formatter/cli/Messages.java | 12 ++++++------ 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/misc/formatter/modules/formatter-cli/README.md b/misc/formatter/modules/formatter-cli/README.md index e4a7e0524673..bce6494f5428 100644 --- a/misc/formatter/modules/formatter-cli/README.md +++ b/misc/formatter/modules/formatter-cli/README.md @@ -8,11 +8,11 @@ according to the default [Ballerina style guide](https://github.com/ballerina-pl The Ballerina format command can be used to format Ballerina source files. ```sh -$ ballerina format --help +$ bal format --help Prints the help guide for the Ballerina format tool. Usage: -ballerina format [ | ] [-d | --dry-run] +bal format [ | ] [-d | --dry-run] ballerinaFile: Path of a single Ballerina source file, which needs to be formatted. moduleName: @@ -29,26 +29,26 @@ Flags: **Example 1:** Formats all the Ballerina source files in a Ballerina project. ```sh -$ ballerina format +$ bal format ``` This command should be executed from the root of the Ballerina project. **Example 2:** Formats all the Ballerina source files in a Ballerina module. ```sh -$ ballerina format module1 +$ bal format module1 ``` This command should be executed from the root of the Ballerina project. **Example 3:** Formats a single Ballerina source file. ```sh -$ ballerina format hello.bal +$ bal format hello.bal ``` **Example 4:** Performs a dry run of the formatter to see which files will be formatted if executed. ```sh -$ ballerina format -d -$ ballerina format module1 -d -$ ballerina format hello.bal -d +$ bal format -d +$ bal format module1 -d +$ bal format hello.bal -d ``` diff --git a/misc/formatter/modules/formatter-cli/src/main/java/org/ballerinalang/formatter/cli/Messages.java b/misc/formatter/modules/formatter-cli/src/main/java/org/ballerinalang/formatter/cli/Messages.java index 0a75c6b7d4fd..44540cd363aa 100644 --- a/misc/formatter/modules/formatter-cli/src/main/java/org/ballerinalang/formatter/cli/Messages.java +++ b/misc/formatter/modules/formatter-cli/src/main/java/org/ballerinalang/formatter/cli/Messages.java @@ -24,15 +24,15 @@ public class Messages { private static final String ARGUMENT_ERROR = "too many arguments." + System.lineSeparator() + "usage: only one argument, either a ballerina file name or a module " + "name, can be applied at a time with or without the option." + System.lineSeparator() - + "i.e: ballerina format [ballerinaFile | ModuleName] [-d | --dry-run]" + System.lineSeparator() - + System.lineSeparator() + "run `ballerina format -h` for more details."; + + "i.e: bal format [ballerinaFile | ModuleName] [-d | --dry-run]" + System.lineSeparator() + + System.lineSeparator() + "run `bal format -h` for more details."; private static final String SUCCESS_MESSAGE = "format successful."; private static final String NOT_BALLERINA_PROJECT = "not a valid Ballerina project." + System.lineSeparator() - + "usage: ballerina format should be run inside a ballerina project or pass in a ballerina file." - + System.lineSeparator() + "i.e. `ballerina format `" - + System.lineSeparator() + System.lineSeparator() + "run `ballerina format -h` for more details"; + + "usage: bal format should be run inside a ballerina project or pass in a ballerina file." + + System.lineSeparator() + "i.e. `bal format `" + + System.lineSeparator() + System.lineSeparator() + "run `bal format -h` for more details"; private static final String NO_MODULE_FOUND = "couldn't find an existing module by the name: "; @@ -42,7 +42,7 @@ public class Messages { private static final String NOT_BALLERINA_FILE = "not a valid ballerina source file." + System.lineSeparator() + "usage: ballerina source files should have the file extension as `.bal`." + System.lineSeparator() - + "i.e. `ballerina format hello.bal`"; + + "i.e. `bal format hello.bal`"; private static final String NO_BALLERINA_FILE_OR_MODULE = "couldn't find an existing ballerina file or " + "module by the name: "; From ead12e02d89b1d37d830c9b1cf88d20b3b317ade Mon Sep 17 00:00:00 2001 From: hindujaB Date: Thu, 19 Oct 2023 13:02:49 +0530 Subject: [PATCH 06/14] Fix xml serializer setting default NS --- .../io/ballerina/runtime/internal/BallerinaXmlSerializer.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/BallerinaXmlSerializer.java b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/BallerinaXmlSerializer.java index f47bf9dcbfbf..c836f4929cbb 100644 --- a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/BallerinaXmlSerializer.java +++ b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/BallerinaXmlSerializer.java @@ -287,7 +287,7 @@ private String getXmlNsUriPrefix(Map nsPrefixMap, String uri) { } private void writeAttributes(HashSet curNSSet, Map attributeMap) throws XMLStreamException { - String defaultNS = xmlStreamWriter.getNamespaceContext().getNamespaceURI(XMLNS); + String defaultNS = xmlStreamWriter.getNamespaceContext().getNamespaceURI(""); for (Map.Entry attributeEntry : attributeMap.entrySet()) { String key = attributeEntry.getKey(); int closingCurlyPos = key.lastIndexOf('}'); From 54dc9d6f8fbaf830b4697041e24380e97a7656c1 Mon Sep 17 00:00:00 2001 From: hindujaB Date: Thu, 19 Oct 2023 13:03:19 +0530 Subject: [PATCH 07/14] Add xml NS tests --- .../xml/XMLLiteralWithNamespacesTest.java | 23 +++++++++++-------- .../xml/xml-literals-with-namespaces.bal | 20 +++++++++++++++- 2 files changed, 33 insertions(+), 10 deletions(-) diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLLiteralWithNamespacesTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLLiteralWithNamespacesTest.java index 19c662608953..3ba39254c60b 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLLiteralWithNamespacesTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLLiteralWithNamespacesTest.java @@ -31,6 +31,7 @@ import org.testng.Assert; import org.testng.annotations.AfterClass; import org.testng.annotations.BeforeClass; +import org.testng.annotations.DataProvider; import org.testng.annotations.Test; import java.io.ByteArrayOutputStream; @@ -178,7 +179,7 @@ public void testObjectLevelXML() { public void xmlWithDefaultNamespaceToString() { Object returns = BRunUtil.invoke(literalWithNamespacesResult, "XMLWithDefaultNamespaceToString"); Assert.assertEquals(returns.toString(), - "\n" + + "\n" + " \n" + " \n" + " \n" + @@ -199,11 +200,6 @@ public void testXMLSerialize() { "hello"); } - @Test - public void testXmlLiteralUsingXmlNamespacePrefix() { - BRunUtil.invoke(literalWithNamespacesResult, "testXmlLiteralUsingXmlNamespacePrefix"); - } - @Test public void testXMLToString() { BXml xml = XmlFactory.parse("" + @@ -211,9 +207,18 @@ public void testXMLToString() { Assert.assertEquals(xml.toString(), "Example"); } - @Test - public void testXmlInterpolationWithQuery() { - BRunUtil.invoke(literalWithNamespacesResult, "testXmlInterpolationWithQuery"); + @Test (dataProvider = "xmlValueFunctions") + public void testXmlStrings(String functionName) { + BRunUtil.invoke(literalWithNamespacesResult, functionName); + } + + @DataProvider(name = "xmlValueFunctions") + private String[] xmlValueFunctions() { + return new String[]{ + "testXmlLiteralUsingXmlNamespacePrefix", + "testXmlInterpolationWithQuery", + "testAddAttributeToDefaultNS" + }; } @AfterClass diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal b/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal index 96cdb12d4820..8b41a4754be5 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal @@ -147,7 +147,7 @@ function getXML() returns xml { } function XMLWithDefaultNamespaceToString() returns string { - xml x = xml ` + xml x = xml ` @@ -294,3 +294,21 @@ function testXmlInterpolationWithQuery() returns error? { } } } + +function testAddAttributeToDefaultNS() { + xml x1 = xml ``; + var xAttr = let var x2 = <'xml:Element>x1 in x2.getAttributes(); + //adding attribute with default namespace + xAttr["{http://sample.com/wso2/c1}foo1"] = "bar1"; + string s = x1.toString(); + string expectedStr = ""; + if (s != expectedStr) { + panic error("Assertion error", expected = expectedStr, found=s); + } + s = xAttr.toString(); + expectedStr = "{\"{http://www.w3.org/2000/xmlns/}xmlns\":\"http://sample.com/wso2/c1\"," + + "\"{http://www.w3.org/2000/xmlns/}ns3\":\"http://sample.com/wso2/f\",\"{http://sample.com/wso2/c1}foo1\":\"bar1\"}"; + if (s != expectedStr) { + panic error("Assertion error", expected = expectedStr, found=s); + } +} \ No newline at end of file From f9d450dbabc9e75fec17ae801af1a43153333f34 Mon Sep 17 00:00:00 2001 From: hindujaB Date: Sat, 21 Oct 2023 11:49:52 +0530 Subject: [PATCH 08/14] Address suggestions --- .../test/types/xml/XMLAttributesTest.java | 6 +- .../xml/xml-literals-with-namespaces.bal | 70 ++++++------------- 2 files changed, 23 insertions(+), 53 deletions(-) diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLAttributesTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLAttributesTest.java index b17b8efd1c1b..b990c23dcc15 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLAttributesTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLAttributesTest.java @@ -72,8 +72,7 @@ public void testAddAttributeWithEmptyNamespace() { "xmlns:ns3=\"http://sample.com/wso2/f\" foo1=\"bar\"/>"); } - // ToDo: enable after fixing #40373 - @Test(enabled = false) + @Test() public void testAddNamespaceAsAttribute1() { BArray returns = (BArray) BRunUtil.invoke(xmlAttrProgFile, "testAddNamespaceAsAttribute"); Assert.assertTrue(returns.get(0) instanceof BXml); @@ -132,8 +131,7 @@ public void testAddAttributeWithQName_3() { "xmlns:ns5=\"http://sample.com/wso2/f/\" ns5:diff=\"yes\" ns5:foo1=\"bar1\"/>"); } - // ToDo: enable after fixing #40373 - @Test(enabled = false) + @Test() public void testAddAttributeWithQName_5() { Object returns = BRunUtil.invoke(xmlAttrProgFile, "testAddAttributeWithDiffQName_5"); Assert.assertTrue(returns instanceof BXml); diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal b/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal index 8b41a4754be5..e79c1010a186 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/types/xml/xml-literals-with-namespaces.bal @@ -1,3 +1,5 @@ +import ballerina/test; + xmlns "http://ballerina.com/b" as ns1; function testElementLiteralWithNamespaces() returns [xml, xml] { @@ -162,9 +164,7 @@ function testXmlLiteralUsingXmlNamespacePrefix() { xml x1 = xml ``; string s = x1.toString(); string expectedStr = ""; - if (s != expectedStr) { - panic error("Assertion error", expected = expectedStr, found=s); - } + test:assertEquals(s, expectedStr, "XML literal with xml namespace prefix failed"); } xmlns "http://www.so2w.org" as globalNS; @@ -177,9 +177,7 @@ function testXmlInterpolationWithQuery() returns error? { xml x2 = x1/[0]; string s1 = x2.toString(); string expectedStr1 = "1"; - if (s1 != expectedStr1) { - panic error("Assertion error", expected = expectedStr1, found = s1); - } + test:assertEquals(s1, expectedStr1, "XML interpolation with query failed"); xmlns "http://www.so2w.org" as localNS; xml x3 = xml ` @@ -189,17 +187,13 @@ function testXmlInterpolationWithQuery() returns error? { xml x4 = x3/[0]/; string s2 = x4.toString(); string expectedStr2 = "1"; - if (s2 != expectedStr2) { - panic error("Assertion error", expected = expectedStr2, found = s2); - } + test:assertEquals(s2, expectedStr2, "XML interpolation with query failed"); xml x5 = from int i in [1] select xml `${i}`; string s3 = x5.toString(); string expectedStr3 = "1"; - if (s3 != expectedStr3) { - panic error("Assertion error", expected = expectedStr3, found = s3); - } + test:assertEquals(s3, expectedStr3, "XML interpolation with query failed"); xml x6 = xml ` ${from int i in 1 ... 3 @@ -208,9 +202,7 @@ function testXmlInterpolationWithQuery() returns error? { xml x7 = x6/[0]/; string s4 = x7.toString(); string expectedStr4 = "1"; - if (s4 != expectedStr4) { - panic error("Assertion error", expected = expectedStr4, found = s4); - } + test:assertEquals(s4, expectedStr4, "XML interpolation with query failed"); xml x8 = xml ``; from int i in [1] @@ -218,9 +210,7 @@ function testXmlInterpolationWithQuery() returns error? { x8 = xml `${i}`; }; string s5 = x8.toString(); - if (s5 != expectedStr3) { - panic error("Assertion error", expected = expectedStr3, found = s5); - } + test:assertEquals(s5, expectedStr3, "XML interpolation with query failed"); xml x9 = xml ``; from int i in [1] @@ -231,26 +221,20 @@ function testXmlInterpolationWithQuery() returns error? { }; }; string s6 = x9.toString(); - if (s6 != expectedStr3) { - panic error("Assertion error", expected = expectedStr3, found = s6); - } + test:assertEquals(s6, expectedStr3, "XML interpolation with query failed"); xml x10 = from int i in [1] let xml y = xml `${i}` select xml `${y}`; string s7 = x10.toString(); string expectedStr5 = "1"; - if (s7 != expectedStr5) { - panic error("Assertion error", expected = expectedStr3, found = s7); - } + test:assertEquals(s7, expectedStr5, "XML interpolation with query failed"); xml x11 = from xml x in (from int j in [1] select xml `${j}`) select xml `${x}`; string s8 = x11.toString(); - if (s8 != expectedStr5) { - panic error("Assertion error", expected = expectedStr3, found = s7); - } + test:assertEquals(s8, expectedStr5, "XML interpolation with query failed"); xml x12 = from int i in [1] join int j in [1] @@ -259,18 +243,14 @@ function testXmlInterpolationWithQuery() returns error? { select xml `${i}`; string s9 = x12.toString(); string expectedStr6 = "1"; - if (s9 != expectedStr6) { - panic error("Assertion error", expected = expectedStr3, found = s7); - } + test:assertEquals(s9, expectedStr6, "XML interpolation with query failed"); xml expectedXml = xml `1`; xml x13 = from int i in [1] where xml `${i}` == expectedXml select xml `${expectedXml}`; string s10 = x13.toString(); - if (s10 != expectedStr5) { - panic error("Assertion error", expected = expectedStr5, found = s10); - } + test:assertEquals(s10, expectedStr5, "XML interpolation with query failed"); do { xmlns "http://www.so2w1.org" as doNS; @@ -278,9 +258,7 @@ function testXmlInterpolationWithQuery() returns error? { select xml `${i}`; string s11 = x14.toString(); string expectedStr7 = "1"; - if (s11 != expectedStr7) { - panic error("Assertion error", expected = expectedStr7, found = s11); - } + test:assertEquals(s11, expectedStr7, "XML interpolation with query failed"); } do { @@ -289,9 +267,7 @@ function testXmlInterpolationWithQuery() returns error? { select xml `${i}`; string s12 = x15.toString(); string expectedStr8 = "1"; - if (s12 != expectedStr8) { - panic error("Assertion error", expected = expectedStr8, found = s12); - } + test:assertEquals(s12, expectedStr8, "XML interpolation with query failed"); } } @@ -301,14 +277,10 @@ function testAddAttributeToDefaultNS() { //adding attribute with default namespace xAttr["{http://sample.com/wso2/c1}foo1"] = "bar1"; string s = x1.toString(); - string expectedStr = ""; - if (s != expectedStr) { - panic error("Assertion error", expected = expectedStr, found=s); - } + string expectedStr = string ``; + test:assertEquals(s, expectedStr, "XML add attribute with default namespace failed"); + s = xAttr.toString(); - expectedStr = "{\"{http://www.w3.org/2000/xmlns/}xmlns\":\"http://sample.com/wso2/c1\"," + - "\"{http://www.w3.org/2000/xmlns/}ns3\":\"http://sample.com/wso2/f\",\"{http://sample.com/wso2/c1}foo1\":\"bar1\"}"; - if (s != expectedStr) { - panic error("Assertion error", expected = expectedStr, found=s); - } -} \ No newline at end of file + expectedStr = string `{"{http://www.w3.org/2000/xmlns/}xmlns":"http://sample.com/wso2/c1","{http://www.w3.org/2000/xmlns/}ns3":"http://sample.com/wso2/f","{http://sample.com/wso2/c1}foo1":"bar1"}`; + test:assertEquals(s, expectedStr, "XML add attribute with default namespace failed"); +} From 1b0a0f35ab961fd457327c48aebdd58db60474d9 Mon Sep 17 00:00:00 2001 From: hindujaB Date: Mon, 23 Oct 2023 11:19:51 +0530 Subject: [PATCH 09/14] Fix CCE for query starting with whitespace --- .../runtime/internal/values/XmlItem.java | 6 +-- .../test/query/XMLQueryExpressionTest.java | 5 ++ .../test-src/query/xml-query-expression.bal | 46 +++++++++++++++++++ 3 files changed, 54 insertions(+), 3 deletions(-) diff --git a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/XmlItem.java b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/XmlItem.java index 842256465bd4..ab15068c0347 100644 --- a/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/XmlItem.java +++ b/bvm/ballerina-runtime/src/main/java/io/ballerina/runtime/internal/values/XmlItem.java @@ -382,9 +382,9 @@ private BError createXMLCycleError() { } private void mergeAdjoiningTextNodesIntoList(List leftList, List appendingList) { - XmlPi lastChild = (XmlPi) leftList.get(leftList.size() - 1); - String firstChildContent = ((XmlPi) appendingList.get(0)).getData(); - String mergedTextContent = lastChild.getData() + firstChildContent; + XmlText lastChild = (XmlText) leftList.get(leftList.size() - 1); + String firstChildContent = appendingList.get(0).getTextValue(); + String mergedTextContent = lastChild.getTextValue() + firstChildContent; XmlText text = new XmlText(mergedTextContent); leftList.set(leftList.size() - 1, text); for (int i = 1; i < appendingList.size(); i++) { diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java index 39307ff0c501..a7d373391384 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java @@ -522,6 +522,11 @@ public void testQueryExpressionIteratingOverStreamReturningXMLWithReadonly() { BRunUtil.invoke(result, "testQueryExpressionIteratingOverStreamReturningXMLWithReadonly"); } + @Test(description = "Test XML template with query expression iterating over xml starting with whitespace") + public void testQueryExpressionXmlStartWithWhiteSpace() { + BRunUtil.invoke(result, "testQueryExpressionXmlStartWithWhiteSpace"); + } + @AfterClass public void tearDown() { result = null; diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal b/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal index 70c9bb27170a..55c5688135a0 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal @@ -1514,6 +1514,52 @@ function testQueryExpressionIteratingOverStreamReturningXMLWithReadonly() { assertEquality(res.toString(), (xml `JohnMike`).toString()); } +function testQueryExpressionXmlStartWithWhiteSpace() { + Person[] personList = [{name: "John", country: "Australia"}, {name: "Mike", country : "Canada"}]; + xml xmlValue = xml ` + + + Dynamic Table + + + + + + + + ${from var {name, country} in personList + select xml ` + + + `} +
NameCountry
${name}${country}
+ + + `; + assertEquality(xmlValue.toString(), string ` + + + Dynamic Table + + + + + + + + + + + + + + +
NameCountry
JohnAustralia
MikeCanada
+ + + `); +} + function assertEquality(any|error actual, any|error expected) { if expected is anydata && actual is anydata && expected == actual { return; From a4d7f0eefde8cffcd26a6afd5ac8391b81a5c672 Mon Sep 17 00:00:00 2001 From: hindujaB Date: Mon, 23 Oct 2023 11:33:03 +0530 Subject: [PATCH 10/14] Remove `disableOnOldParser` test group --- .../bala/record/ClosedRecordTypeInclusionTest.java | 2 +- .../bala/record/OpenRecordTypeInclusionTest.java | 2 +- .../lambda/FunctionPointersNegativeTest.java | 2 +- .../lambda/FunctionPointersWithOptionalArgsTest.java | 2 +- .../MappingConstructorExprTest.java | 2 +- .../test/object/ObjectDocumentationTest.java | 4 ++-- .../ballerinalang/test/query/LimitClauseTest.java | 2 +- .../ballerinalang/test/query/OrderByClauseTest.java | 2 +- .../test/query/XMLQueryExpressionTest.java | 12 +++++------- .../test/record/ClosedRecordOptionalFieldsTest.java | 2 +- .../test/record/OpenRecordNegativeTest.java | 3 +-- .../test/record/RecordDocumentationTest.java | 4 ++-- .../test/statements/arrays/SealedArrayTest.java | 2 +- .../test/types/bytetype/BByteValueNegativeTest.java | 2 +- .../types/integer/BIntegerValueNegativeTest.java | 2 +- .../test/types/map/MapAccessExprTest.java | 2 +- .../types/var/VarDeclaredAssignmentStmtTest.java | 2 +- .../test/types/xml/XMLIterationTest.java | 6 ++---- 18 files changed, 25 insertions(+), 30 deletions(-) diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/ClosedRecordTypeInclusionTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/ClosedRecordTypeInclusionTest.java index ca828de57c9f..48ba6acd5de8 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/ClosedRecordTypeInclusionTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/ClosedRecordTypeInclusionTest.java @@ -51,7 +51,7 @@ public void setup() { compileResult = BCompileUtil.compile("test-src/record/closed_record_type_inclusion.bal"); } - @Test(description = "Negative tests" , groups = {"disableOnOldParser"}) + @Test(description = "Negative tests") public void negativeTests() { CompileResult negative = BCompileUtil.compile("test-src/record/closed_record_type_inclusion_negative.bal"); int index = 0; diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/OpenRecordTypeInclusionTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/OpenRecordTypeInclusionTest.java index 5c6d9e62aaf0..e7f08457dc79 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/OpenRecordTypeInclusionTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/bala/record/OpenRecordTypeInclusionTest.java @@ -51,7 +51,7 @@ public void setup() { compileResult = BCompileUtil.compile("test-src/record/open_record_type_inclusion.bal"); } - @Test(description = "Negative tests" , groups = {"disableOnOldParser"}) + @Test(description = "Negative tests") public void negativeTests() { CompileResult negative = BCompileUtil.compile("test-src/record/open_record_type_inclusion_negative.bal"); int index = 0; diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersNegativeTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersNegativeTest.java index 879e4768b73f..f29a3bf1da7d 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersNegativeTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersNegativeTest.java @@ -67,7 +67,7 @@ public void testFPInStructIncorrectArg() { BAssertUtil.validateError(result, 0, "incompatible types: expected 'string', found 'Person'", 32, 30); } - @Test(groups = { "disableOnOldParser" }) + @Test() public void testFPWithNoImport() { CompileResult result = BCompileUtil.compile("test-src/expressions/lambda/negative/fp-with-import-negative.bal"); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersWithOptionalArgsTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersWithOptionalArgsTest.java index 285867d08d7a..71d59cf48468 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersWithOptionalArgsTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/lambda/FunctionPointersWithOptionalArgsTest.java @@ -41,7 +41,7 @@ public void setup() { result = BCompileUtil.compile("test-src/expressions/lambda/function-pointers-with-optional-args.bal"); } - @Test(groups = { "disableOnOldParser" }) + @Test() public void testFunctionPointersWithNamedArgs() { CompileResult result = BCompileUtil.compile("test-src/expressions/lambda/function-pointers-with-named-args-negative.bal"); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/mappingconstructor/MappingConstructorExprTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/mappingconstructor/MappingConstructorExprTest.java index 9914ad447bf9..6590d74cd67c 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/mappingconstructor/MappingConstructorExprTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/expressions/mappingconstructor/MappingConstructorExprTest.java @@ -327,7 +327,7 @@ public Object[][] readOnlyFieldTests() { }; } - @Test(groups = "disableOnOldParser") + @Test() public void testReadOnlyFieldsSemanticNegative() { CompileResult compileResult = BCompileUtil.compile("test-src/expressions/mappingconstructor/readonly_field_negative.bal"); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/object/ObjectDocumentationTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/object/ObjectDocumentationTest.java index 69f91d0e68d4..6d2564e4b04f 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/object/ObjectDocumentationTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/object/ObjectDocumentationTest.java @@ -66,7 +66,7 @@ public void testDocAnnotation() { Assert.assertNotNull(docNode); } - @Test(description = "Test doc struct.", groups = { "disableOnOldParser" }) + @Test(description = "Test doc struct.") public void testDocStruct() { CompileResult compileResult = BCompileUtil.compile("test-src/object/object_doc_annotation.bal"); Assert.assertEquals(compileResult.getWarnCount(), 0); @@ -88,7 +88,7 @@ public void testDocStruct() { EMPTY_STRING), "struct `field c` documentation"); } - @Test(description = "Test doc negative cases.", groups = { "disableOnOldParser" }) + @Test(description = "Test doc negative cases.") public void testDocumentationNegative() { CompileResult compileResult = BCompileUtil.compile("test-src/object/object_documentation_negative.bal"); Assert.assertEquals(compileResult.getErrorCount(), 0, getErrorString(compileResult.getDiagnostics())); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/LimitClauseTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/LimitClauseTest.java index 97427fbc9a3e..6bf2d3a5dbc3 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/LimitClauseTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/LimitClauseTest.java @@ -152,7 +152,7 @@ public void testLetExpressionWithLimitClause() { Assert.assertTrue((Boolean) values); } - @Test(description = "Test limit clause with incompatible types", groups = {"disableOnOldParser"}) + @Test(description = "Test limit clause with incompatible types") public void testNegativeScenarios() { negativeResult = BCompileUtil.compile("test-src/query/limit-clause-negative.bal"); Assert.assertEquals(negativeResult.getErrorCount(), 3); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/OrderByClauseTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/OrderByClauseTest.java index 3ed601d37ddb..59b4789c5199 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/OrderByClauseTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/OrderByClauseTest.java @@ -35,7 +35,7 @@ * * @since Swan Lake */ -@Test(groups = {"disableOnOldParser"}) +@Test() public class OrderByClauseTest { private CompileResult result; diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java index a7d373391384..6fe2729ab2d9 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/query/XMLQueryExpressionTest.java @@ -50,7 +50,7 @@ public void testNegativeQueryExprForXML() { validateError(negativeResult, index++, "incompatible types: expected " + "'xml<((xml:Element|xml:Comment|xml:ProcessingInstruction|xml:Text) & readonly)> & readonly'," + " found 'xml'", 21, 16); - validateError(negativeResult, index++, "incompatible types: expected 'xml:Element & readonly', " + "" + + validateError(negativeResult, index++, "incompatible types: expected 'xml:Element & readonly', " + "found 'xml:Element'", 25, 16); validateError(negativeResult, index++, "incompatible types: expected 'xml<(xml:Element & readonly)> & readonly', found 'xml:Element'", @@ -89,7 +89,7 @@ public void testSimpleQueryExprForXML() { "Sherlock HolmesThe Da Vinci Code"); } - @Test(groups = {"disableOnOldParser"}, description = "Test simple query expression for XMLs - #2") + @Test(description = "Test simple query expression for XMLs - #2") public void testSimpleQueryExprForXML2() { Object returnValues = BRunUtil.invoke(result, "testSimpleQueryExprForXML2"); Assert.assertNotNull(returnValues); @@ -149,7 +149,7 @@ public void testSimpleQueryExprForXMLOrNilResult() { "Sherlock HolmesThe Da Vinci Code"); } - @Test(groups = {"disableOnOldParser"}, description = "Test simple query expression for xml? - #2") + @Test(description = "Test simple query expression for xml? - #2") public void testSimpleQueryExprForXMLOrNilResult2() { Object returnValues = BRunUtil.invoke(result, "testSimpleQueryExprForXMLOrNilResult2"); Assert.assertNotNull(returnValues); @@ -355,8 +355,7 @@ public void testSimpleQueryExprForXMLWithReadonly1() { BRunUtil.invoke(result, "testSimpleQueryExprForXMLWithReadonly1"); } - @Test(groups = {"disableOnOldParser"}, - description = "Test simple query expression for XMLs with readonly intersection - #2") + @Test(description = "Test simple query expression for XMLs with readonly intersection - #2") public void testSimpleQueryExprForXMLWithReadonly2() { BRunUtil.invoke(result, "testSimpleQueryExprForXMLWithReadonly2"); } @@ -386,8 +385,7 @@ public void testSimpleQueryExprForXMLOrNilResultWithReadonly1() { BRunUtil.invoke(result, "testSimpleQueryExprForXMLOrNilResultWithReadonly1"); } - @Test(groups = {"disableOnOldParser"}, - description = "Test simple query expression for xml? with readonly intersection - #2") + @Test(description = "Test simple query expression for xml? with readonly intersection - #2") public void testSimpleQueryExprForXMLOrNilResultWithReadonly2() { BRunUtil.invoke(result, "testSimpleQueryExprForXMLOrNilResultWithReadonly2"); } diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/ClosedRecordOptionalFieldsTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/ClosedRecordOptionalFieldsTest.java index 8cceda02f20e..da2f74175d23 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/ClosedRecordOptionalFieldsTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/ClosedRecordOptionalFieldsTest.java @@ -47,7 +47,7 @@ public void setup() { compileResult = BCompileUtil.compile("test-src/record/closed_record_optional_fields.bal"); } - @Test(description = "Test for the compile errors", groups = {"disableOnOldParser"}) + @Test(description = "Test for the compile errors") public void testNegatives() { CompileResult negativeResult = BCompileUtil.compile( "test-src/record/closed_record_optional_fields_negatives.bal"); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/OpenRecordNegativeTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/OpenRecordNegativeTest.java index ac64fb80990b..c5fef5094863 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/OpenRecordNegativeTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/OpenRecordNegativeTest.java @@ -71,8 +71,7 @@ public void invalidRecordAssignment() { " anydata...; |} j; anydata...; |}', found 'int'", 4, 9); } - @Test(description = "Test white space between the type name and ellipsis in rest descriptor", - groups = {"disableOnOldParser"}) + @Test(description = "Test white space between the type name and ellipsis in rest descriptor") public void testRestDescriptorSyntax() { CompileResult result = BCompileUtil.compile("test-src/record/open_record_invalid_rest_desc.bal"); assertEquals(result.getErrorCount(), 0); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/RecordDocumentationTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/RecordDocumentationTest.java index ef871e87c8b4..e3850bab3379 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/RecordDocumentationTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/record/RecordDocumentationTest.java @@ -40,7 +40,7 @@ public class RecordDocumentationTest { public void setup() { } - @Test(description = "Test doc annotation.", groups = {"disableOnOldParser"}) + @Test(description = "Test doc annotation.") public void testDocAnnotation() { CompileResult compileResult = BCompileUtil.compile("test-src/record/record_annotation.bal"); Assert.assertEquals(compileResult.getWarnCount(), 3); @@ -88,7 +88,7 @@ public void testDocStruct() { EMPTY_STRING), "struct `field c` documentation"); } - @Test(description = "Test doc negative cases.", groups = {"disableOnOldParser"}) + @Test(description = "Test doc negative cases.") public void testDocumentationNegative() { CompileResult compileResult = BCompileUtil.compile("test-src/record/record_documentation_negative.bal"); Assert.assertEquals(compileResult.getErrorCount(), 0, diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/statements/arrays/SealedArrayTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/statements/arrays/SealedArrayTest.java index 034251b4e140..1a515c77c94d 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/statements/arrays/SealedArrayTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/statements/arrays/SealedArrayTest.java @@ -455,7 +455,7 @@ public void testSealedArrayConstrainedMapInvalidIndex() { BRunUtil.invoke(compileResult, "testSealedArrayConstrainedMapInvalidIndex", args); } - @Test(groups = { "disableOnOldParser" }) + @Test() public void testArrayWithConstantSizeReferenceFill() { BRunUtil.invoke(compileResult, "testArrayWithConstantSizeReferenceFill"); } diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/bytetype/BByteValueNegativeTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/bytetype/BByteValueNegativeTest.java index 1741d5fcb718..f472813c288d 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/bytetype/BByteValueNegativeTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/bytetype/BByteValueNegativeTest.java @@ -77,7 +77,7 @@ public void testByteValueNegative() { BAssertUtil.validateError(result, 22, msg4, 40, 87); } - @Test(description = "Test byte shift operators negative", groups = { "disableOnOldParser" }) + @Test(description = "Test byte shift operators negative") public void invalidByteShiftOperators() { CompileResult result = BCompileUtil.compile("test-src/types/byte/byte-shift-operators-negative.bal"); Assert.assertEquals(result.getErrorCount(), 13); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/integer/BIntegerValueNegativeTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/integer/BIntegerValueNegativeTest.java index 259c9ed265f5..65a56a863520 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/integer/BIntegerValueNegativeTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/integer/BIntegerValueNegativeTest.java @@ -26,7 +26,7 @@ /** * Test class for negative integer tests. */ -@Test(groups = { "disableOnOldParser" }) +@Test() public class BIntegerValueNegativeTest { @Test diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/map/MapAccessExprTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/map/MapAccessExprTest.java index 2633d1d610ba..a2781fa49824 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/map/MapAccessExprTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/map/MapAccessExprTest.java @@ -147,7 +147,7 @@ public void testGetMapValues() { Assert.assertEquals(returns.get(1).toString(), "Colombo"); } - @Test(description = "Map access negative scenarios", groups = {"disableOnOldParser"}) + @Test(description = "Map access negative scenarios") public void testNegativeSemantics() { Assert.assertEquals(resultSemanticsNegative.getDiagnostics().length, 4); int index = 0; diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/var/VarDeclaredAssignmentStmtTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/var/VarDeclaredAssignmentStmtTest.java index 31427964a1dd..2c36efc7c007 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/var/VarDeclaredAssignmentStmtTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/var/VarDeclaredAssignmentStmtTest.java @@ -153,7 +153,7 @@ public void testObjectToVarAssignment2() { BRunUtil.invoke(result, "testObjectToVarAssignment2"); } - @Test(description = "Test var in variable def.", groups = {"disableOnOldParser"}) + @Test(description = "Test var in variable def.") public void testVarTypeInVariableDefStatement() { //var type is not not allowed in variable def statements CompileResult res = BCompileUtil.compile("test-src/types/var/var-type-variable-def-negative.bal"); diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLIterationTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLIterationTest.java index 32fa97298e38..03425577fffe 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLIterationTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/xml/XMLIterationTest.java @@ -181,8 +181,7 @@ public void testXMLChainedIterableOps() { Assert.assertEquals(((BXmlSequence) resArray.getRefValue(1)).getTextValue().toString(), authors[1][0]); } - @Test(groups = {"disableOnOldParser"}, - description = "Test iterating over xml elements where some elements are characters") + @Test(description = "Test iterating over xml elements where some elements are characters") public void testXMLCompoundCharacterSequenceIteration() { Object results = BRunUtil.invoke(result, "xmlSequenceIter"); Assert.assertEquals(result.getDiagnostics().length, 0); @@ -190,8 +189,7 @@ public void testXMLCompoundCharacterSequenceIteration() { Assert.assertEquals(str, "the book\nbit of text\\u2702\\u2705\n"); } - @Test(groups = {"disableOnOldParser"}, - description = "Test iterating over xml sequence where all elements are character items") + @Test(description = "Test iterating over xml sequence where all elements are character items") public void testXMLCharacterSequenceIteration() { Object results = BRunUtil.invoke(result, "xmlCharItemIter"); Assert.assertEquals(result.getDiagnostics().length, 0); From 924ae6f2436ebfc2753f0db1c4a35a9e460d416c Mon Sep 17 00:00:00 2001 From: hindujaB Date: Thu, 26 Oct 2023 09:59:27 +0530 Subject: [PATCH 11/14] Fix failing test --- .../test/resources/test-src/query/xml-query-expression.bal | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal b/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal index 55c5688135a0..c9db31e26b46 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/query/xml-query-expression.bal @@ -1536,7 +1536,7 @@ function testQueryExpressionXmlStartWithWhiteSpace() { `; - assertEquality(xmlValue.toString(), string ` + xml expected = xml ` Dynamic Table @@ -1557,7 +1557,8 @@ function testQueryExpressionXmlStartWithWhiteSpace() { - `); + `; + assertEquality(xmlValue, expected); } function assertEquality(any|error actual, any|error expected) { From 4dbbdb77d2e2598319a5aee9b1185fe136c79b7e Mon Sep 17 00:00:00 2001 From: Nipuna Fernando Date: Thu, 26 Oct 2023 15:14:07 +0530 Subject: [PATCH 12/14] Increase tests for composite keys in tables --- .../types/table/TableKeyFieldValueTest.java | 6 +- .../table/table_key_field_value_test.bal | 160 +++++++++++++++--- 2 files changed, 136 insertions(+), 30 deletions(-) diff --git a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java index cb06d58044d9..c2ddaa908435 100644 --- a/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java +++ b/tests/jballerina-unit-test/src/test/java/org/ballerinalang/test/types/table/TableKeyFieldValueTest.java @@ -73,8 +73,10 @@ public Object[] dataToTestTableKeyFieldValue() { "testKeyCollision", "testRegExpAsKeyValue", "testKeyCollisionWithStringAndRegExpAsKeyValues", - "testTupleAsKeyValue", - "testStringAsKeyValue" + "testStringAsKeyValue", + "testStringAsCompositeKeyValue", + "testMapAsCompositeKeyValue", + "testArrayAsCompositeKeyValue" }; } diff --git a/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal b/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal index 01a2fef2cbee..1593863285c6 100644 --- a/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal +++ b/tests/jballerina-unit-test/src/test/resources/test-src/types/table/table_key_field_value_test.bal @@ -583,54 +583,158 @@ function testKeyCollisionWithStringAndRegExpAsKeyValues() { assertEqual(tbl, tbl5); } -type Employee record {| - readonly string orgId; - readonly string appId; - string company; +type Row12 record {| + readonly string key1; + readonly string key2; + string a; |}; -function testTupleAsKeyValue() { - table key(orgId, appId) tbl = table [ - {orgId: "1", appId: "1", company: "xxx"} +function testStringAsKeyValue() { + Row12 expectedRec = {key1: "k1", key2: "k2", a: "n2"}; + + table key(key1) tbl = table [ + {key1: "k1", key2: "k2", a: "n1"} + ]; + table tbl2 = table [ + {key1: "k1", key2: "k2", a: "n2"} ]; - tbl.put({ - orgId: "1", - appId: "1", - company: "yyy" - }); + // Test the put method of the table + tbl.put(expectedRec.clone()); - table tbl1 = from Employee r in tbl - where r.orgId == "1" && r.appId == "1" + table tbl1 = from Row12 r in tbl + where r.key1 == "k1" && r.key2 == "k2" select r; + assertEqual(tbl1, tbl2); + + // Test the get method of the table + readonly & string keyString = "k1"; + Row12 outputRec = tbl.get(keyString); + assertEqual(expectedRec, outputRec); + + // Test the add method of the table + error? err = trap tbl.add(expectedRec); + assertEqual(err is error, true); + assertEqual((err).message(), "{ballerina/lang.table}KeyConstraintViolation"); + + // Test the remove method of the table + Row12 removedRec = tbl.remove(keyString); + assertEqual(expectedRec, removedRec); + assertEqual(tbl.length(), 0); +} + +function testStringAsCompositeKeyValue() { + Row12 expectedRec = {key1: "k1", key2: "k2", a: "n2"}; - table tbl2 = table [ - {orgId: "1", appId: "1", company: "yyy"} + table key(key1, key2) tbl = table [ + {key1: "k1", key2: "k2", a: "n1"} ]; + table tbl2 = table [ + {key1: "k1", key2: "k2", a: "n2"} + ]; + + // Test the put method of the table + tbl.put(expectedRec.clone()); + table tbl1 = from Row12 r in tbl + where r.key1 == "k1" && r.key2 == "k2" + select r; assertEqual(tbl1, tbl2); + + // Test the get method of the table + [string & readonly, string & readonly] keyTuple = ["k1", "k2"]; + Row12 outputRec = tbl.get(keyTuple); + assertEqual(expectedRec, outputRec); + + // Test the add method of the table + error? err = trap tbl.add(expectedRec); + assertEqual(err is error, true); + assertEqual((err).message(), "{ballerina/lang.table}KeyConstraintViolation"); + + // Test the remove method of the table + Row12 removedRec = tbl.remove(keyTuple); + assertEqual(expectedRec, removedRec); + assertEqual(tbl.length(), 0); } -function testStringAsKeyValue() { - table key(orgId) tbl = table [ - {orgId: "1", appId: "1", company: "xxx"} +type Row13 record {| + readonly map keys; + readonly map values; + string a; +|}; + +function testMapAsCompositeKeyValue() { + Row13 expectedRec = {keys: {"k1": "v1", "k2": "v2"}, values: {"k1": 1, "k2": 2}, a: "n2"}; + + table key(keys, values) tbl = table [ + {keys: {"k1": "v1", "k2": "v2"}, values: {"k1": 1, "k2": 2}, a: "n1"} + ]; + table tbl2 = table [ + {keys: {"k1": "v1", "k2": "v2"}, values: {"k1": 1, "k2": 2}, a: "n2"} ]; - tbl.put({ - orgId: "1", - appId: "1", - company: "yyy" - }); + // Test the put method of the table + tbl.put(expectedRec.clone()); - table tbl1 = from Employee r in tbl - where r.orgId == "1" && r.appId == "1" + table tbl1 = from Row13 r in tbl + where r.keys == {"k1": "v1", "k2": "v2"} && r.values == {"k1": 1, "k2": 2} select r; + assertEqual(tbl1, tbl2); + + // Test the get method of the table + [map & readonly, map & readonly] keyTuple = [{"k1": "v1", "k2": "v2"}, {"k1": 1, "k2": 2}]; + Row13 outputRec = tbl.get(keyTuple); + assertEqual(expectedRec, outputRec); - table tbl2 = table [ - {orgId: "1", appId: "1", company: "yyy"} + // Test the add method of the table + error? err = trap tbl.add(expectedRec); + assertEqual(err is error, true); + assertEqual((err).message(), "{ballerina/lang.table}KeyConstraintViolation"); + + // Test the remove method of the table + Row13 removedRec = tbl.remove(keyTuple); + assertEqual(expectedRec, removedRec); + assertEqual(tbl.length(), 0); +} + +type Row14 record {| + readonly string[] keys; + readonly int[] values; + string a; +|}; + +function testArrayAsCompositeKeyValue() { + Row14 expectedRec = {keys: ["k1", "k2"], values: [1, 2], a: "n2"}; + + table key(keys, values) tbl = table [ + {keys: ["k1", "k2"], values: [1, 2], a: "n1"} ]; + table tbl2 = table [ + {keys: ["k1", "k2"], values: [1, 2], a: "n2"} + ]; + + // Test the put method of the table + tbl.put(expectedRec.clone()); + table tbl1 = from Row14 r in tbl + where r.keys == ["k1", "k2"] && r.values == [1, 2] + select r; assertEqual(tbl1, tbl2); + + // Test the get method of the table + [string[] & readonly, int[] & readonly] keyTuple = [["k1", "k2"], [1, 2]]; + Row14 outputRec = tbl.get(keyTuple); + assertEqual(expectedRec, outputRec); + + // Test the add method of the table + error? err = trap tbl.add(expectedRec); + assertEqual(err is error, true); + assertEqual((err).message(), "{ballerina/lang.table}KeyConstraintViolation"); + + // Test the remove method of the table + Row14 removedRec = tbl.remove(keyTuple); + assertEqual(expectedRec, removedRec); + assertEqual(tbl.length(), 0); } function assertEqual(any expected, any actual) { From b20eaf92bfac45739e85a25359740703a90ff8b7 Mon Sep 17 00:00:00 2001 From: Gayal Dassanayake Date: Tue, 31 Oct 2023 14:37:52 +0530 Subject: [PATCH 13/14] Make TestCommandTest version agnostic --- .../java/io/ballerina/cli/cmd/TestCommandTest.java | 11 +++++++---- .../project_b_100/resources/expectedDeps.toml | 2 +- 2 files changed, 8 insertions(+), 5 deletions(-) diff --git a/cli/ballerina-cli/src/test/java/io/ballerina/cli/cmd/TestCommandTest.java b/cli/ballerina-cli/src/test/java/io/ballerina/cli/cmd/TestCommandTest.java index af01dac0283b..a9a537a4043d 100644 --- a/cli/ballerina-cli/src/test/java/io/ballerina/cli/cmd/TestCommandTest.java +++ b/cli/ballerina-cli/src/test/java/io/ballerina/cli/cmd/TestCommandTest.java @@ -30,6 +30,7 @@ import org.testng.Assert; import org.testng.annotations.BeforeClass; import org.testng.annotations.Test; +import org.wso2.ballerinalang.util.RepoUtils; import picocli.CommandLine; import java.io.File; @@ -277,8 +278,9 @@ public void testBalTestWithStickyFlag() throws IOException { String buildLog = readOutput(true); Assert.assertEquals(buildLog.replaceAll("\r", ""), getOutput("bal-test-project.txt")); Assert.assertTrue(projectPath.resolve(DEPENDENCIES_TOML).toFile().exists()); - Assert.assertEquals(readFileAsString(projectPath.resolve(DEPENDENCIES_TOML)).trim(), readFileAsString( - projectPath.resolve(RESOURCE_DIR_NAME).resolve("expectedDeps.toml")).trim()); + Assert.assertEquals(readFileAsString(projectPath.resolve(DEPENDENCIES_TOML)).trim(), + readFileAsString(projectPath.resolve(RESOURCE_DIR_NAME).resolve("expectedDeps.toml")) + .trim().replace("INSERT_VERSION_HERE", RepoUtils.getBallerinaShortVersion())); // remove build file Files.deleteIfExists(projectPath.resolve(TARGET_DIR_NAME).resolve(BUILD_FILE)); @@ -294,8 +296,9 @@ public void testBalTestWithStickyFlag() throws IOException { String secondBuildLog = readOutput(true); Assert.assertEquals(secondBuildLog.replaceAll("\r", ""), getOutput("bal-test-project.txt")); Assert.assertTrue(projectPath.resolve(DEPENDENCIES_TOML).toFile().exists()); - Assert.assertEquals(readFileAsString(projectPath.resolve(DEPENDENCIES_TOML)).trim(), readFileAsString( - projectPath.resolve(RESOURCE_DIR_NAME).resolve("expectedDeps.toml")).trim()); + Assert.assertEquals(readFileAsString(projectPath.resolve(DEPENDENCIES_TOML)).trim(), + readFileAsString(projectPath.resolve(RESOURCE_DIR_NAME).resolve("expectedDeps.toml")) + .trim().replace("INSERT_VERSION_HERE", RepoUtils.getBallerinaShortVersion())); } @Test(description = "Test a ballerina project with the flag dump-graph") diff --git a/cli/ballerina-cli/src/test/resources/test-resources/balTestWithStickyFlag/project_b_100/resources/expectedDeps.toml b/cli/ballerina-cli/src/test/resources/test-resources/balTestWithStickyFlag/project_b_100/resources/expectedDeps.toml index cf1fc2d02a2e..9aa444443339 100644 --- a/cli/ballerina-cli/src/test/resources/test-resources/balTestWithStickyFlag/project_b_100/resources/expectedDeps.toml +++ b/cli/ballerina-cli/src/test/resources/test-resources/balTestWithStickyFlag/project_b_100/resources/expectedDeps.toml @@ -5,7 +5,7 @@ [ballerina] dependencies-toml-version = "2" -distribution-version = "2201.8.0-SNAPSHOT" +distribution-version = "INSERT_VERSION_HERE" [[package]] org = "ballerina" From df851d97e12a344356eac9e664de6c3df0b35d12 Mon Sep 17 00:00:00 2001 From: Anupama Pathirage Date: Fri, 3 Nov 2023 10:40:47 -0500 Subject: [PATCH 14/14] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 2277447e3aa0..22955ba535b8 100644 --- a/README.md +++ b/README.md @@ -57,7 +57,7 @@ You can use the following resources to learn Ballerina. >**Tip:** If you are unsure whether you have found a bug, search the existing issues in the GitHub repo and raise it in the [Ballerina Discord](https://discord.com/invite/wAJYFbMrG2) or [Stack Overflow](https://stackoverflow.com/questions/tagged/ballerina). - Language, Tooling, Website: ballerina-lang repo - - Ballerina library: ballerina-lang repo + - Ballerina library: ballerina-library repo - Security flaw: send an email to security@ballerina.io. For details, see the security policy.