{"record":{"id":"8d65d2ca36faf1a9","repo":"floci-io/floci","slug":"invalid-awsemail","errorCode":null,"errorMessage":"Invalid AWSEmail: {}","messagePattern":"Invalid AWSEmail: (.+?)","errorType":"validation","errorClass":"CoercingParseValueException","httpStatus":null,"severity":"error","filePath":"src/main/java/io/github/hectorvent/floci/services/appsync/graphql/scalars/AppSyncScalars.java","lineNumber":178,"sourceCode":"            }\n        })\n        .build();\n\n    private static final Pattern EMAIL_PATTERN = Pattern.compile(\"^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\\\.[a-zA-Z]{2,}$\");\n\n    public static final GraphQLScalarType AWS_EMAIL = GraphQLScalarType.newScalar()\n        .name(\"AWSEmail\")\n        .description(\"An RFC 5322 email address\")\n        .coercing(new Coercing<String, String>() {\n            @Override\n            public String serialize(Object dataFetcherResult) {\n                return dataFetcherResult != null ? dataFetcherResult.toString() : null;\n            }\n            @Override\n            public String parseValue(Object input) {\n                String str = input.toString();\n                if (!EMAIL_PATTERN.matcher(str).matches())\n                    throw new CoercingParseValueException(\"Invalid AWSEmail: \" + str);\n                return str;\n            }\n            @Override\n            public String parseLiteral(Object input) {\n                if (!(input instanceof StringValue sv)) return null;\n                return parseValue(sv.getValue());\n            }\n        })\n        .build();\n\n    public static final GraphQLScalarType AWS_URL = GraphQLScalarType.newScalar()\n        .name(\"AWSURL\")\n        .description(\"A valid URL\")\n        .coercing(new Coercing<String, String>() {\n            @Override\n            public String serialize(Object dataFetcherResult) {\n                return dataFetcherResult != null ? dataFetcherResult.toString() : null;\n            }","sourceCodeStart":160,"sourceCodeEnd":196,"githubUrl":"https://github.com/floci-io/floci/blob/62ff490619e7bd3554597c28c704081b4c15add5/src/main/java/io/github/hectorvent/floci/services/appsync/graphql/scalars/AppSyncScalars.java#L160-L196","documentation":"Thrown by the AWSEmail scalar's parseValue when the string does not match the RFC-style email regex ^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,}$. The scalar validates syntactic shape only: local part, @, domain with dot, and a TLD of at least two letters.","triggerScenarios":"A GraphQL request sends \"user@@example.com\", \"user@example\" (no TLD), \"user @example.com\" (space), \"user@example.c\" (single-letter TLD), or an empty string as an AWSEmail variable.","commonSituations":"Missing client-side trim/validation before submit; copy-pasted addresses with trailing spaces or newlines; internationalized domains rendered with unicode (the pattern is ASCII-only); test fixtures using \"not-an-email\" or \"a@b\" placeholders.","solutions":["Validate (and trim) client-side before the request with an RFC 5322 or HTML5 email regex","Reject empty strings early with your own error message","For non-ASCII/international addresses, convert to punycode (IDN.toASCII) before sending","Use realistic fixtures like user@example.com in tests"],"exampleFix":"// before\nvariables.put(\"email\", \"  user@example \"); // fails pattern\n\n// after\nString email = raw.trim();\nif (!email.matches(\"^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\\\.[a-zA-Z]{2,}$\")) throw new IllegalArgumentException(\"bad email\");\nvariables.put(\"email\", email);","handlingStrategy":"validation","validationCode":"private static final Pattern EMAIL = Pattern.compile(\"^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\\\.[a-zA-Z]{2,}$\");\nString email = raw == null ? null : raw.trim();\nif (email != null && !EMAIL.matcher(email).matches()) throw new IllegalArgumentException(\"invalid email\");","typeGuard":"const isAwsEmail = (s: string): boolean => /^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,}$/.test(s.trim());","tryCatchPattern":"catch (CoercingParseValueException e) { // invalid input: mark the form field, do not retry as-is }","preventionTips":["Trim and validate email at the form boundary","Convert internationalized domains to punycode (IDN.toASCII) before sending","Keep email validation in one shared client util"],"tags":["graphql","appsync","awsemail","email","regex","validation"],"backgroundTag":null,"analyzedSha":"62ff490619e7bd3554597c28c704081b4c15add5","analyzedAt":"2026-08-14T14:25:23.764Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}