Git Product home page Git Product logo

ferry's People

Contributors

2shrestha22 avatar aaahrens avatar agufagit avatar aliyazdi75 avatar anlumo avatar awaik avatar berserkore avatar budde377 avatar caffeineflo avatar doctorjohn avatar friebetill avatar gp4ck avatar janosroden avatar knaeckekami avatar micimize avatar odlund avatar pd4d10 avatar petrus-jvrensburg avatar smkhalsa avatar tarekkma avatar tberman avatar tpucci avatar valentinvignal avatar warrenisarobot avatar yamhoresh avatar yusukemorijapan avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

ferry's Issues

Flatten root operations

Currently, each operation gets normalized underneath its root type in the cache.

For example, the following query

query TestQuery($first: Int, $offset: Int) {
  posts(first: $first, offset: $offset) {
    __typename
    id
    title
  }
}

Might result in the following normalized cache:

final Map<String, dynamic> sharedNormalizedMap = {
  'Query': {
    '__typename': 'Query'
    'posts({"first": 1, "offset":0})': [
      {'\$ref': 'Post:123'}
    ]
  },
  'Post:123': {
    'id': '123',
    '__typename': 'Post',
    'title': 'My awesome blog post',
  },
};

Since all queries exist under the root Query key, individual queries cannot be easily evicted.

I propose we flatten root operations. The same example above would then look like this:

final Map<String, dynamic> sharedNormalizedMap = {
  'Query:posts({"first": 1, "offset":0})': {
    '__typename': 'Query'
    'posts({"first": 1, "offset":0})': [
      {'\$ref': 'Post:123'}
    ]
  },
  'Post:123': {
    'id': '123',
    '__typename': 'Post',
    'title': 'My awesome blog post',
  },
};

If we were to execute the same query with different args, our cache might look like this:

final Map<String, dynamic> sharedNormalizedMap = {
  'Query:posts({"first": 1, "offset":0})': {
    '__typename': 'Query'
    'posts({"first": 1, "offset":0})': [
      {'\$ref': 'Post:123'}
    ]
  },
  'Query:posts({"first": 1, "offset":1})': {
    '__typename': 'Query'
    'posts({"first": 1, "offset":1})': [
      {'\$ref': 'Post:456'}
    ]
  },
  'Post:123': {
    'id': '123',
    '__typename': 'Post',
    'title': 'My awesome blog post',
  },
  'Post:456': {
    'id': '456',
    '__typename': 'Post',
    'title': 'My second blog post',
  },
};

custom scalars error

build

targets:
  $default:
    builders:
      gql_build|schema_builder:
        enabled: true
        options:
          type_overrides:
            jsonb:
              name: DateTime
            timestamp:
              name: DateTime  
      gql_build|ast_builder:
        enabled: true
      gql_build|data_builder:
        enabled: true
        options:
          schema: app|lib/schema.graphql
      gql_build|var_builder:
        enabled: true
        options:
          schema: app|lib/schema.graphql
      gql_build|serializer_builder:
        enabled: true
        options:
          schema: app|lib/schema.graphql

      ferry_generator|req_builder:
        enabled: true
        options:
          schema: app|lib/schema.graphql

error message

Error in BuiltValueGenerator for abstract class Ginsert_missionVars implements Built<Ginsert_missionVars, dynamic>.
Please make the following changes to use BuiltValue:

1. Make field end_time have non-dynamic type. If you are already specifying a type, please make sure the type is correctly imported.

CacheAndNetwork and offline

Hi!

In app I use FetchPolicy.CacheAndNetwork for query.

When I disable internet on phone or internet very bad, but data is set in cache, I get this error.

It is normal logic for CacheAndNetwork?

DeepinScreenshot_выберите-область_20200407174812

The getter 'loading' was called on null.
Receiver: null
Tried calling: loading

When I use query without FetchPolicy, data is set in cache and disable internet, it is ok.

Fix example

The example pokemon details page doesn't load. It may be an issue with the Dgraph slash server

normalize with the 0.4.2 version is not a good thing

When I run ferry_graphql, get a error.

../../development/flutter/.pub-cache/hosted/pub.flutter-io.cn/ferry-0.7.4/lib/src/cache.dart:284:23: Error: Method not found: 'reachableDataIds'.
    final reachable = utils.reachableDataIds(                           
                      ^^^^^^^^^^^^^^^^                                  
                                                                        
                                                                        
FAILURE: Build failed with an exception.                                
                                                                        
* Where:                                                                
Script '/Users/huangzheng/development/flutter/packages/flutter_tools/gradle/flutter.gradle' line: 904
                                                                        
* What went wrong:                                                      
Execution failed for task ':app:compileFlutterBuildDebug'.    

I recommend making normalize version 0.5

After update to 0.3.0: Undefined name 'ResponseSource'

Hi!

Updated ferry yesterday in an error appeared.
When testing on the gql-dart / improve-errors branch, everything was fine.

error: Undefined name 'ResponseSource'.

DeepinScreenshot_выберите-область_20200424084204

DeepinScreenshot_выберите-область_20200424085844

When I disable internet on phone.

DeepinScreenshot_выберите-область_20200424085426
DeepinScreenshot_выберите-область_20200424085320

Maybe I didn’t install the new package correctly?

Response stream initial request

I'm wondering whether the 'initial' request performed within the Client.responseStream method is required or can be made controllable.

In my use case I want to setup a response stream listener when a screen is displayed, without implicitly triggering a request. The initial request is particular annoying when its a mutation the user first has to provide arguments for.

As far as I can tell, making the initial request disableable, but enabled by default for backwards compatibility, would hurt, right?

Need a way to refetch the query

There is currently no way to refetch a query manually with the same variables.

Even if the fetch policy includes the network i.e. CacheAndNetwork, I currently have to use a key to force the parent widget of the query to reload when refetch is required.

Ideally, the network policy could be set to CacheFirst and then the query manually refetched as required.

Updating Firebase token for client

Hello, I've started implementing your package and have difficulties with updating the client token for Firebase.
They issue a new token every 3600 seconds. So, I have to have a reliable way to update it in the app.
Right now you in your example you suggest using such an approach

import 'package:gql_http_link/gql_http_link.dart';
import 'package:ferry/ferry.dart';
import 'package:hive/hive.dart';
import 'package:hive_flutter/hive_flutter.dart';

Future<Client> initClient() async {
  await Hive.initFlutter();

  final box = await Hive.openBox("graphql");

  final store = HiveStore(box);

  final cache = Cache(dataStore: store);

  final link = HttpLink("https://graphql-pokemon.now.sh/graphql");

  final client = Client(
    link: link,
    cache: cache,
  );

  return client;
}

I tried to make reliable updating for connecting with the short living token, but I failed. If you have some best practices for this, can you please share?

Maybe, it could be useful to add update() method to Client

class Client {
  final Link link;
  final Cache cache;
  final ClientOptions options;

Thank you for such a nice plugin!

Not able to correctly generate the code

output after run pub run build_runner build --delete-conflicting-outputs

[INFO] Generating build script completed, took 483ms
[WARNING] Configuring `gql_build:serializer_builder` in target `app:app` but this is not a known Builder
[INFO] Reading cached asset graph completed, took 73ms
[INFO] Checking for updates since last build completed, took 1.0s
[INFO] Running build completed, took 23ms
[INFO] Caching finalized dependency graph completed, took 79ms
[INFO] Succeeded after 115ms with 0 outputs (0 actions)

error in the generated file test.req.gql.dart
Target of URI doesn't exist: 'package:app/gql/query/test.op.gql.dart'. Try creating the file referenced by the URI, or Try using a URI for a file that does exist

Any solutions?

Thanks

prevent subscription from adding __typename

As per the GraphQL spec, subscriptions must include one and only one root field including introspection fields.

I have a MessageReceived subscription with one root field:

subscription MessageReceived {
    messageReceived {
        prevMessageTimestamp
        message {
            ...on TextMessage {
                ...FullTextMessage
            }
            ...on RecordingMessage {
                ...FullRecordingMessage
            }
            ...on TypingMessage {
                ...FullTypingMessage
            }
            ...on PresenceMessage {
                ...FullPresenceMessage
            }
        }
    }
}

and for some reason I get Subscription "MessageReceived" must select only one top level field. error message.

I hight suspect that addTypename functionality automatically adds __typename to my subscription and therefore invalidating it.

  1. Is there a way to prevent a certain request from adding the __typename?
  2. In general I think we should prevent addTypename on the root Subscription type.

Offline mutation support

Description

With optimistic cache make the mutation without the internet connection. After that turn on the connection.

Error code

[VERBOSE-2:ui_dart_state.cc(157)] Unhandled Exception: 
#0      IOClient.send (package:http/src/io_client.dart:65:7)
<asynchronous suspension>
#1      BaseClient._sendUnstreamed (package:http/src/base_client.dart:176:38)
#2      BaseClient.post (package:http/src/base_client.dart:58:7)
#3      HttpLink.request (package:gql_http_link/src/link.dart:99:44)
<asynchronous suspension>
#4      Client._networkResponseStream (package:ferry/src/client/client.dart:146:12)
#5      Client._optimisticNetworkResponseStream (package:ferry/src/client/client.dart:128:13)
#6      Client._responseStream (package:ferry/src/client/client.dart:88:16)
#7      Client.responseStream.<anonymous closure> (package:ferry/src/client/client.dart:49:29)
#8      SwitchMapStreamTransformer._buildTransformer.<anonymous closure>.<anonymous closure>.<anonymous closure> (package:rxdart/src/transformers/switch_map.dart:55:47)
#9      _rootRunUnary (dart:async/zone.dart:1134:38)
#10     _CustomZone.runUnary (dart:async/zone.dart:1031:19)
#11<…>

Screenshots

It took 60 seconds to get the issue, sorry for the long animated gif.

ezgif com-video-to-gif (1)

[normalize] Asking the same object in the same operation with less fields results in a failure to cache the operation

I'll explain this bug with an example:

type Person implements Node {
    id: ID!
    firstName: String!
    lastName: String!
}

type Message implements Node {
    id: ID!
    content: String!
    sender: Person!
}

type Viewer implements Node {
    id: ID!
    friends: [Person!]!
    latestMessage: Message!
}

type Query {
    viewer: Viewer!
}

And let's say in the main screen of my app I want to display a list of friends (first name + last name) and my latest message: (only first name is shown in the sender line of messages on my app)

query FetchMainScreen {
    viewer {
        friends {
            id
            firstName
            lastName
        }
        latestMessage {
            id
            content
            sender {
                id
                firstName
            }
        }
    }
}

When I fetch this query the first time: _client.responseStream(GFetchMainScreenReq()) using a cache-enabled fetch policy, it will write the normalized data to the cache. But during this process it will override one sender with only firstName attached to it. (because the latestMessage's sender is parsed after the friends list, and it only contains firstName)

So if I run _client.cache.readQuery(GFetchMainScreenReq()) immediately after it will return null because a PartialDataException is raised.

This can't be right, as I just executed this query, and now it's by-design stays partial in the cache.

If, say, I rewrite the query above like that: (latestMessage first, friends after)

query FetchMainScreen {
    viewer {
        latestMessage {
            id
            content
            sender {
                id
                firstName
            }
        }
        friends {
            id
            firstName
            lastName
        }
    }
}

The cache works as expected (since the overwrite just added a lastName field to the sender)

The source of this issue to my understanding is at normalize_node.dart:75

        if (fieldPolicy?.merge != null) {
          return data
            ..[fieldName] = fieldPolicy.merge(
              existingFieldData,
              fieldData,
              FieldFunctionOptions(
                field: field,
                config: config,
              ),
            );
        }
        // ->>>>>>>>> This overrides the previous person that was normalized in this operation with less complete data.
        return data..[fieldName] = fieldData; 

I would suggest implementing a default deepMerge (as indeed happens in across-queries writes to the cache) even if I didn't implement a custom merge in a field policy.

Link does not get notified when stream isn't listened anymore

Hi,

I think it would be nice if a custom Link would get notified when the Stream it is returning in it's request method isn't being listened to anymore.
This would allow for the Link to cancel a Subscription automatically once no one is listening anymore, or to clean up other resources.

Currently, this is not the case.

This can be shown in this test case, which will time out:

import 'dart:async';

import 'package:ferry/ferry.dart';
import 'package:gql_exec/gql_exec.dart';
import 'package:gql_exec/src/response.dart';
import 'package:test/test.dart';

import './graphql/all_pokemon.req.gql.dart';


class _StreamCancelTestLink extends Link {
  final Completer hasCanceledStreamCompleter = Completer();

  @override
  Stream<Response> request(Request request, [forward]) async* {
    StreamController<Response> controller =
        StreamController(onCancel: () => print("oncancel controller"));
    StreamSubscription sub;
    try {
      //simulate events coming in, e.g. from a websocket
      sub =
          Stream.periodic(Duration(microseconds: 1), (_) => Response(data: {}))
              .listen(controller.add);
      //yield* should finish when the client stops listening
      yield* controller.stream;
    } finally {
      //this gets called when the client stops listening to the stream
      sub?.cancel();
      controller.close();

      hasCanceledStreamCompleter.complete();
    }
  }
}

void main() {
  test("Can cleanup", () async {
    final link = _StreamCancelTestLink();

    final client = Client(link: link);
    final req1 = AllPokemon(
        fetchPolicy: FetchPolicy.NetworkOnly, buildVars: (b) => b..first = 3);
    expect(link.hasCanceledStreamCompleter.isCompleted, isFalse);
    StreamSubscription subscription;
    subscription = client.responseStream(req1).skip(1).listen((event) async {
      //cancel subscription after first item
      //this ensures the the link.request() method is entered
      await subscription.cancel();
    });
    // the link should complete its "yield*" statement when the subscription is cancelled
    // and complete its completer
    await link.hasCanceledStreamCompleter.future;

    expect(link.hasCanceledStreamCompleter.isCompleted, isTrue);
  });

}

I think with two small changes to the Ferry client we can get this behavior. I will open PRs with these changes shortly.

Can you override the default `DateTime` serializer?

Loving the library so far but I have a couple questions...

I got the rest of my schema working properly, along with other custom scalars, but DateTime still seems to default to using the default serializer which only returns a string, and its also converting it to GDateTime. If I include a custom DateTimeSerializer it ignores it. Is there a better way to ensure it gets properly deserialized into a proper DateTime object? I'm pulling in a Prisma schema FYI.

abstract class GDateTime implements Built<GDateTime, GDateTimeBuilder> {
  GDateTime._();

  factory GDateTime([String value]) =>
      _$GDateTime((b) => value != null ? (b..value = value) : b);

  String get value;
  @BuiltValueSerializer(custom: true)
  static Serializer<GDateTime> get serializer =>
      _i1.DefaultScalarSerializer<GDateTime>(
          (Object serialized) => GDateTime(serialized));
}
import 'package:built_value/serializer.dart';

class DateTimeSerializer implements PrimitiveSerializer<DateTime> {
  @override
  DateTime deserialize(
    Serializers serializers,
    Object serialized, {
    FullType specifiedType = FullType.unspecified,
  }) {
    assert(serialized is String,
        "DateSerializer expected 'String' but got ${serialized.runtimeType}");
    return DateTime.parse(serialized.toString());
  }

  @override
  Object serialize(
    Serializers serializers,
    DateTime date, {
    FullType specifiedType = FullType.unspecified,
  }) =>
      date.toIso8601String();

  @override
  Iterable<Type> get types => [DateTime];

  @override
  String get wireName => 'DateTime';
}

Release normalize hotfix

There's this bug (#81) that prevents me from using the published version of normalize (I override using direct GitHub reference)
The fix was already merged into master but was never released.

Expanding fragments defined on interfaces

The expandFragments function in the normalize package only includes fragments if their type name matches the data objects type name. This is a problem if the fragment is defined on an interface. GraphQL servers return concrete typed data even when a query contains an fragment that is defined on an interface.

As an example consider the following type, interface and query (slightly inspired by the github graphql api):

interface Actor {
    id: ID!
    avatarUrl: String!
}

type User implements Actor {
    id: ID!
    avatarUrl: String!
    name: String!
}
query Users {
    users {
      ... ActorInfo
    }
}

fragment ActorInfo on Actor {
    __typename
    id
    avatarUrl
}

A response to this query could look something like this:

"users": [
    {
        "__typename": "User",
         "id": "1",
         "avatarUrl": "http://example.com/avatar.png"
    }
]

Running normalize on it should return the following normalized map:

"Query": {
    "users": [
        {
            "$ref": "UserType:1"
        },
    ],
},
"User:1": {
    "__typename": "User",
    "id": "1",
    "avatarUrl": "http://example.com/avatar.png",
}

In expandFragments the normalized map (variable data) is used to perform the following check:

// Only include this fragment if the type name matches
if (fragment.typeCondition.on.name.value == data["__typename"]) {
    // ...
}

The fragments type name will be Actor but the datas (concrete) type will be User, thus the fragment wont't be included.

Use embedded graphql strings instead of seperate .graphql files

Hey guys,
as I discussed in the Feedback issue (#1) I suggested a better (IMO) way of structuring the widgets and data requirements based on the design of react-relay.

I will try to lay here the way I think it should work.

GQLClientProvider

In relay, there is one object that manages the dispatching and processing of queries, subscriptions, mutations etc. It quite naturally translates to a GQLClientProvider here that all widgets in the tree will know to reference when wanting to perform some graphql operation.

  @override
  Widget build(BuildContext context) {
    return GQLClientProvider(
      client: _buildClient();
      child: MaterialApp(...)
    );
  }

Queries widgets, fragment widgets

The strength of relay, as stated in numerous lectures online, is its ability to localize and couple components and their data requirements. That way, it is less likely to add/remove component behaviour while forgetting to adjust the data requirements accordingly.

@query(r"""
query FetchArticle($articleId: ID!) {
  article($articleId) {
    title
    publicationDate

    ...ArticleAuthor_author
    ...ArticleComments_comments
  }
}
""")
class Article with $FetchArticleQuery extends StatelessWidget {

  final String articleId;
  const Article({Key key, this.articleId}) : super(key: key);

  // The actual build method is generated and sits in $FetchArticleQuery

  buildVars() => $FetchArticleQuery$Vars(articleId: this.articleId);

  Widget buildLoading(BuildContext context) {
    return CircularProgressIndicator();
  }

  Widget buildError(BuildContext, Error error) {
    return Text("$error");
  }

  @override
  Widget buildResult(BuildContext context, $FetchArticleQuery$Response data) {
    // Note how I don't have access here to author and comments
    // since they go directly through context to ArticleAuthor and ArticleComments.
    // This is "data-masking"

    return Column(
      children: [
        Text(data.article.title),
        Text(data.article.publicationDate.toString()),
        
        ArticleAuthor(),

        ArticleComments(),

      ]
    );
  }
}

@fragment(r"""
  fragment ArticleComments_comments {
    title,
    author {
      name
    }
  }
""")
class ArticleComments with $ArticleComments_commentsFragment extends StatelessWidget {
  
  const ArticleComments({Key key}) : super(key: key);
  // Here we don't need loading and error since it's only rendered after parent query was executed
  @override
  Widget buildFragment(BuildContext context, ArticleComments_commentsFragment$Data data) {
    return Column(
      children: data.map((comment) => Text(comment.title + comment.author.name))
    );
  }
}

@fragment("""
fragment ArticleAuthor_author {
  name
}
""")
class ArticleAuthor with $ArticleAuthor_authorFragment extends StatelessWidget {
  const ArticleAuthor({Key key}) : super(key: key);

  @override
  Widget buildFragment(BuildContext context, ArticleComments_authorFragment$Data data) {
    return Text(data.name);
  }
}

It's just a quick thought process, I'm not sure how to handle pagination, caching, offline mutations and so on. but it's a start. LMK what you think.

Rename package

I've been thinking about renaming this package to something more unique rather than descriptive. Since it's based on dart streams, I've been thinking about something stream-related.

One option is "ferry" since the package ferries data around through streams. It'd also be easy to create a memorable "ferry" icon.

Thoughts on this or other names?

For Flutter Web: AssetNotFoundException: lib/main_prod_web_entrypoint.ddc.js

Following the instruction, for Flutter Web getting the below error. Suppose, this is because gql_build is not yet available for Flutter Web. Otherwise, please assist :

Launching lib/main.dart on Chrome in debug mode...
Building application for the web...
Configuring `gql_build:schema_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Configuring `gql_build:ast_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Configuring `gql_build:op_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Configuring `gql_build:data_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Configuring `gql_build:var_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Configuring `gql_build:fragment_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Configuring `gql_client:req_builder` in target `realspaceweb:realspaceweb` but this is not a known Builder
Error creating realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill
Error creating kernel summary for module:realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill

Response:--dart-sdk-output=/private/var/folders/nr/yvt4wkdn3p9_dy_6b5bc3zxh0000gn/T/scratch_space0jEMkm/packages/realspaceweb/widgets/search/SearchLocationButton.ddc.dill --packages-file=file:///var/folders/nr/yvt4wkdn3p9_dy_6b5bc3zxh0000gn/T/kernel_builder_3SGhES/.packages --multi-root-scheme=org-dartlang-app --exclude-non-sources --summary-only --target=ddc --libraries-file=file:///Users/user/Dropbox/BUSINESS/Soft/flutter/bin/cache/flutter_web_sdk/libraries.json --reuse-compiler-result --use-incremental-compiler --used-inputs=/var/folders/nr/yvt4wkdn3p9_dy_6b5bc3zxh0000gn/T/kernel_builder_XAvEiZ/used_inputs.txt --input-summary=org-dartlang-app:///packages/expandable/expandable.ddc.dill --input-summary=org-dartlang-app:///packages/gql_client/gql_client.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/material.ddc.dill --input-summary=org-dartlang-app:///packages/font_awesome_flutter/font_awesome_flutter.ddc.dill --input-summary=org-dartlang-app:///packages/gql_http_link/gql_http_link.ddc.dill --input-summary=org-dartlang-app:///packages/normalize/normalize.ddc.dill --input-summary=org-dartlang-app:///packages/gql_exec/gql_exec.ddc.dill --input-summary=org-dartlang-app:///packages/meta/meta.ddc.dill --input-summary=org-dartlang-app:///packages/hive/hive.ddc.dill --input-summary=org-dartlang-app:///packages/built_value/built_value.ddc.dill --input-summary=org-dartlang-app:///packages/gql/ast.ddc.dill --input-summary=org-dartlang-app:///packages/rxdart/rxdart.ddc.dill --input-summary=org-dartlang-app:///packages/gql_link/gql_link.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/gestures.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/foundation.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/cupertino.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/widgets.ddc.dill --input-summary=org-dartlang-app:///packages/vector_math/vector_math_64.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/semantics.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/rendering.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/animation.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/painting.ddc.dill --input-summary=org-dartlang-app:///packages/font_awesome_flutter/icon_data.ddc.dill --input-summary=org-dartlang-app:///packages/http/http.ddc.dill --input-summary=org-dartlang-app:///packages/gql_exec/exec/response.ddc.dill --input-summary=org-dartlang-app:///packages/gql_exec/exec/context.ddc.dill --input-summary=org-dartlang-app:///packages/gql_exec/exec/request.ddc.dill --input-summary=org-dartlang-app:///packages/gql_exec/exec/error.ddc.dill --input-summary=org-dartlang-app:///packages/gql_exec/exec/operation.ddc.dill --input-summary=org-dartlang-app:///packages/crypto/crypto.ddc.dill --input-summary=org-dartlang-app:///packages/gql/src/ast/ast.ddc.dill --input-summary=org-dartlang-app:///packages/rxdart/transformers.ddc.dill --input-summary=org-dartlang-app:///packages/rxdart/src/streams/never.ddc.dill --input-summary=org-dartlang-app:///packages/gql/language.ddc.dill --input-summary=org-dartlang-app:///packages/collection/collection.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/gestures/arena.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/foundation/_bitfield_web.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/cupertino/action_sheet.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/widgets/actions.ddc.dill --input-summary=org-dartlang-app:///packages/vector_math/hash.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/semantics/binding.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/rendering/animated_size.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/animation/animation.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/painting/_network_image_web.ddc.dill --input-summary=org-dartlang-app:///packages/http/src/base_client.ddc.dill --input-summary=org-dartlang-app:///packages/http_parser/http_parser.ddc.dill --input-summary=org-dartlang-app:///packages/typed_data/typed_data.ddc.dill --input-summary=org-dartlang-app:///packages/convert/convert.ddc.dill --input-summary=org-dartlang-app:///packages/source_span/source_span.ddc.dill --input-summary=org-dartlang-app:///packages/collection/src/algorithms.ddc.dill --input-summary=org-dartlang-app:///packages/collection/src/utils.ddc.dill --input-summary=org-dartlang-app:///packages/collection/src/iterable_zip.ddc.dill --input-summary=org-dartlang-app:///packages/collection/src/comparators.ddc.dill --input-summary=org-dartlang-app:///packages/collection/src/priority_queue.ddc.dill --input-summary=org-dartlang-app:///packages/collection/src/canonicalized_map.ddc.dill --input-summary=org-dartlang-app:///packages/typed_data/typed_buffers.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/physics.ddc.dill --input-summary=org-dartlang-app:///packages/pedantic/pedantic.ddc.dill --input-summary=org-dartlang-app:///packages/string_scanner/src/eager_span_scanner.ddc.dill --input-summary=org-dartlang-app:///packages/charcode/ascii.ddc.dill --input-summary=org-dartlang-app:///packages/path/path.ddc.dill --input-summary=org-dartlang-app:///packages/term_glyph/src/generated/ascii_glyph_set.ddc.dill --input-summary=org-dartlang-app:///packages/charcode/charcode.ddc.dill --input-summary=org-dartlang-app:///packages/flutter/src/physics/clamped_simulation.ddc.dill --input-summary=org-dartlang-app:///packages/charcode/html_entity.ddc.dill --source=package:realspaceweb/widgets/search/SearchLocationButton.dart
Crash when compiling package:realspaceweb/config/AppConfig.dart,
at character offset null:
Reference to root::package:gql_client/src/store//memory_store.dart is not bound to an AST node. A library was expected
#0      Reference.asLibrary (package:kernel/ast.dart:265:7)
#1      LibraryDependency.targetLibrary (package:kernel/ast.dart:642:57)
#2      SourceLoader.computeFullComponent (package:front_end/src/fasta/source/source_loader.dart:873:38)
#3      SourceLoader.computeHierarchy (package:front_end/src/fasta/source/source_loader.dart:890:38)
#4      KernelTarget.buildOutlines.<anonymous closure> (package:front_end/src/fasta/kernel/kernel_target.dart:275:14)
<asynchronous suspension>
#5      withCrashReporting (package:front_end/src/fasta/crash.dart:122:24)
#6      KernelTarget.buildOutlines (package:front_end/src/fasta/kernel/kernel_target.dart:252:12)
#7      IncrementalCompiler.computeDelta.<anonymous closure> (package:front_end/src/fasta/incremental_compiler.dart:462:52)
<asynchronous suspension>
#8      CompilerContext.runInContext.<anonymous closure>.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:46)
#9      new Future.sync (dart:async/future.dart:224:31)
#10     CompilerContext.runInContext.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:19)
#11     _rootRun (dart:async/zone.dart:1126:13)
#12     _CustomZone.run (dart:async/zone.dart:1023:19)
#13     _runZoned (dart:async/zone.dart:1518:10)
#14     runZoned (dart:async/zone.dart:1465:12)
#15     CompilerContext.runInContext (package:front_end/src/fasta/compiler_context.dart:122:12)
#16     IncrementalCompiler.computeDelta (package:front_end/src/fasta/incremental_compiler.dart:156:20)
#17     computeKernel (file:///b/s/w/ir/cache/builder/src/third_party/dart/utils/bazel/kernel_worker.dart:320:10)
<asynchronous suspension>
#18     KernelWorker.performRequest (file:///b/s/w/ir/cache/builder/src/third_party/dart/utils/bazel/kernel_worker.dart:69:26)
#19     AsyncWorkerLoop.run.<anonymous closure> (package:bazel_worker/src/worker/async_worker_loop.dart:33:41)
#20     _rootRun (dart:async/zone.dart:1126:13)
#21     _CustomZone.run (dart:async/zone.dart:1023:19)
#22     _runZoned (dart:async/zone.dart:1518:10)
#23     runZoned (dart:async/zone.dart:1465:12)
#24     AsyncWorkerLoop.run (package:bazel_worker/src/worker/async_worker_loop.dart:33:26)
<asynchronous suspension>
#25     main (file:///b/s/w/ir/cache/builder/src/third_party/dart/utils/bazel/kernel_worker.dart:38:48)
#26     _startIsolate.<anonymous closure> (dart:isolate-patch/isolate_patch.dart:303:32)
#27     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:174:12)


#0      Reference.asLibrary (package:kernel/ast.dart:265:7)
#1      LibraryDependency.targetLibrary (package:kernel/ast.dart:642:57)
#2      SourceLoader.computeFullComponent (package:front_end/src/fasta/source/source_loader.dart:873:38)
#3      SourceLoader.computeHierarchy (package:front_end/src/fasta/source/source_loader.dart:890:38)
#4      KernelTarget.buildOutlines.<anonymous closure> (package:front_end/src/fasta/kernel/kernel_target.dart:275:14)
<asynchronous suspension>
#5      withCrashReporting (package:front_end/src/fasta/crash.dart:122:24)
#6      KernelTarget.buildOutlines (package:front_end/src/fasta/kernel/kernel_target.dart:252:12)
#7      IncrementalCompiler.computeDelta.<anonymous closure> (package:front_end/src/fasta/incremental_compiler.dart:462:52)
<asynchronous suspension>
#8      CompilerContext.runInContext.<anonymous closure>.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:46)
#9      new Future.sync (dart:async/future.dart:224:31)
#10     CompilerContext.runInContext.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:19)
#11     _rootRun (dart:async/zone.dart:1126:13)
#12     _CustomZone.run (dart:async/zone.dart:1023:19)
#13     _runZoned (dart:async/zone.dart:1518:10)
#14     runZoned (dart:async/zone.dart:1465:12)
#15     CompilerContext.runInContext (package:front_end/src/fasta/compiler_context.dart:122:12)
#16     IncrementalCompiler.computeDelta (package:front_end/src/fasta/incremental_compiler.dart:156:20)
#17     computeKernel (file:///b/s/w/ir/cache/builder/src/third_party/dart/utils/bazel/kernel_worker.dart:320:10)
<asynchronous suspension>
#18     KernelWorker.performRequest (file:///b/s/w/ir/cache/builder/src/third_party/dart/utils/bazel/kernel_worker.dart:69:26)
#19     AsyncWorkerLoop.run.<anonymous closure> (package:bazel_worker/src/worker/async_worker_loop.dart:33:41)
#20     _rootRun (dart:async/zone.dart:1126:13)
#21     _CustomZone.run (dart:async/zone.dart:1023:19)
#22     _runZoned (dart:async/zone.dart:1518:10)
#23     runZoned (dart:async/zone.dart:1465:12)
#24     AsyncWorkerLoop.run (package:bazel_worker/src/worker/async_worker_loop.dart:33:26)
<asynchronous suspension>
#25     main (file:///b/s/w/ir/cache/builder/src/third_party/dart/utils/bazel/kernel_worker.dart:38:48)
#26     _startIsolate.<anonymous closure> (dart:isolate-patch/isolate_patch.dart:303:32)
#27     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:174:12)




AssetNotFoundException: realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill
Error compiling dartdevc module:realspaceweb|lib/widgets/search/SearchLocationButton.ddc.js

We're sorry, you've found a bug in our compiler.
You can report this bug at:
    https://github.com/dart-lang/sdk/issues/labels/web-dev-compiler
Please include the information below in your report, along with
any other information that may help us track it down. Thanks!
-------------------- %< --------------------
    dartdevc -k arguments: --kernel --dart-sdk-dill --modules=amd --no-summarize -o packages/realspaceweb/widgets/search/SearchLocationButton.ddc.js --source-map --summary=packages/meta/meta.ddc.dill=packages/meta/meta --summary=packages/typed_data/typed_buffers.ddc.dill=packages/typed_data/typed_buffers --summary=packages/flutter/src/foundation/_bitfield_web.ddc.dill=packages/flutter/src/foundation/_bitfield_web --summary=packages/flutter/foundation.ddc.dill=packages/flutter/foundation --summary=packages/vector_math/hash.ddc.dill=packages/vector_math/hash --summary=packages/vector_math/vector_math_64.ddc.dill=packages/vector_math/vector_math_64 --summary=packages/flutter/src/physics/clamped_simulation.ddc.dill=packages/flutter/src/physics/clamped_simulation --summary=packages/flutter/physics.ddc.dill=packages/flutter/physics --summary=packages/collection/src/utils.ddc.dill=packages/collection/src/utils --summary=packages/collection/src/algorithms.ddc.dill=packages/collection/src/algorithms --summary=packages/collection/src/iterable_zip.ddc.dill=packages/collection/src/iterable_zip --summary=packages/collection/src/comparators.ddc.dill=packages/collection/src/comparators --summary=packages/collection/src/priority_queue.ddc.dill=packages/collection/src/priority_queue --summary=packages/collection/src/canonicalized_map.ddc.dill=packages/collection/src/canonicalized_map --summary=packages/collection/collection.ddc.dill=packages/collection/collection --summary=packages/flutter/src/gestures/arena.ddc.dill=packages/flutter/src/gestures/arena --summary=packages/flutter/gestures.ddc.dill=packages/flutter/gestures --summary=packages/flutter/src/painting/_network_image_web.ddc.dill=packages/flutter/src/painting/_network_image_web --summary=packages/flutter/painting.ddc.dill=packages/flutter/painting --summary=packages/flutter/src/semantics/binding.ddc.dill=packages/flutter/src/semantics/binding --summary=packages/flutter/semantics.ddc.dill=packages/flutter/semantics --summary=packages/flutter/src/animation/animation.ddc.dill=packages/flutter/src/animation/animation --summary=packages/flutter/animation.ddc.dill=packages/flutter/animation --summary=packages/flutter/src/rendering/animated_size.ddc.dill=packages/flutter/src/rendering/animated_size --summary=packages/flutter/rendering.ddc.dill=packages/flutter/rendering --summary=packages/flutter/src/widgets/actions.ddc.dill=packages/flutter/src/widgets/actions --summary=packages/flutter/widgets.ddc.dill=packages/flutter/widgets --summary=packages/flutter/src/cupertino/action_sheet.ddc.dill=packages/flutter/src/cupertino/action_sheet --summary=packages/flutter/cupertino.ddc.dill=packages/flutter/cupertino --summary=packages/flutter/material.ddc.dill=packages/flutter/material --summary=packages/realspaceweb/constants/constants.ddc.dill=packages/realspaceweb/constants/constants --summary=packages/gql_exec/exec/context.ddc.dill=packages/gql_exec/exec/context --summary=packages/gql_exec/exec/error.ddc.dill=packages/gql_exec/exec/error --summary=packages/gql_exec/exec/response.ddc.dill=packages/gql_exec/exec/response --summary=packages/path/path.ddc.dill=packages/path/path --summary=packages/term_glyph/src/generated/ascii_glyph_set.ddc.dill=packages/term_glyph/src/generated/ascii_glyph_set --summary=packages/charcode/ascii.ddc.dill=packages/charcode/ascii --summary=packages/charcode/html_entity.ddc.dill=packages/charcode/html_entity --summary=packages/charcode/charcode.ddc.dill=packages/charcode/charcode --summary=packages/source_span/source_span.ddc.dill=packages/source_span/source_span --summary=packages/gql/src/ast/ast.ddc.dill=packages/gql/src/ast/ast --summary=packages/gql/ast.ddc.dill=packages/gql/ast --summary=packages/gql_exec/exec/operation.ddc.dill=packages/gql_exec/exec/operation --summary=packages/gql_exec/exec/request.ddc.dill=packages/gql_exec/exec/request --summary=packages/gql_exec/gql_exec.ddc.dill=packages/gql_exec/gql_exec --summary=packages/gql/language.ddc.dill=packages/gql/language --summary=packages/gql_link/gql_link.ddc.dill=packages/gql_link/gql_link --summary=packages/pedantic/pedantic.ddc.dill=packages/pedantic/pedantic --summary=packages/string_scanner/src/eager_span_scanner.ddc.dill=packages/string_scanner/src/eager_span_scanner --summary=packages/typed_data/typed_data.ddc.dill=packages/typed_data/typed_data --summary=packages/http_parser/http_parser.ddc.dill=packages/http_parser/http_parser --summary=packages/http/src/base_client.ddc.dill=packages/http/src/base_client --summary=packages/http/http.ddc.dill=packages/http/http --summary=packages/gql_http_link/gql_http_link.ddc.dill=packages/gql_http_link/gql_http_link --summary=packages/realspaceweb/widgets/search/SearchSectionTitle.ddc.dill=packages/realspaceweb/widgets/search/SearchSectionTitle --summary=packages/realspaceweb/widgets/search/SearchSection.ddc.dill=packages/realspaceweb/widgets/search/SearchSection --summary=packages/font_awesome_flutter/icon_data.ddc.dill=packages/font_awesome_flutter/icon_data --summary=packages/font_awesome_flutter/font_awesome_flutter.ddc.dill=packages/font_awesome_flutter/font_awesome_flutter --summary=packages/realspaceweb/utils/Utils.ddc.dill=packages/realspaceweb/utils/Utils --summary=packages/realspaceweb/config/AppConfig.ddc.dill=packages/realspaceweb/config/AppConfig --summary=packages/normalize/normalize.ddc.dill=packages/normalize/normalize --summary=packages/convert/convert.ddc.dill=packages/convert/convert --summary=packages/crypto/crypto.ddc.dill=packages/crypto/crypto --summary=packages/hive/hive.ddc.dill=packages/hive/hive --summary=packages/built_value/built_value.ddc.dill=packages/built_value/built_value --summary=packages/rxdart/src/streams/never.ddc.dill=packages/rxdart/src/streams/never --summary=packages/rxdart/transformers.ddc.dill=packages/rxdart/transformers --summary=packages/rxdart/rxdart.ddc.dill=packages/rxdart/rxdart --summary=packages/gql_client/gql_client.ddc.dill=packages/gql_client/gql_client --summary=packages/realspaceweb/widgets/DropdownStringWidget.ddc.dill=packages/realspaceweb/widgets/DropdownStringWidget --summary=packages/expandable/expandable.ddc.dill=packages/expandable/expandable --packages=file:///var/folders/nr/yvt4wkdn3p9_dy_6b5bc3zxh0000gn/T/kernel_builder_ptIly3/.packages --module-name=packages/realspaceweb/widgets/search/SearchLocationButton --multi-root-scheme=org-dartlang-app --multi-root=. --track-widget-creation --inline-source-map --libraries-file=file:///Users/user/Dropbox/BUSINESS/Soft/flutter/bin/cache/flutter_web_sdk/libraries.json --used-inputs-file=/var/folders/nr/yvt4wkdn3p9_dy_6b5bc3zxh0000gn/T/ddk_builder_N3Q6uB/used_inputs.txt package:realspaceweb/widgets/search/SearchLocationButton.dart
    dart --version: 2.8.0-dev.0.0.flutter-c547f5d933 (Fri Dec 27 00:43:14 2019 +0000) on "macos_x64"

Crash when compiling null,
at character offset null:
Reference to root::package:gql_client/src/store//memory_store.dart is not bound to an AST node. A library was expected
#0      Reference.asLibrary (package:kernel/ast.dart:265:7)
#1      LibraryDependency.targetLibrary (package:kernel/ast.dart:642:57)
#2      SourceLoader.computeFullComponent (package:front_end/src/fasta/source/source_loader.dart:873:38)
#3      SourceLoader.computeHierarchy (package:front_end/src/fasta/source/source_loader.dart:890:38)
#4      KernelTarget.buildOutlines.<anonymous closure> (package:front_end/src/fasta/kernel/kernel_target.dart:275:14)
<asynchronous suspension>
#5      withCrashReporting (package:front_end/src/fasta/crash.dart:122:24)
#6      KernelTarget.buildOutlines (package:front_end/src/fasta/kernel/kernel_target.dart:252:12)
#7      IncrementalCompiler.computeDelta.<anonymous closure> (package:front_end/src/fasta/incremental_compiler.dart:462:52)
<asynchronous suspension>
#8      CompilerContext.runInContext.<anonymous closure>.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:46)
#9      new Future.sync (dart:async/future.dart:224:31)
#10     CompilerContext.runInContext.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:19)
#11     _rootRun (dart:async/zone.dart:1126:13)
#12     _CustomZone.run (dart:async/zone.dart:1023:19)
#13     _runZoned (dart:async/zone.dart:1518:10)
#14     runZoned (dart:async/zone.dart:1465:12)
#15     CompilerContext.runInContext (package:front_end/src/fasta/compiler_context.dart:122:12)
#16     IncrementalCompiler.computeDelta (package:front_end/src/fasta/incremental_compiler.dart:156:20)
#17     _compile (package:dev_compiler/src/kernel/command.dart:333:64)
<asynchronous suspension>
#18     compile (package:dev_compiler/src/kernel/command.dart:46:18)
#19     compile (package:dev_compiler/src/compiler/shared_command.dart:410:10)
#20     _CompilerWorker.performRequest.<anonymous closure> (file:///b/s/w/ir/cache/builder/src/third_party/dart/pkg/dev_compiler/bin/dartdevc.dart:64:13)
#21     _rootRun (dart:async/zone.dart:1126:13)
#22     _CustomZone.run (dart:async/zone.dart:1023:19)
#23     _runZoned (dart:async/zone.dart:1518:10)
#24     runZoned (dart:async/zone.dart:1465:12)
#25     _CompilerWorker.performRequest (file:///b/s/w/ir/cache/builder/src/third_party/dart/pkg/dev_compiler/bin/dartdevc.dart:62:24)
#26     AsyncWorkerLoop.run.<anonymous closure> (package:bazel_worker/src/worker/async_worker_loop.dart:33:41)
#27     _rootRun (dart:async/zone.dart:1126:13)
#28     _CustomZone.run (dart:async/zone.dart:1023:19)
#29     _runZoned (dart:async/zone.dart:1518:10)
#30     runZoned (dart:async/zone.dart:1465:12)
#31     AsyncWorkerLoop.run (package:bazel_worker/src/worker/async_worker_loop.dart:33:26)
<asynchronous suspension>
#32     main (file:///b/s/w/ir/cache/builder/src/third_party/dart/pkg/dev_compiler/bin/dartdevc.dart:28:57)
#33     _startIsolate.<anonymous closure> (dart:isolate-patch/isolate_patch.dart:303:32)
#34     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:174:12)


#0      Reference.asLibrary (package:kernel/ast.dart:265:7)
#1      LibraryDependency.targetLibrary (package:kernel/ast.dart:642:57)
#2      SourceLoader.computeFullComponent (package:front_end/src/fasta/source/source_loader.dart:873:38)
#3      SourceLoader.computeHierarchy (package:front_end/src/fasta/source/source_loader.dart:890:38)
#4      KernelTarget.buildOutlines.<anonymous closure> (package:front_end/src/fasta/kernel/kernel_target.dart:275:14)
<asynchronous suspension>
#5      withCrashReporting (package:front_end/src/fasta/crash.dart:122:24)
#6      KernelTarget.buildOutlines (package:front_end/src/fasta/kernel/kernel_target.dart:252:12)
#7      IncrementalCompiler.computeDelta.<anonymous closure> (package:front_end/src/fasta/incremental_compiler.dart:462:52)
<asynchronous suspension>
#8      CompilerContext.runInContext.<anonymous closure>.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:46)
#9      new Future.sync (dart:async/future.dart:224:31)
#10     CompilerContext.runInContext.<anonymous closure> (package:front_end/src/fasta/compiler_context.dart:123:19)
#11     _rootRun (dart:async/zone.dart:1126:13)
#12     _CustomZone.run (dart:async/zone.dart:1023:19)
#13     _runZoned (dart:async/zone.dart:1518:10)
#14     runZoned (dart:async/zone.dart:1465:12)
#15     CompilerContext.runInContext (package:front_end/src/fasta/compiler_context.dart:122:12)
#16     IncrementalCompiler.computeDelta (package:front_end/src/fasta/incremental_compiler.dart:156:20)
#17     _compile (package:dev_compiler/src/kernel/command.dart:333:64)
<asynchronous suspension>
#18     compile (package:dev_compiler/src/kernel/command.dart:46:18)
#19     compile (package:dev_compiler/src/compiler/shared_command.dart:410:10)
#20     _CompilerWorker.performRequest.<anonymous closure> (file:///b/s/w/ir/cache/builder/src/third_party/dart/pkg/dev_compiler/bin/dartdevc.dart:64:13)
#21     _rootRun (dart:async/zone.dart:1126:13)
#22     _CustomZone.run (dart:async/zone.dart:1023:19)
#23     _runZoned (dart:async/zone.dart:1518:10)
#24     runZoned (dart:async/zone.dart:1465:12)
#25     _CompilerWorker.performRequest (file:///b/s/w/ir/cache/builder/src/third_party/dart/pkg/dev_compiler/bin/dartdevc.dart:62:24)
#26     AsyncWorkerLoop.run.<anonymous closure> (package:bazel_worker/src/worker/async_worker_loop.dart:33:41)
#27     _rootRun (dart:async/zone.dart:1126:13)
#28     _CustomZone.run (dart:async/zone.dart:1023:19)
#29     _runZoned (dart:async/zone.dart:1518:10)
#30     runZoned (dart:async/zone.dart:1465:12)
#31     AsyncWorkerLoop.run (package:bazel_worker/src/worker/async_worker_loop.dart:33:26)
<asynchronous suspension>
#32     main (file:///b/s/w/ir/cache/builder/src/third_party/dart/pkg/dev_compiler/bin/dartdevc.dart:28:57)
#33     _startIsolate.<anonymous closure> (dart:isolate-patch/isolate_patch.dart:303:32)
#34     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:174:12)





AssetNotFoundException: realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill

AssetNotFoundException: realspaceweb|lib/main_prod_web_entrypoint.ddc.js

AssetNotFoundException: realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill

AssetNotFoundException: realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill

AssetNotFoundException: realspaceweb|lib/widgets/search/SearchLocationButton.ddc.dill

AssetNotFoundException: realspaceweb|lib/main_web_entrypoint.ddc.js
Failed after 382ms
Finished with error: Failed to build application for the Web.

UpdateCacheHandler is not called after Pagination

Hi

I have a request to fetch a list of items, and a loadMore function for pagination, sane as in the example https://ferrygraphql.com/docs/pagination

The initial request will call the UpdateCacheHandler, but any loadMore calls will not call it!
Is this expected behavior?

extra information about the app ligic:
What I am doing with UpdateCacheHandler?
I want to write each item from the results of getItems(limit, offset) to cache, so

  1. individual item fetch getItem(id) will be from cache
  2. when I update any property of the item from one page I rewrite the item fragment and it will update both requests.

Update cache with mutations

Hello guys, one more question - after we make a mutation, what is the best way to update the cache?

Right now in your documentation is example

final updateCacheHandlers = <dynamic, Function>{
  "MyHandlerKey": MyUpdateCacheHandler,
};

final options = ClientOptions(updateCacheHandlers: updateCacheHandlers);

final client = Client(
  link: link,
  options: options,
);

But for me, it is not clear, how to implement it. Maybe there are obvious approaches, but I just started to use graphql and will be appreciated for example.

Documentation. When I finished things in my app I ready to create one more example for your package for demonstrating mutations, links updates, and cache updates. I quests, that it will be topical questions from your users.

Consider removing Query Widget

I'd like to keep the API footprint as minimal as possible without sacrificing core functionality.

The Query widget is a very light wrapper around StreamBuilder. StreamBuilder re-subscribes whenever the stream changes. The only value that Query is adding currently over using StreamBuilder directly is that it prevents re-subscribing whenever the parent widget rebuilds. Since QueryRequest doesn't currently override "==", if the QueryRequest is created within the build method of the parent widget, it will have a new identity on every build and will cause StreamBuilder to re-subscribe.

By simply overriding "==" in QueryRequest (either directly or by implementing built_value) we should be able to just use StreamBuilder directly and remove the Query Widget altogether.

This should reduce the API footprint and make it more transparent to the user how the library works.

Cache update with optimisticResponse

Description

During diving into the code for #18, I found some problems with the cache update with optimisticResponse.

If we make the mutation with Optimistic Response

final mutation = ProfileBmiMutation2(
  buildVars: (b) => b..input = profileInput,
  updateCacheHandlerKey: IdCacheHandlers.profileBmiMutation,
  optimisticResponse: optimisticRequest,
).copyWith(
  context: Context.fromList(
    [
      HttpLinkHeaders(
        headers: idToken,
      ),
    ],
  ),
);
client
    .responseStream(mutation)
    .firstWhere((response) => response.optimistic)
    .then((response) {});

cache updates incorrectly.

Assumption where the bug is

Maybe it is connected with code here /lib/src/cache/cache_proxy.dart, because if we change optimistic: _optimistic, to optimistic: false, it starts to work correctly (in this exact use-case).
I guess, there is more logic. I just pointed out what I've found.

  void writeQuery(
    Request request,
    Map<String, dynamic> data,
  ) =>
      _cache.writeQuery(
        request,
        data,
        optimistic: false,
        queryId: _queryId,
      );

Screenshot

  1. When we make the first request cache is not updated.
  2. But if we open the screen again, cache updates.
  3. After that, other updates do not change the cache.

ezgif com-video-to-gif (2)

Use generated data classes for optimistic response

Hello, as you recommended, I made an optimisticResponse, and it works just fine. I got data from this response and can use it before I get updates from API.

This question is about best practices.

In the app, we made a mutation and passes there the 'resultObjectFromApp'. For the optimisticResponse we should create a 'mapFromApp' with structure

{QueryName: 
  {__typename: TypeName,  
  height: xx, 
  weight: xx,
  birthday: xx}
}

where all the data except {**QueryName**: {__typename: **TypeName**, duplicate resultObjectFromApp data.

So, the question is - are there any ways to create this map outside widgets or, maybe, it is possible to implement the automatic creation of this map?

final mutation = SomeMutation(
  buildVars: (b) => b..input = resultObjectFromApp,
  updateCacheHandlerKey:
      IdCacheHandlers.someMutation,
  optimisticResponse: mapFromApp,
).copyWith(
  context: Context.fromList(
    [
      HttpLinkHeaders(
        headers: idToken,
      ),
    ],
  ),
);
client
    .responseStream(mutation)
    .firstWhere((response) => response.optimistic)
    .then((response) {
});

how to upload files

As the title says I want to upload a pictures, but I don't know how to use scalar Upload .
Please tell me the way, thanks.

[normalize feature req] validation and safety utils

I'm looking at adding some handlers in graphql/client.dart to check for / distinguish between malformed response data and cache misconfigurations, and I'm wondering if there's a better way than what I'm currently thinking.

Current thinking:

  • denormalizeOperation already validates all subtree structure right? So we can create a thin wrapper validateResponseStructure that ignores denormalization, or extract the traversal logic into its own helper
  • On response, we do a writeQuery/readQuery. If it returns null, we then:
    • throw a MismatchedDataStructureException if validateResponseStructure is null
    • throw a CacheRoundTripException otherwise (could be broken down further later).

The main idea is to validateResponseStructure independent of the cache. Might be a util better suited for gql.

Cache Evictions

Hi!

A few questions:

  1. How can I create a forced request when the cache data is set already?
  2. How I can clear cache for specific query?

Automatically assign unique queryIds in req_builder

I think we should automatically assign queryIds (possibly using https://github.com/Daegalus/dart-uuid) in the req_builder.

This issue is a bit of a data dump for later consideration.

  1. Currently, the cache's optimistic patch map is based on queryId, so each mutation will need a unique ID. Otherwise, any patch from a mutation without an ID will overwrite the previous.
  2. I previously thought that queryId should be null by default so that subsequent identical queries would trigger an update, even if no queryId is provided. However, this should happen anyway (should test) since the cache update would trigger a refresh of the previous query.

How to send Auth Token Header (JWT)

Looking through Ferrys documentation, I haven't been able to find how to send JWT header token to the client for GraphQL requests that need authentication.

https://ferrygraphql.com/docs/queries

I have a data layer for my GraphQL queries which is then used in my view models to read/write data.

Any help or would be appreciated.

How to convert custom scalar to List/BuiltList<Model>?

I can't seem to figure out how to convert a custom scalar to a List or BuiltList of a local model.

type_overrides:
  DateTime:
    name: DateTime
  MyModels:
    name: BuiltList<MyModel>
    # import: 'package:name/path/to/model.dart'

Ive implemented a MyModelsSerializer which returns BuiltList<MyModel>. Ive also tried importing the model file that. defines MyModel (a freezed class)

It doesn't seem to resolve the types properly so build_runner keeps throwing `Make field [name] have non-dynamic type. Is there a naming convention I'm missing for the config?

proxy.writeQuery - doesn't write

Description

The bug appears when I trying to update the cache in the example app.
The results are printed in the code, when we use deleteTodoMutationHandler
https://github.com/awaik/todo_ferry_example/blob/master/lib/src/client.dart

The code

    print('resMap --- ${resMap}');
    proxy.writeQuery(query, resMap);
    print('proxy.readQuery(query) --- ${proxy.readQuery(query)}');

proxy.readQuery(query); returns the old, not updated value.

So, the line proxy.writeQuery(query, SomeMap); doesn't change the cache.

Fragment Bug

Didn't test to see if it only happens when nesting fragments or not, but if you have have a nested graph with ONLY a fragment, when normalized, it gets nulled...

foobar{
...fragment
}

i can work around by always asking for a typename

foobar{
__typename,
...fragment
}

Future of this project

Hey man! Thanks for working on this project! I just have 1 quick question out of curiosity and due to some problems I meet every day in other graphql package.

What is your motivation and how do you see the future of this project?
And also, why did you decide to build this package instead of contributing to the original package?

Thanks for your answers, sorry for creating an issue, IDK where else can I ping you.
Cheers!

New typed links architecture not backward compatible

Please make such refactors backward compatible as it makes it super hard to update. (no responseStream method?)
In general a library such as this that is so central to every app using it must keep the number of breaking changes to a minimum.

Denormalization does not merge data of expanded fragments

There is an issue with the denormalizeNode function in the normalize package.

It denormalizes all fragments in a query one by one. The values of the fields requested by a fragment are then stored in a result map under the key of the queried field. If the same field is queried again by another fragment, the value stored before is replaced.

This is problematic if multiple fragments query an object, but query different fields of that object. In that case only the object data of the last processed fragment is present in the result.

Here is an example. Consider the following query and fragments.

fragment MovieStarComponent on MovieType {
	__typename
	id
	name
	starRole {
		__typename
		id
		name
		age
		haircolor
	}
}

fragment MovieTitleComponent on MovieType {
	__typename
	id
	name
	starRole {
		__typename
		id
		name
	}
}

query MovieByID($movieID: ID!) {
	movie(id: $movieID) {
		... MovieStarComponent
		... MovieTitleComponent
	}
}

Running denormalize on this query will result in the following map:

{
	movie {
		__typename: MovieType,
		id: 1,
		name: Rocky,
		starRole {
			__typename: ActorType,
			id: 1,
			name: Sylvester Stallone,
		}

	}
}

Notice that the starRole objects age and haircolor fields are not returned, even though they are queried by the MovieStarComponent fragment.

Here the MovieStarComponent fragment is processed first. The result map now contains the queried movies starRole object and all fields queried by the MovieStarComponent fragment.

Next the MovieTitleComponent fragment is processed. It queries the same starRole object but less fields than the MovieStarComponent fragment.

Due to the bug described before, the data queried by the MovieStarComponent fragment is replaced with the data of the MovieTitleComponent fragment.

Changing the order of the fragments in this particular query would "fix" the issue in this situation.

Solution

One solution to fix this problem would be to deepmerge the data of denormalized fragments on the same level, instead of just keeping the data of the last processed fragment. I will create an PR in a minute with such changes.

Allow subfields in TypePolicy.keyFields

Apollo allows subfields to be used in keyFields:

const cache = new InMemoryCache({
  typePolicies: {
    Book: {
      keyFields: ["title", "author", ["name"]],
    },
  },
});

In this case, the title and author name are used as the unique identifiers for a Book.

We currently only support a single level of depth in normalize. I propose adjusting the API to use a Map of booleans for keyFields. For example:

final cache = Cache(
  typePolicies: {
    'Book': TypePolicy(
      keyFields: {
        'title': true,
        'author': {
          'name': true
        }
      },
    ),
  },
);

Although this is a divergence from the Apollo API, I think it more accurately describes the keyFields.

How get input data in UpdateCacheHandler?

Hi!

How get input data from mutation in body UpdateCacheHandler?

final UpdateCacheHandler<$MyMutation> myMutationHandler = (
  CacheProxy proxy,
  QueryResponse<$MyMutation> response,
) {
  final query = MyQueryToUpdate();
  final result = proxy.readQuery(query);

  /// update the result
  proxy.writeQuery(query, result);
};

Let's talk subscriptions!

What is the roadmap regarding graphql subscriptions using the websocket transport?
It seems reasonable to expect a streams-based graphql client to support subscriptions. Is it of much work?

Please make the documentation more clear

Hey, I have been trying out Ferry after getting very frustrated with graphql_flutter. So far the project looks like it is designed better but I have not spent much time with it yet.

One of the issues I am running into is the lack of documentation. There is currently one very thin example to go off. The large number of dependencies is also very confusing and will potentially be a nightmare to keep versions in sync (I've already run into conflicts). It would be ideal if the ferry flutter client could be installed as a single package which would include all required codegen/gql packages etc. I think that will be key to increasing adoption of Ferry.

Also, as a side note, it would be awesome if there was a hooks API. Coming from React/Apollo client, working with GraphQL in Flutter is currently extremely clunky. I think this library has the potential to change that.

update ferry_flutter dependency

I'm getting this error while trying to use latest ferry (0.4.0) with ferry_flutter:

ferry_flutter ^0.1.0 which depends on ferry ^0.3.1+2, ferry ^0.3.1+2 is required.
So, because test_project depends on ferry ^0.4.0, version solving failed.

Also, it causes conflicts while running the usage provided here, since objects and functions are declared in multiple libraries

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.