diff --git a/README.md b/README.md
index dc03e02..4a0b264 100644
--- a/README.md
+++ b/README.md
@@ -274,6 +274,56 @@ An example query to look for customers in the Romanian locale might look like:
}
```
+## Country Code Scalar
+The CountryCode scalar type as defined by [ISO 3166-1 alpha-2](https://en.wikipedia.org/wiki/ISO_3166-1_alpha-2).
+
+
+An example declaration in SDL might be:
+```graphql
+ scalar CountryCode
+
+ type Customer {
+ name : String
+ countryCode : CountryCode
+ }
+```
+
+And example query might look like:
+
+```graphql
+ query {
+ customers(code : "US") {
+ name
+ countryCode
+ }
+ }
+```
+## Currency Scalar
+
+A field whose value is an [ISO-4217](https://en.wikipedia.org/wiki/ISO_4217) currency.
+
+An example declaration in SDL might be:
+```graphql
+ scalar Currency
+
+ type Account {
+ id : String
+ currency : Currency
+ accountNumber: String
+ }
+```
+
+And example query might look like:
+
+```graphql
+ query {
+ accounts(currency : "USD") {
+ id
+ currency
+ accountNumber
+ }
+ }
+```
## Alias Scalars
diff --git a/src/main/java/graphql/scalars/ExtendedScalars.java b/src/main/java/graphql/scalars/ExtendedScalars.java
index b4a28ed..ce36232 100644
--- a/src/main/java/graphql/scalars/ExtendedScalars.java
+++ b/src/main/java/graphql/scalars/ExtendedScalars.java
@@ -2,6 +2,8 @@
import graphql.PublicApi;
import graphql.scalars.alias.AliasedScalar;
+import graphql.scalars.country.code.CountryCodeScalar;
+import graphql.scalars.currency.CurrencyScalar;
import graphql.scalars.datetime.DateScalar;
import graphql.scalars.datetime.DateTimeScalar;
import graphql.scalars.datetime.LocalTimeCoercing;
@@ -23,8 +25,6 @@
import graphql.scalars.url.UrlScalar;
import graphql.schema.GraphQLScalarType;
-import java.util.UUID;
-
/**
* This is the API entry point for all the extended scalars
*/
@@ -138,6 +138,18 @@ public class ExtendedScalars {
*/
public static final GraphQLScalarType Locale = LocaleScalar.INSTANCE;
+ /**
+ * A field whose value is an ISO-4217 currency.
+ * See the ISO-4217 for more details.
+ */
+ public static final GraphQLScalarType Currency = CurrencyScalar.INSTANCE;
+
+ /**
+ * The CountryCode scalar type as defined by ISO 3166-1 alpha-2.
+ * See the ISO 3166-1 alpha-2 for more details.
+ */
+ public static final GraphQLScalarType CountryCode = CountryCodeScalar.INSTANCE;
+
/**
* A UUID scalar that accepts a universally unique identifier and produces {@link
* java.util.UUID} objects at runtime.
diff --git a/src/main/java/graphql/scalars/country/code/CountryCode.java b/src/main/java/graphql/scalars/country/code/CountryCode.java
new file mode 100644
index 0000000..c604b8c
--- /dev/null
+++ b/src/main/java/graphql/scalars/country/code/CountryCode.java
@@ -0,0 +1,18 @@
+package graphql.scalars.country.code;
+
+/**
+ * The CountryCode list as defined by ISO 3166-1 alpha-2.
+ * See the ISO 3166-1 alpha-2 for more details.
+ */
+public enum CountryCode {
+ AD, AE, AF, AG, AI, AL, AM, AO, AQ, AR, AS, AT, AU, AW, AX, AZ, BA, BB, BD, BE, BF, BG, BH, BI, BJ, BL, BM, BN, BO,
+ BQ, BR, BS, BT, BV, BW, BY, BZ, CA, CC, CD, CF, CG, CH, CI, CK, CL, CM, CN, CO, CR, CU, CV, CW, CX, CY, CZ, DE, DJ,
+ DK, DM, DO, DZ, EC, EE, EG, EH, ER, ES, ET, FI, FJ, FK, FM, FO, FR, GA, GB, GD, GE, GF, GG, GH, GI, GL, GM, GN, GP,
+ GQ, GR, GS, GT, GU, GW, GY, HK, HM, HN, HR, HT, HU, ID, IE, IL, IM, IN, IO, IQ, IR, IS, IT, JE, JM, JO, JP, KE, KG,
+ KH, KI, KM, KN, KP, KR, KW, KY, KZ, LA, LB, LC, LI, LK, LR, LS, LT, LU, LV, LY, MA, MC, MD, ME, MF, MG, MH, MK, ML,
+ MM, MN, MO, MP, MQ, MR, MS, MT, MU, MV, MW, MX, MY, MZ, NA, NC, NE, NF, NG, NI, NL, NO, NP, NR, NU, NZ, OM, PA, PE,
+ PF, PG, PH, PK, PL, PM, PN, PR, PS, PT, PW, PY, QA, RE, RO, RS, RU, RW, SA, SB, SC, SD, SE, SG, SH, SI, SJ, SK, SL,
+ SM, SN, SO, SR, SS, ST, SV, SX, SY, SZ, TC, TD, TF, TG, TH, TJ, TK, TL, TM, TN, TO, TR, TT, TV, TW, TZ, UA, UG, UM,
+ US, UY, UZ, VA, VC, VE, VG, VI, VN, VU, WF, WS, YE, YT, ZA, ZM, ZW
+}
+
diff --git a/src/main/java/graphql/scalars/country/code/CountryCodeScalar.java b/src/main/java/graphql/scalars/country/code/CountryCodeScalar.java
new file mode 100644
index 0000000..b88c139
--- /dev/null
+++ b/src/main/java/graphql/scalars/country/code/CountryCodeScalar.java
@@ -0,0 +1,72 @@
+package graphql.scalars.country.code;
+
+import graphql.Internal;
+import graphql.language.StringValue;
+import graphql.language.Value;
+import graphql.schema.*;
+
+import java.util.function.Function;
+
+import static graphql.scalars.util.Kit.typeName;
+
+/**
+ * Access this via {@link graphql.scalars.ExtendedScalars#CountryCode}
+ */
+@Internal
+public class CountryCodeScalar {
+
+ public static final GraphQLScalarType INSTANCE;
+
+ static {
+ Coercing coercing = new Coercing() {
+
+ @Override
+ public String serialize(Object input) throws CoercingSerializeException {
+ CountryCode countryCode = parseCountryCode(input, CoercingParseValueException::new);
+ return countryCode.name();
+ }
+
+ @Override
+ public CountryCode parseValue(Object input) throws CoercingParseValueException {
+ return parseCountryCode(input, CoercingParseValueException::new);
+ }
+
+ @Override
+ public CountryCode parseLiteral(Object input) throws CoercingParseLiteralException {
+ if (!(input instanceof StringValue)) {
+ throw new CoercingParseLiteralException("Expected AST type 'StringValue' but was '" + typeName(input) + "'.");
+ }
+ String stringValue = ((StringValue) input).getValue();
+ return parseCountryCode(stringValue, CoercingParseLiteralException::new);
+
+ }
+
+ @Override
+ public Value> valueToLiteral(Object input) {
+ String s = serialize(input);
+ return StringValue.newStringValue(s).build();
+ }
+
+ private CountryCode parseCountryCode(Object input, Function exceptionMaker) {
+ final CountryCode result;
+ if (input instanceof String) {
+ try {
+ result = CountryCode.valueOf((String) input);
+ } catch (NullPointerException | IllegalArgumentException ex) {
+ throw exceptionMaker.apply("Invalid ISO 3166-1 alpha-2 value : '" + input + "'. because of : '" + ex.getMessage() + "'");
+ }
+ } else if (input instanceof CountryCode) {
+ result = (CountryCode) input;
+ } else {
+ throw exceptionMaker.apply("Expected a 'String' or 'CountryCode' but was '" + typeName(input) + "'.");
+ }
+ return result;
+ }
+ };
+
+ INSTANCE = GraphQLScalarType.newScalar()
+ .name("CountryCode")
+ .description("The CountryCode scalar type as defined by ISO 3166-1 alpha-2.")
+ .coercing(coercing).build();
+ }
+}
diff --git a/src/main/java/graphql/scalars/currency/CurrencyScalar.java b/src/main/java/graphql/scalars/currency/CurrencyScalar.java
new file mode 100644
index 0000000..a2193a0
--- /dev/null
+++ b/src/main/java/graphql/scalars/currency/CurrencyScalar.java
@@ -0,0 +1,73 @@
+package graphql.scalars.currency;
+
+import graphql.Internal;
+import graphql.language.StringValue;
+import graphql.language.Value;
+import graphql.schema.*;
+
+import java.util.Currency;
+import java.util.function.Function;
+
+import static graphql.scalars.util.Kit.typeName;
+
+/**
+ * Access this via {@link graphql.scalars.ExtendedScalars#Currency}
+ */
+@Internal
+public class CurrencyScalar {
+
+ public static final GraphQLScalarType INSTANCE;
+
+ static {
+ Coercing coercing = new Coercing() {
+ @Override
+ public String serialize(Object input) throws CoercingSerializeException {
+ Currency currency = parseCurrency(input, CoercingSerializeException::new);
+ return currency.getCurrencyCode();
+ }
+
+ @Override
+ public Currency parseValue(Object input) throws CoercingParseValueException {
+ return parseCurrency(input, CoercingParseValueException::new);
+ }
+
+
+ @Override
+ public Currency parseLiteral(Object input) throws CoercingParseLiteralException {
+ if (!(input instanceof StringValue)) {
+ throw new CoercingParseLiteralException("Expected AST type 'StringValue' but was '" + typeName(input) + "'.");
+ }
+ String stringValue = ((StringValue) input).getValue();
+ return parseCurrency(stringValue, CoercingParseLiteralException::new);
+ }
+
+ @Override
+ public Value> valueToLiteral(Object input) {
+ String serializedInput = serialize(input);
+ return StringValue.newStringValue(serializedInput).build();
+ }
+
+
+ private Currency parseCurrency(Object input, Function exceptionMaker) {
+ final Currency result;
+ if (input instanceof Currency) {
+ result = (Currency) input;
+ } else if (input instanceof String) {
+ try {
+ result = Currency.getInstance((String) input);
+ } catch (NullPointerException | IllegalArgumentException ex) {
+ throw exceptionMaker.apply("Invalid ISO 4217 value : '" + input + "'. because of : '" + ex.getMessage() + "'");
+ }
+ } else {
+ throw exceptionMaker.apply("Expected a 'String' or 'Currency' but was '" + typeName(input) + "'.");
+ }
+ return result;
+ }
+ };
+
+ INSTANCE = GraphQLScalarType.newScalar()
+ .name("Currency")
+ .description("An ISO-4217 compliant Currency Scalar")
+ .coercing(coercing).build();
+ }
+}
\ No newline at end of file
diff --git a/src/test/groovy/graphql/scalars/country/code/CountryCodeScalarTest.groovy b/src/test/groovy/graphql/scalars/country/code/CountryCodeScalarTest.groovy
new file mode 100644
index 0000000..6cebaf0
--- /dev/null
+++ b/src/test/groovy/graphql/scalars/country/code/CountryCodeScalarTest.groovy
@@ -0,0 +1,351 @@
+package graphql.scalars.country.code
+
+import graphql.language.StringValue
+import graphql.scalars.ExtendedScalars
+import graphql.schema.CoercingParseValueException
+import spock.lang.Specification
+import spock.lang.Unroll
+
+import static graphql.scalars.util.TestKit.mkCountryCode
+import static graphql.scalars.util.TestKit.mkStringValue
+
+class CountryCodeScalarTest extends Specification {
+
+ def coercing = ExtendedScalars.CountryCode.getCoercing()
+
+ @Unroll
+ def "invoke parseValue for countryCode"() {
+ when:
+ def result = coercing.parseValue(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+ "US" | mkCountryCode("US")
+ "IN" | mkCountryCode("IN")
+ mkCountryCode("US") | mkCountryCode("US")
+ }
+
+
+ @Unroll
+ def "invoke parseLiteral for countryCode"() {
+
+ when:
+ def result = coercing.parseLiteral(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+ new StringValue("GB") | mkCountryCode("GB")
+ new StringValue("US") | mkCountryCode("US")
+ new StringValue("IN") | mkCountryCode("IN")
+ }
+
+ @Unroll
+ def "invoke serialize with countryCode"() {
+ when:
+ def result = coercing.serialize(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+ "GB" | "GB"
+ "US" | "US"
+ "IN" | "IN"
+ mkCountryCode("US") | "US"
+ }
+
+ @Unroll
+ def "invoke valueToLiteral with countryCode"() {
+
+ when:
+ def result = coercing.valueToLiteral(input)
+ then:
+ result.isEqualTo(expectedValue)
+ where:
+ input | expectedValue
+ "GB" | mkStringValue("GB")
+ "US" | mkStringValue("US")
+ "IN" | mkStringValue("IN")
+ mkCountryCode("US") | mkStringValue("US")
+ }
+
+ @Unroll
+ def "parseValue throws exception for invalid input #value"() {
+ when:
+ coercing.parseValue(value)
+ then:
+ thrown(CoercingParseValueException)
+
+ where:
+ value | _
+ "" | _
+ "US(UNITED STATES)" | _
+ "not a countryCode " | _
+ "42.3" | _
+ new Double(42.3) | _
+ new Float(42.3) | _
+ new Object() | _
+ }
+
+
+ @Unroll
+ def "invoke parseValue with all countryCode list"() {
+ when:
+ def result = coercing.parseValue(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+ "GB" | mkCountryCode("GB")
+ "US" | mkCountryCode("US")
+ "IN" | mkCountryCode("IN")
+ "AF" | mkCountryCode("AF")
+ "AX" | mkCountryCode("AX")
+ "AL" | mkCountryCode("AL")
+ "DZ" | mkCountryCode("DZ")
+ "AS" | mkCountryCode("AS")
+ "AD" | mkCountryCode("AD")
+ "AO" | mkCountryCode("AO")
+ "AI" | mkCountryCode("AI")
+ "AQ" | mkCountryCode("AQ")
+ "AG" | mkCountryCode("AG")
+ "AR" | mkCountryCode("AR")
+ "AM" | mkCountryCode("AM")
+ "AW" | mkCountryCode("AW")
+ "AU" | mkCountryCode("AU")
+ "AT" | mkCountryCode("AT")
+ "AZ" | mkCountryCode("AZ")
+ "BS" | mkCountryCode("BS")
+ "BH" | mkCountryCode("BH")
+ "BD" | mkCountryCode("BD")
+ "BB" | mkCountryCode("BB")
+ "BY" | mkCountryCode("BY")
+ "BE" | mkCountryCode("BE")
+ "BZ" | mkCountryCode("BZ")
+ "BJ" | mkCountryCode("BJ")
+ "BM" | mkCountryCode("BM")
+ "BT" | mkCountryCode("BT")
+ "BO" | mkCountryCode("BO")
+ "BQ" | mkCountryCode("BQ")
+ "BA" | mkCountryCode("BA")
+ "BW" | mkCountryCode("BW")
+ "BV" | mkCountryCode("BV")
+ "BR" | mkCountryCode("BR")
+ "IO" | mkCountryCode("IO")
+ "BN" | mkCountryCode("BN")
+ "BG" | mkCountryCode("BG")
+ "BF" | mkCountryCode("BF")
+ "BI" | mkCountryCode("BI")
+ "KH" | mkCountryCode("KH")
+ "CM" | mkCountryCode("CM")
+ "CA" | mkCountryCode("CA")
+ "CV" | mkCountryCode("CV")
+ "KY" | mkCountryCode("KY")
+ "CF" | mkCountryCode("CF")
+ "TD" | mkCountryCode("TD")
+ "CL" | mkCountryCode("CL")
+ "CN" | mkCountryCode("CN")
+ "CX" | mkCountryCode("CX")
+ "CC" | mkCountryCode("CC")
+ "CO" | mkCountryCode("CO")
+ "KM" | mkCountryCode("KM")
+ "CG" | mkCountryCode("CG")
+ "CD" | mkCountryCode("CD")
+ "CK" | mkCountryCode("CK")
+ "CR" | mkCountryCode("CR")
+ "CI" | mkCountryCode("CI")
+ "HR" | mkCountryCode("HR")
+ "CU" | mkCountryCode("CU")
+ "CW" | mkCountryCode("CW")
+ "CY" | mkCountryCode("CY")
+ "CZ" | mkCountryCode("CZ")
+ "DK" | mkCountryCode("DK")
+ "DJ" | mkCountryCode("DJ")
+ "DM" | mkCountryCode("DM")
+ "DO" | mkCountryCode("DO")
+ "EC" | mkCountryCode("EC")
+ "EG" | mkCountryCode("EG")
+ "SV" | mkCountryCode("SV")
+ "GQ" | mkCountryCode("GQ")
+ "ER" | mkCountryCode("ER")
+ "EE" | mkCountryCode("EE")
+ "ET" | mkCountryCode("ET")
+ "FK" | mkCountryCode("FK")
+ "FO" | mkCountryCode("FO")
+ "FJ" | mkCountryCode("FJ")
+ "FI" | mkCountryCode("FI")
+ "FR" | mkCountryCode("FR")
+ "GF" | mkCountryCode("GF")
+ "PF" | mkCountryCode("PF")
+ "TF" | mkCountryCode("TF")
+ "GA" | mkCountryCode("GA")
+ "GM" | mkCountryCode("GM")
+ "GE" | mkCountryCode("GE")
+ "DE" | mkCountryCode("DE")
+ "GH" | mkCountryCode("GH")
+ "GI" | mkCountryCode("GI")
+ "GR" | mkCountryCode("GR")
+ "GL" | mkCountryCode("GL")
+ "GD" | mkCountryCode("GD")
+ "GP" | mkCountryCode("GP")
+ "GU" | mkCountryCode("GU")
+ "GT" | mkCountryCode("GT")
+ "GG" | mkCountryCode("GG")
+ "GN" | mkCountryCode("GN")
+ "GW" | mkCountryCode("GW")
+ "GY" | mkCountryCode("GY")
+ "HT" | mkCountryCode("HT")
+ "HM" | mkCountryCode("HM")
+ "VA" | mkCountryCode("VA")
+ "HN" | mkCountryCode("HN")
+ "HK" | mkCountryCode("HK")
+ "HU" | mkCountryCode("HU")
+ "IS" | mkCountryCode("IS")
+ "ID" | mkCountryCode("ID")
+ "IR" | mkCountryCode("IR")
+ "IQ" | mkCountryCode("IQ")
+ "IE" | mkCountryCode("IE")
+ "IM" | mkCountryCode("IM")
+ "IL" | mkCountryCode("IL")
+ "IT" | mkCountryCode("IT")
+ "JM" | mkCountryCode("JM")
+ "JP" | mkCountryCode("JP")
+ "JE" | mkCountryCode("JE")
+ "JO" | mkCountryCode("JO")
+ "KZ" | mkCountryCode("KZ")
+ "KE" | mkCountryCode("KE")
+ "KI" | mkCountryCode("KI")
+ "KP" | mkCountryCode("KP")
+ "KR" | mkCountryCode("KR")
+ "KW" | mkCountryCode("KW")
+ "KG" | mkCountryCode("KG")
+ "LA" | mkCountryCode("LA")
+ "LV" | mkCountryCode("LV")
+ "LB" | mkCountryCode("LB")
+ "LS" | mkCountryCode("LS")
+ "LR" | mkCountryCode("LR")
+ "LY" | mkCountryCode("LY")
+ "LI" | mkCountryCode("LI")
+ "LT" | mkCountryCode("LT")
+ "LU" | mkCountryCode("LU")
+ "MO" | mkCountryCode("MO")
+ "MK" | mkCountryCode("MK")
+ "MG" | mkCountryCode("MG")
+ "MW" | mkCountryCode("MW")
+ "MY" | mkCountryCode("MY")
+ "MV" | mkCountryCode("MV")
+ "ML" | mkCountryCode("ML")
+ "MT" | mkCountryCode("MT")
+ "MH" | mkCountryCode("MH")
+ "MQ" | mkCountryCode("MQ")
+ "MR" | mkCountryCode("MR")
+ "MU" | mkCountryCode("MU")
+ "YT" | mkCountryCode("YT")
+ "MX" | mkCountryCode("MX")
+ "FM" | mkCountryCode("FM")
+ "MD" | mkCountryCode("MD")
+ "MC" | mkCountryCode("MC")
+ "MN" | mkCountryCode("MN")
+ "ME" | mkCountryCode("ME")
+ "MS" | mkCountryCode("MS")
+ "MA" | mkCountryCode("MA")
+ "MZ" | mkCountryCode("MZ")
+ "MM" | mkCountryCode("MM")
+ "NA" | mkCountryCode("NA")
+ "NR" | mkCountryCode("NR")
+ "NP" | mkCountryCode("NP")
+ "NL" | mkCountryCode("NL")
+ "NC" | mkCountryCode("NC")
+ "NZ" | mkCountryCode("NZ")
+ "NI" | mkCountryCode("NI")
+ "NE" | mkCountryCode("NE")
+ "NG" | mkCountryCode("NG")
+ "NU" | mkCountryCode("NU")
+ "NF" | mkCountryCode("NF")
+ "MP" | mkCountryCode("MP")
+ "NO" | mkCountryCode("NO")
+ "OM" | mkCountryCode("OM")
+ "PK" | mkCountryCode("PK")
+ "PW" | mkCountryCode("PW")
+ "PS" | mkCountryCode("PS")
+ "PA" | mkCountryCode("PA")
+ "PG" | mkCountryCode("PG")
+ "PY" | mkCountryCode("PY")
+ "PE" | mkCountryCode("PE")
+ "PH" | mkCountryCode("PH")
+ "PN" | mkCountryCode("PN")
+ "PL" | mkCountryCode("PL")
+ "PT" | mkCountryCode("PT")
+ "PR" | mkCountryCode("PR")
+ "QA" | mkCountryCode("QA")
+ "RE" | mkCountryCode("RE")
+ "RO" | mkCountryCode("RO")
+ "RU" | mkCountryCode("RU")
+ "RW" | mkCountryCode("RW")
+ "BL" | mkCountryCode("BL")
+ "SH" | mkCountryCode("SH")
+ "KN" | mkCountryCode("KN")
+ "LC" | mkCountryCode("LC")
+ "MF" | mkCountryCode("MF")
+ "PM" | mkCountryCode("PM")
+ "VC" | mkCountryCode("VC")
+ "WS" | mkCountryCode("WS")
+ "SM" | mkCountryCode("SM")
+ "ST" | mkCountryCode("ST")
+ "SA" | mkCountryCode("SA")
+ "SN" | mkCountryCode("SN")
+ "RS" | mkCountryCode("RS")
+ "SC" | mkCountryCode("SC")
+ "SL" | mkCountryCode("SL")
+ "SG" | mkCountryCode("SG")
+ "SX" | mkCountryCode("SX")
+ "SK" | mkCountryCode("SK")
+ "SI" | mkCountryCode("SI")
+ "SB" | mkCountryCode("SB")
+ "SO" | mkCountryCode("SO")
+ "ZA" | mkCountryCode("ZA")
+ "GS" | mkCountryCode("GS")
+ "SS" | mkCountryCode("SS")
+ "ES" | mkCountryCode("ES")
+ "LK" | mkCountryCode("LK")
+ "SD" | mkCountryCode("SD")
+ "SR" | mkCountryCode("SR")
+ "SJ" | mkCountryCode("SJ")
+ "SZ" | mkCountryCode("SZ")
+ "SE" | mkCountryCode("SE")
+ "CH" | mkCountryCode("CH")
+ "SY" | mkCountryCode("SY")
+ "TW" | mkCountryCode("TW")
+ "TJ" | mkCountryCode("TJ")
+ "TZ" | mkCountryCode("TZ")
+ "TH" | mkCountryCode("TH")
+ "TL" | mkCountryCode("TL")
+ "TG" | mkCountryCode("TG")
+ "TK" | mkCountryCode("TK")
+ "TO" | mkCountryCode("TO")
+ "TT" | mkCountryCode("TT")
+ "TN" | mkCountryCode("TN")
+ "TR" | mkCountryCode("TR")
+ "TM" | mkCountryCode("TM")
+ "TC" | mkCountryCode("TC")
+ "TV" | mkCountryCode("TV")
+ "UG" | mkCountryCode("UG")
+ "UA" | mkCountryCode("UA")
+ "AE" | mkCountryCode("AE")
+ "UM" | mkCountryCode("UM")
+ "UY" | mkCountryCode("UY")
+ "UZ" | mkCountryCode("UZ")
+ "VU" | mkCountryCode("VU")
+ "VE" | mkCountryCode("VE")
+ "VN" | mkCountryCode("VN")
+ "VG" | mkCountryCode("VG")
+ "VI" | mkCountryCode("VI")
+ "WF" | mkCountryCode("WF")
+ "EH" | mkCountryCode("EH")
+ "YE" | mkCountryCode("YE")
+ "ZM" | mkCountryCode("ZM")
+ "ZW" | mkCountryCode("ZW")
+ }
+
+}
diff --git a/src/test/groovy/graphql/scalars/currency/CurrencyScalarTest.groovy b/src/test/groovy/graphql/scalars/currency/CurrencyScalarTest.groovy
new file mode 100644
index 0000000..616b8ba
--- /dev/null
+++ b/src/test/groovy/graphql/scalars/currency/CurrencyScalarTest.groovy
@@ -0,0 +1,281 @@
+package graphql.scalars.currency
+
+import graphql.language.StringValue
+import graphql.scalars.ExtendedScalars
+import graphql.schema.CoercingParseValueException
+import spock.lang.Specification
+import spock.lang.Unroll
+
+import static graphql.scalars.util.TestKit.mkCurrency
+import static graphql.scalars.util.TestKit.mkStringValue
+
+class CurrencyScalarTest extends Specification {
+
+
+ def coercing = ExtendedScalars.Currency.getCoercing()
+
+ @Unroll
+ def "currency parseValue cases"() {
+
+ when:
+ def result = coercing.parseValue(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+
+ "USD" | mkCurrency("USD")
+ mkCurrency("USD") | mkCurrency("USD")
+ "GBP" | mkCurrency("GBP")
+ "EUR" | mkCurrency("EUR")
+ "CNY" | mkCurrency("CNY")
+ "ARS" | mkCurrency("ARS")
+ mkCurrency("ARS") | mkCurrency("ARS")
+ mkCurrency("ALL") | mkCurrency("ALL")
+ mkCurrency("AMD") | mkCurrency("AMD")
+ mkCurrency("ANG") | mkCurrency("ANG")
+ mkCurrency("AOA") | mkCurrency("AOA")
+ }
+
+
+ @Unroll
+ def "currency parseLiteral"() {
+
+ when:
+ def result = coercing.parseLiteral(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+ new StringValue("EUR") | mkCurrency("EUR")
+ new StringValue("USD") | mkCurrency("USD")
+ new StringValue("GBP") | mkCurrency("GBP")
+ }
+
+ @Unroll
+ def "currency serialize"() {
+
+ when:
+ def result = coercing.serialize(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+ "USD" | "USD"
+ mkCurrency("USD") | "USD"
+ }
+
+ @Unroll
+ def "currency valueToLiteral"() {
+
+ when:
+ def result = coercing.valueToLiteral(input)
+ then:
+ result.isEqualTo(expectedValue)
+ where:
+ input | expectedValue
+ "USD" | mkStringValue("USD")
+ mkCurrency("USD") | mkStringValue("USD")
+ }
+
+ @Unroll
+ def "parseValue throws exception for invalid input #value"() {
+ when:
+ coercing.parseValue(value)
+ then:
+ thrown(CoercingParseValueException)
+
+ where:
+ value | _
+ "" | _
+ "US_DOLLAR" | _
+ "not a currency " | _
+ "42.3" | _
+ new Double(42.3) | _
+ new Float(42.3) | _
+ new Object() | _
+ }
+
+
+ @Unroll
+ def "all currency ISO list parseValue"() {
+
+ when:
+ def result = coercing.parseValue(input)
+ then:
+ result == expectedValue
+ where:
+ input | expectedValue
+
+ "USD" | mkCurrency("USD")
+ "EUR" | mkCurrency("EUR")
+ "GBP" | mkCurrency("GBP")
+ "CNY" | mkCurrency("CNY")
+ "AED" | mkCurrency("AED")
+ "AFN" | mkCurrency("AFN")
+ "ALL" | mkCurrency("ALL")
+ "AMD" | mkCurrency("AMD")
+ "ANG" | mkCurrency("ANG")
+ "AOA" | mkCurrency("AOA")
+ "ARS" | mkCurrency("ARS")
+ "AUD" | mkCurrency("AUD")
+ "AWG" | mkCurrency("AWG")
+ "AZN" | mkCurrency("AZN")
+ "BAM" | mkCurrency("BAM")
+ "BBD" | mkCurrency("BBD")
+ "BDT" | mkCurrency("BDT")
+ "BGN" | mkCurrency("BGN")
+ "BHD" | mkCurrency("BHD")
+ "BIF" | mkCurrency("BIF")
+ "BMD" | mkCurrency("BMD")
+ "BND" | mkCurrency("BND")
+ "BOB" | mkCurrency("BOB")
+ "BOV" | mkCurrency("BOV")
+ "BRL" | mkCurrency("BRL")
+ "BSD" | mkCurrency("BSD")
+ "BTN" | mkCurrency("BTN")
+ "BWP" | mkCurrency("BWP")
+ "BYN" | mkCurrency("BYN")
+ "BZD" | mkCurrency("BZD")
+ "CAD" | mkCurrency("CAD")
+ "CDF" | mkCurrency("CDF")
+ "CHE" | mkCurrency("CHE")
+ "CHF" | mkCurrency("CHF")
+ "CHW" | mkCurrency("CHW")
+ "CLF" | mkCurrency("CLF")
+ "CLP" | mkCurrency("CLP")
+ "COP" | mkCurrency("COP")
+ "COU" | mkCurrency("COU")
+ "CRC" | mkCurrency("CRC")
+ "CUC" | mkCurrency("CUC")
+ "CUP" | mkCurrency("CUP")
+ "CVE" | mkCurrency("CVE")
+ "CZK" | mkCurrency("CZK")
+ "DJF" | mkCurrency("DJF")
+ "DKK" | mkCurrency("DKK")
+ "DOP" | mkCurrency("DOP")
+ "DZD" | mkCurrency("DZD")
+ "EGP" | mkCurrency("EGP")
+ "ERN" | mkCurrency("ERN")
+ "ETB" | mkCurrency("ETB")
+ "FJD" | mkCurrency("FJD")
+ "FKP" | mkCurrency("FKP")
+ "GEL" | mkCurrency("GEL")
+ "GHS" | mkCurrency("GHS")
+ "GIP" | mkCurrency("GIP")
+ "GMD" | mkCurrency("GMD")
+ "GNF" | mkCurrency("GNF")
+ "GTQ" | mkCurrency("GTQ")
+ "GYD" | mkCurrency("GYD")
+ "HKD" | mkCurrency("HKD")
+ "HNL" | mkCurrency("HNL")
+ "HRK" | mkCurrency("HRK")
+ "HTG" | mkCurrency("HTG")
+ "HUF" | mkCurrency("HUF")
+ "IDR" | mkCurrency("IDR")
+ "ILS" | mkCurrency("ILS")
+ "INR" | mkCurrency("INR")
+ "IQD" | mkCurrency("IQD")
+ "IRR" | mkCurrency("IRR")
+ "ISK" | mkCurrency("ISK")
+ "JMD" | mkCurrency("JMD")
+ "JOD" | mkCurrency("JOD")
+ "JPY" | mkCurrency("JPY")
+ "KES" | mkCurrency("KES")
+ "KGS" | mkCurrency("KGS")
+ "KHR" | mkCurrency("KHR")
+ "KMF" | mkCurrency("KMF")
+ "KPW" | mkCurrency("KPW")
+ "KRW" | mkCurrency("KRW")
+ "KWD" | mkCurrency("KWD")
+ "KYD" | mkCurrency("KYD")
+ "KZT" | mkCurrency("KZT")
+ "LAK" | mkCurrency("LAK")
+ "LBP" | mkCurrency("LBP")
+ "LKR" | mkCurrency("LKR")
+ "LRD" | mkCurrency("LRD")
+ "LSL" | mkCurrency("LSL")
+ "LYD" | mkCurrency("LYD")
+ "MAD" | mkCurrency("MAD")
+ "MDL" | mkCurrency("MDL")
+ "MGA" | mkCurrency("MGA")
+ "MKD" | mkCurrency("MKD")
+ "MMK" | mkCurrency("MMK")
+ "MNT" | mkCurrency("MNT")
+ "MOP" | mkCurrency("MOP")
+ "MRU" | mkCurrency("MRU")
+ "MUR" | mkCurrency("MUR")
+ "MVR" | mkCurrency("MVR")
+ "MWK" | mkCurrency("MWK")
+ "MXN" | mkCurrency("MXN")
+ "MXV" | mkCurrency("MXV")
+ "MYR" | mkCurrency("MYR")
+ "MZN" | mkCurrency("MZN")
+ "NAD" | mkCurrency("NAD")
+ "NGN" | mkCurrency("NGN")
+ "NIO" | mkCurrency("NIO")
+ "NOK" | mkCurrency("NOK")
+ "NPR" | mkCurrency("NPR")
+ "NZD" | mkCurrency("NZD")
+ "OMR" | mkCurrency("OMR")
+ "PAB" | mkCurrency("PAB")
+ "PEN" | mkCurrency("PEN")
+ "PGK" | mkCurrency("PGK")
+ "PHP" | mkCurrency("PHP")
+ "PKR" | mkCurrency("PKR")
+ "PLN" | mkCurrency("PLN")
+ "PYG" | mkCurrency("PYG")
+ "QAR" | mkCurrency("QAR")
+ "RON" | mkCurrency("RON")
+ "RSD" | mkCurrency("RSD")
+ "RWF" | mkCurrency("RWF")
+ "RUB" | mkCurrency("RUB")
+ "SAR" | mkCurrency("SAR")
+ "SBD" | mkCurrency("SBD")
+ "SCR" | mkCurrency("SCR")
+ "SDG" | mkCurrency("SDG")
+ "SEK" | mkCurrency("SEK")
+ "SGD" | mkCurrency("SGD")
+ "SHP" | mkCurrency("SHP")
+ "SLL" | mkCurrency("SLL")
+ "SOS" | mkCurrency("SOS")
+ "SRD" | mkCurrency("SRD")
+ "SSP" | mkCurrency("SSP")
+ "STN" | mkCurrency("STN")
+ "SVC" | mkCurrency("SVC")
+ "SYP" | mkCurrency("SYP")
+ "SZL" | mkCurrency("SZL")
+ "THB" | mkCurrency("THB")
+ "TJS" | mkCurrency("TJS")
+ "TMT" | mkCurrency("TMT")
+ "TND" | mkCurrency("TND")
+ "TOP" | mkCurrency("TOP")
+ "TRY" | mkCurrency("TRY")
+ "TTD" | mkCurrency("TTD")
+ "TWD" | mkCurrency("TWD")
+ "TZS" | mkCurrency("TZS")
+ "UAH" | mkCurrency("UAH")
+ "UGX" | mkCurrency("UGX")
+ "USN" | mkCurrency("USN")
+ "UYI" | mkCurrency("UYI")
+ "UYU" | mkCurrency("UYU")
+ "UZS" | mkCurrency("UZS")
+ "VEF" | mkCurrency("VEF")
+ "VND" | mkCurrency("VND")
+ "VUV" | mkCurrency("VUV")
+ "WST" | mkCurrency("WST")
+ "XAF" | mkCurrency("XAF")
+ "XCD" | mkCurrency("XCD")
+ "XDR" | mkCurrency("XDR")
+ "XOF" | mkCurrency("XOF")
+ "XPF" | mkCurrency("XPF")
+ "XSU" | mkCurrency("XSU")
+ "XUA" | mkCurrency("XUA")
+ "YER" | mkCurrency("YER")
+ "ZAR" | mkCurrency("ZAR")
+ "ZMW" | mkCurrency("ZMW")
+ "ZWL" | mkCurrency("ZWL")
+ }
+
+
+}
diff --git a/src/test/groovy/graphql/scalars/util/TestKit.groovy b/src/test/groovy/graphql/scalars/util/TestKit.groovy
index 60a2982..2a96dee 100644
--- a/src/test/groovy/graphql/scalars/util/TestKit.groovy
+++ b/src/test/groovy/graphql/scalars/util/TestKit.groovy
@@ -3,6 +3,7 @@ package graphql.scalars.util
import graphql.language.FloatValue
import graphql.language.IntValue
import graphql.language.StringValue
+import graphql.scalars.country.code.CountryCode
import java.time.LocalDate
import java.time.LocalDateTime
@@ -89,4 +90,11 @@ class TestKit {
return UUID.fromString(s)
}
+ static Currency mkCurrency(String currency) {
+ return Currency.getInstance(currency)
+ }
+
+ static CountryCode mkCountryCode(String countryCode) {
+ return CountryCode.valueOf(countryCode)
+ }
}