mirror of
https://github.com/graphql-python/graphene.git
synced 2024-11-14 21:56:54 +03:00
155 lines
4.1 KiB
Python
155 lines
4.1 KiB
Python
import six
|
|
from graphql.language.ast import BooleanValue, FloatValue, IntValue, StringValue
|
|
|
|
from .base import BaseOptions, BaseType
|
|
from .unmountedtype import UnmountedType
|
|
|
|
|
|
class ScalarOptions(BaseOptions):
|
|
pass
|
|
|
|
|
|
class Scalar(UnmountedType, BaseType):
|
|
"""
|
|
Scalar Type Definition
|
|
|
|
The leaf values of any request and input values to arguments are
|
|
Scalars (or Enums) and are defined with a name and a series of functions
|
|
used to parse input from ast or variables and to ensure validity.
|
|
"""
|
|
|
|
@classmethod
|
|
def __init_subclass_with_meta__(cls, **options):
|
|
_meta = ScalarOptions(cls)
|
|
super(Scalar, cls).__init_subclass_with_meta__(_meta=_meta, **options)
|
|
|
|
serialize = None
|
|
parse_value = None
|
|
parse_literal = None
|
|
|
|
@classmethod
|
|
def get_type(cls):
|
|
"""
|
|
This function is called when the unmounted type (Scalar instance)
|
|
is mounted (as a Field, InputField or Argument)
|
|
"""
|
|
return cls
|
|
|
|
|
|
# As per the GraphQL Spec, Integers are only treated as valid when a valid
|
|
# 32-bit signed integer, providing the broadest support across platforms.
|
|
#
|
|
# n.b. JavaScript's integers are safe between -(2^53 - 1) and 2^53 - 1 because
|
|
# they are internally represented as IEEE 754 doubles.
|
|
MAX_INT = 2147483647
|
|
MIN_INT = -2147483648
|
|
|
|
|
|
class Int(Scalar):
|
|
"""
|
|
The `Int` scalar type represents non-fractional signed whole numeric
|
|
values. Int can represent values between -(2^53 - 1) and 2^53 - 1 since
|
|
represented in JSON as double-precision floating point numbers specified
|
|
by [IEEE 754](http://en.wikipedia.org/wiki/IEEE_floating_point).
|
|
"""
|
|
|
|
@staticmethod
|
|
def coerce_int(value):
|
|
try:
|
|
num = int(value)
|
|
except ValueError:
|
|
try:
|
|
num = int(float(value))
|
|
except ValueError:
|
|
return None
|
|
if MIN_INT <= num <= MAX_INT:
|
|
return num
|
|
|
|
serialize = coerce_int
|
|
parse_value = coerce_int
|
|
|
|
@staticmethod
|
|
def parse_literal(ast):
|
|
if isinstance(ast, IntValue):
|
|
num = int(ast.value)
|
|
if MIN_INT <= num <= MAX_INT:
|
|
return num
|
|
|
|
|
|
class Float(Scalar):
|
|
"""
|
|
The `Float` scalar type represents signed double-precision fractional
|
|
values as specified by
|
|
[IEEE 754](http://en.wikipedia.org/wiki/IEEE_floating_point).
|
|
"""
|
|
|
|
@staticmethod
|
|
def coerce_float(value):
|
|
# type: (Any) -> float
|
|
try:
|
|
return float(value)
|
|
except ValueError:
|
|
return None
|
|
|
|
serialize = coerce_float
|
|
parse_value = coerce_float
|
|
|
|
@staticmethod
|
|
def parse_literal(ast):
|
|
if isinstance(ast, (FloatValue, IntValue)):
|
|
return float(ast.value)
|
|
|
|
|
|
class String(Scalar):
|
|
"""
|
|
The `String` scalar type represents textual data, represented as UTF-8
|
|
character sequences. The String type is most often used by GraphQL to
|
|
represent free-form human-readable text.
|
|
"""
|
|
|
|
@staticmethod
|
|
def coerce_string(value):
|
|
if isinstance(value, bool):
|
|
return u"true" if value else u"false"
|
|
return six.text_type(value)
|
|
|
|
serialize = coerce_string
|
|
parse_value = coerce_string
|
|
|
|
@staticmethod
|
|
def parse_literal(ast):
|
|
if isinstance(ast, StringValue):
|
|
return ast.value
|
|
|
|
|
|
class Boolean(Scalar):
|
|
"""
|
|
The `Boolean` scalar type represents `true` or `false`.
|
|
"""
|
|
|
|
serialize = bool
|
|
parse_value = bool
|
|
|
|
@staticmethod
|
|
def parse_literal(ast):
|
|
if isinstance(ast, BooleanValue):
|
|
return ast.value
|
|
|
|
|
|
class ID(Scalar):
|
|
"""
|
|
The `ID` scalar type represents a unique identifier, often used to
|
|
refetch an object or as key for a cache. The ID type appears in a JSON
|
|
response as a String; however, it is not intended to be human-readable.
|
|
When expected as an input type, any string (such as `"4"`) or integer
|
|
(such as `4`) input value will be accepted as an ID.
|
|
"""
|
|
|
|
serialize = str
|
|
parse_value = str
|
|
|
|
@staticmethod
|
|
def parse_literal(ast):
|
|
if isinstance(ast, (StringValue, IntValue)):
|
|
return ast.value
|