スカラ型とは、いくつかの種類がある GraphQL の型において最もプリミティブな値を表すものである。 組み込みスカラとカスタムスカラがある。
以下の 5 種類の組み込みスカラが用意されている
- Int
- Float
- String
- Boolean
- ID
scalar
キーワードを使うことで 独自のスカラ型を使用することができる。
どうシリアライズされるかやパースされるかは実装による。
カスタムスカラを提供してくれているパッケージ
ドキュメント を参考
// resolvers.ts
import { mergeResolvers } from "@graphql-tools/merge";
import { resolvers as scalarResolvers } from "graphql-scalars";
export const resolvers = mergeResolvers([
scalarResolvers,
// ...
]);
// schemas.ts
import { loadFilesSync } from "@graphql-tools/load-files";
import { mergeTypeDefs } from "@graphql-tools/merge";
import { typeDefs as scalarsTypeDefs } from "graphql-scalars";
import path from "path";
const typesArray = loadFilesSync(path.join(__dirname, "./**/*.graphql"));
const types = [scalarsTypeDefs, typesArray];
export const typeDefs = mergeTypeDefs(types);
使用したい graphql-scalars のカスタムスカラを定義
# schema.graphql
scalar EmailAddress
scalar DateTime
scalar URL
適切にバリデーションされるようになる
# schemas.graphql
type User {
id: ID!
name: String!
email: EmailAddress!
birthDate: DateTime!
homePage: URL
}
type Query {
users(url: URL!): [User]!
}
{
"errors": [
{
"message": "Value is not a valid email address: foo",
"locations": [
{
"line": 5,
"column": 5
}
],
"path": [
"users",
0,
"email"
],
"extensions": {
"code": "INTERNAL_SERVER_ERROR",
{
"errors": [
{
"message": "Variable \"$url\" got invalid value \"bar\"; Expected type \"URL\". Invalid URL",
"locations": [
{
"line": 1,
"column": 13
}
],
"extensions": {
"code": "BAD_USER_INPUT",
"exception": {
"stacktrace": [
"TypeError: Invalid URL",
そのまま型生成をしてしまうと any になってしまうので適切な型定義をする
// schemas.ts
// ・・・
export type Scalars = {
ID: string;
String: string;
Boolean: boolean;
Int: number;
Float: number;
DateTime: any;
EmailAddress: any;
URL: any;
};
// ・・・
any になるのを防ぐために設定の追加
defaultScalarType
を任意の型にすると、 any の代わりに設定した型になる
scalars
を設定すると、指定した型で上書きすることができる
# codegen.yml
config:
minify: true
defaultScalarType: unknown
scalars:
EmailAddress: string
// schemas.ts
// ・・・
export type Scalars = {
ID: string;
String: string;
Boolean: boolean;
Int: number;
Float: number;
DateTime: unknown;
EmailAddress: string;
URL: unknown;
};
// ・・・