DEV Community

Cover image for Creating an email custom scalar to Apollo GraphQL
Kevin Martins
Kevin Martins

Posted on • Originally published at kevinmmartins.Medium

Creating an email custom scalar to Apollo GraphQL

Apollo logo

In this tutorial i will show how to implement an Email custom scalar to Apollo GraphQL.

Implement an email scalar isn’t a hard task but i will show in details.

You must implement the functions __parseValue, __serialize and __parseLiteral.

We need a regex to check the email, in this tutorial i used this one:

Email regex

First we must implement the __parseValue function. Basically we will just test the input type and check the input with our Regex:

__parseValue

After this we will implement the __serialize function , in our example let’s just return the value:

__serialize

And finally lets implement the __parseLiteral function , we will check the literal kind and check our regex with literal value:

__parseLiteral

And that’s it ! Our email custom scalar is done. You can check the complete code and the unit test below:

import { gql } from 'apollo-server-express'
import { GraphQLError } from 'graphql/error'
import { Kind } from 'graphql/language'
const EMAIL_REGEX = new RegExp(
/^[a-zA-Z0-9.!#$%&’*+/=?^_`{|}~-]+@[a-zA-Z0-9-]+(?:\.[a-zA-Z0-9-]+)*$/
)
const Email = gql`
"Scalar data representing email"
scalar Email
`
/* eslint-disable no-underscore-dangle */
export const resolver = {
Email: {
__parseValue(value) {
if (typeof value !== 'string') {
throw new TypeError('Value is not string')
}
if (!EMAIL_REGEX.test(value)) {
throw new TypeError(`Value is not a valid email address: ${value}`)
}
return value
},
__serialize(value) {
return value
},
__parseLiteral(ast) {
if (ast.kind !== Kind.STRING) {
throw new GraphQLError(
`Value is not string : ${ast.kind}`
)
}
if (!EMAIL_REGEX.test(ast.value)) {
throw new GraphQLError(`Value is not a valid email address: ${ast.value}`)
}
return ast.value
}
}
}
export default () => [
Email
]
import { Kind } from 'graphql/language'
import { resolver } from '../src/graphql/schema/types/scalar/email'
/* eslint-disable no-underscore-dangle */
const email = 'test@test'
const emailComplete = 'test@test.com'
describe('Email scalar', () => {
describe('when email is valid', () => {
it('serialize correctly with complete email', () => {
expect(resolver.Email.__serialize(emailComplete))
.to
.eql(emailComplete)
})
it('serialize correctly', () => {
expect(resolver.Email.__serialize(email))
.to
.eql(email)
})
it('parseValue correctly with complete email', () => {
expect(resolver.Email.__parseValue(emailComplete))
.to
.eql(emailComplete)
})
it('parseValue correctly', () => {
expect(resolver.Email.__parseValue(email))
.to
.eql(email)
})
it('parseLiteral correctly with complete email', () => {
expect(
resolver.Email.__parseLiteral({
value: emailComplete,
kind: Kind.STRING
}, {})
)
.to
.eql(emailComplete)
})
it('parseLiteral correctly', () => {
expect(
resolver.Email.__parseLiteral({
value: email,
kind: Kind.STRING
}, {})
)
.to
.eql(email)
})
})
describe('when email is invalid', () => {
describe('and not a string', () => {
it('parseValue', () => {
expect(() => resolver.Email.__parseValue(435))
.to
.throw(
'Value is not string'
)
})
it('parseLiteral', () => {
expect(() => resolver.Email.__parseLiteral({
value: '453',
kind: Kind.INT
}, {}))
.to
.throw('Value is not string : IntValue')
})
})
describe('and not an email address', () => {
it('parseValue', () => {
expect(() => resolver.Email.__parseValue('this is a test'))
.to
.throw('Value is not a valid email address: this is a test')
})
it('parseLiteral', () => {
expect(() => resolver.Email.__parseLiteral({
value: 'this is a test',
kind: Kind.STRING
}, {}))
.to
.throw('Value is not a valid email address')
})
})
})
})

I hope this helps !

Heroku

This site is built on Heroku

Join the ranks of developers at Salesforce, Airbase, DEV, and more who deploy their mission critical applications on Heroku. Sign up today and launch your first app!

Get Started

Top comments (0)