Example star wars done

This commit is contained in:
Tobe O 2019-04-11 13:46:04 -04:00
parent 8f98e801ab
commit 91701b56ad
4 changed files with 45 additions and 10 deletions

View file

@ -8,6 +8,11 @@ Map<String, dynamic> _fetchRequestInfo(Map<String, dynamic> arguments) {
};
}
Map<String, dynamic> _getQuery(Map<String, dynamic> arguments) {
var f = Map<String, dynamic>.from(arguments)..remove('id')..remove('data');
return f.isEmpty ? null : {};
}
/// A GraphQL resolver that `index`es an Angel service.
///
/// The arguments passed to the resolver will be forwarded to the service, and the
@ -16,7 +21,7 @@ GraphQLFieldResolver<List<Value>, Serialized>
resolveViaServiceIndex<Value, Serialized>(Service<dynamic, Value> service) {
return (_, arguments) async {
var _requestInfo = _fetchRequestInfo(arguments);
var params = {'query': arguments, 'provider': Providers.graphQL}
var params = {'query': _getQuery(arguments), 'provider': Providers.graphQL}
..addAll(_requestInfo);
return await service.index(params);
@ -32,7 +37,7 @@ GraphQLFieldResolver<Value, Serialized>
Service<dynamic, Value> service) {
return (_, arguments) async {
var _requestInfo = _fetchRequestInfo(arguments);
var params = {'query': arguments, 'provider': Providers.graphQL}
var params = {'query': _getQuery(arguments), 'provider': Providers.graphQL}
..addAll(_requestInfo);
return await service.findOne(params);
};
@ -50,7 +55,7 @@ GraphQLFieldResolver<Value, Serialized>
{String idField: 'id'}) {
return (_, arguments) async {
var _requestInfo = _fetchRequestInfo(arguments);
var params = {'query': arguments, 'provider': Providers.graphQL}
var params = {'query': _getQuery(arguments), 'provider': Providers.graphQL}
..addAll(_requestInfo);
var id = arguments.remove(idField);
return await service.read(id, params);
@ -70,8 +75,9 @@ GraphQLFieldResolver<Value, Serialized>
{String idField: 'id'}) {
return (_, arguments) async {
var _requestInfo = _fetchRequestInfo(arguments);
var params = {'query': arguments, 'provider': Providers.graphQL}
var params = {'query': _getQuery(arguments), 'provider': Providers.graphQL}
..addAll(_requestInfo);
print(params);
var id = arguments.remove(idField);
return await service.modify(id, arguments['data'] as Value, params);
};
@ -93,7 +99,7 @@ GraphQLFieldResolver<Value, Serialized>
{String idField: 'id'}) {
return (_, arguments) async {
var _requestInfo = _fetchRequestInfo(arguments);
var params = {'query': arguments, 'provider': Providers.graphQL}
var params = {'query': _getQuery(arguments), 'provider': Providers.graphQL}
..addAll(_requestInfo);
var id = arguments.remove(idField);
return await service.update(id, arguments['data'] as Value, params);
@ -112,7 +118,7 @@ GraphQLFieldResolver<Value, Serialized>
{String idField: 'id'}) {
return (_, arguments) async {
var _requestInfo = _fetchRequestInfo(arguments);
var params = {'query': arguments, 'provider': Providers.graphQL}
var params = {'query': _getQuery(arguments), 'provider': Providers.graphQL}
..addAll(_requestInfo);
var id = arguments.remove(idField);
return await service.remove(id, params);

View file

@ -4,6 +4,7 @@ import 'package:angel_framework/angel_framework.dart';
import 'package:angel_graphql/angel_graphql.dart';
import 'package:graphql_schema/graphql_schema.dart';
import 'package:graphql_server/graphql_server.dart';
import 'package:graphql_server/mirrors.dart';
import 'src/models/models.dart';
Future configureServer(Angel app) async {
@ -90,7 +91,11 @@ Future configureServer(Angel app) async {
// Next, create a GraphQL object, which will be passed to `graphQLHttp`, and
// used to mount a spec-compliant GraphQL endpoint on the server.
var graphQL = GraphQL(schema);
//
// The `mirrorsFieldResolver` is unnecessary in this case, because we are using
// `Map`s only, but if our services returned concrete Dart objects, we'd need
// this to allow GraphQL to read field values.
var graphQL = GraphQL(schema, defaultFieldResolver: mirrorsFieldResolver);
// Mount the GraphQL endpoint.
app.all('/graphql', graphQLHttp(graphQL));

View file

@ -1,10 +1,9 @@
import 'dart:async';
import 'package:graphql_parser/graphql_parser.dart';
import 'package:graphql_schema/graphql_schema.dart';
import 'introspection.dart';
/// Transforms any [Map] into `Map<String, dynamic>`.
Map<String, dynamic> foldToStringDynamic(Map map) {
return map == null
? null
@ -12,12 +11,21 @@ Map<String, dynamic> foldToStringDynamic(Map map) {
<String, dynamic>{}, (out, k) => out..[k.toString()] = map[k]);
}
/// A Dart implementation of a GraphQL server.
class GraphQL {
/// Any custom types to include in introspection information.
final List<GraphQLType> customTypes = [];
/// An optional callback that can be used to resolve fields from objects that are not [Map]s,
/// when the related field has no resolver.
final FutureOr<T> Function<T>(T, String, Map<String, dynamic>)
defaultFieldResolver;
GraphQLSchema _schema;
GraphQL(GraphQLSchema schema,
{bool introspect: true,
this.defaultFieldResolver,
List<GraphQLType> customTypes = const <GraphQLType>[]})
: _schema = schema {
if (customTypes?.isNotEmpty == true) {
@ -473,6 +481,14 @@ class GraphQL {
var field = objectType.fields.firstWhere((f) => f.name == fieldName);
if (field.resolve == null) {
if (defaultFieldResolver != null)
return await defaultFieldResolver(
objectValue, fieldName, argumentValues);
if (objectValue is Map) {
return objectValue[fieldName] as T;
}
return null;
} else {
return await field.resolve(objectValue, argumentValues) as T;
@ -571,7 +587,6 @@ class GraphQL {
var errors = <GraphQLExceptionError>[];
print(possibleTypes);
for (var t in possibleTypes) {
try {
var validation =

View file

@ -9,6 +9,15 @@ import 'package:angel_serialize/angel_serialize.dart';
import 'package:graphql_schema/graphql_schema.dart';
import 'package:recase/recase.dart';
/// Uses `dart:mirrors` to read field names from items. If they are Maps, performs a regular lookup.
T mirrorsFieldResolver<T>(objectValue, String fieldName,
[Map<String, dynamic> objectValues]) {
if (objectValue is Map)
return objectValue[fieldName] as T;
else
return reflect(objectValue).getField(Symbol(fieldName)).reflectee as T;
}
/// Reflects upon a given [type] and dynamically generates a [GraphQLType] that corresponds to it.
///
/// This function is aware of the annotations from `package:angel_serialize`, and works seamlessly