2015-10-28 13 views
43

Ich begann mit der relay-starter-kit und arbeitete sich auch durch die Relay und GraphQL Dokumentation. Aber es gibt einige Bereiche, die unerklärt und geheimnisvoll sind.In Relay, welche Rolle spielen die Knotenschnittstelle und die globale ID-Spezifikation?

Ernst las ich eine Menge Dokumentationen überall über all diese Dinge, aber konnte keine befriedigende Erklärungen für die folgenden Fragen nicht finden:

Was ist das? Ich setze Protokollierung, aber es wird nie überhaupt genannt:

var {nodeInterface, nodeField} = nodeDefinitions(
    (globalId) => { 
    var {type, id} = fromGlobalId(globalId); 
    if (type === 'User') { 
     return getUser(id); 
    } else if (type === 'Widget') { 
     return getWidget(id); 
    } else { 
     return null; 
    } 
    }, 
    (obj) => { 
    if (obj instanceof User) { 
     return userType; 
    } else if (obj instanceof Widget) { 
     return widgetType; 
    } else { 
     return null; 
    } 
    } 
); 

Und was ist die tatsächliche Wirkung dieser:

interfaces: [nodeInterface], 

Vielleicht, dass im Zusammenhang, was bedeutet das node Feld hier tun:

var queryType = new GraphQLObjectType({ 
    name: 'Query', 
    fields:() => ({ 
    node: nodeField, 
    // Add your own root fields here 
    viewer: { 
     type: userType, 
     resolve:() => getViewer(), 
    }, 
    }), 
}); 

Und was ist die Magie um das Feld id? Was ist globalIdField für?

Ich habe eine id in meiner Datenbank und dachte, dass ich es in meinem GraphQL Objekte verwenden:

Statt:

id: globalIdField('User'), 

ich meine Datenbank-ID verwenden möchten:

id: { 
    type: GraphQLID, 
    description: 'The identifier' 
}, 

Aber wenn ich das tue, erhalte ich einen Fehler im Browser, der RelayQueryWriter: Could not find a type name for record '1' sagt.

Ich kann diesen Fehler loswerden, indem ich __typename zu meinem Component Container Relay Query hinzufügen, aber das scheint alles falsch.

Es wäre großartig, wenn Sie hier ein paar tiefere Einblicke und eine bessere Erklärung geben und die offizielle Dokumentation verbessern könnten.

Danke

Antwort

51

Das Node Wurzelfeld, mit global eindeutiger IDs in Kombination kommt ins Spiel, wenn Relay Refetch ein Objekt benötigt. Das erneute Abrufen findet statt, wenn Sie this.props.relay.forceFetch() aufrufen oder wenn Sie Felder zu der Abfrage für ein Objekt hinzufügen, dessen globale ID bekannt ist, da es bereits teilweise abgerufen worden ist.

In solchen Fällen schließt Relay die reguläre Abfrage kurz und führt eine Abfrage für das Objekt direkt mit seiner globalen ID und dem Root-Aufruf node aus.

Beispiel:

Angenommen, $showCommentsfalse war, als diese Abfrage zuerst gelöst wurde.

query { 
    viewer { 
    stories(first: 10) { 
     edges { 
     node { 
      id, 
      comments(first: 10) @include(if: $showComments) { 
      author, 
      commentText 
      } 
      text, 
     } 
     } 
    } 
    } 
} 

wird dies verursacht ein, sind jetzt bekannt, deren IDs für id und text für eine bestimmte Anzahl von Geschichten zu holen.

Stellen Sie sich vor, dass zu einem späteren Zeitpunkt die Variable true wird. Relay ruft nur die Daten ab, die es benötigt, und verwendet dabei das Root-Feld node.

query { 
    node(id: "ABC123") { 
    fragment on Story { comments(first: 10) { author, commentText } } 
    } 
    node(id: "DEF456") { 
    fragment on Story { comments(first: 10) { author, commentText } } 
    } 
    node(id: "GHI789") { 
    fragment on Story { comments(first: 10) { author, commentText } } 
    } 
    ... 
} 

Dies hängt von ein paar Stücke:

  1. Jedes Objekt muss eine global eindeutige ID haben oder durch eine Art/ID-Paar identifiziert werden (die globalIdField Helfer tut dies und erzeugt eine Base64-codierte Zeichenfolge).
  2. Der Server muss wissen, wie ein Objekt von einer global eindeutigen ID aufgelöst werden kann und umgekehrt. Dies ist, was die nodeDefinitions sind.
  3. Jedes Objekt, das mit diesem System referenzierbar sein soll, muss nodeInterface implementieren.

Siehe auch: https://facebook.github.io/relay/docs/graphql-object-identification.html#content

+2

Hoffentlich wird seinen Weg in das Tutorial bald machen. Ich war auch eine ganze Weile verwirrt, bis ich schließlich alles durchgearbeitet und die Teile zusammengesetzt habe. –

+3

Vielleicht fügen Sie ein bisschen mehr zu dieser Antwort in Bezug auf 'fromGlobalId' und' toGlobalId' hinzu? und wie erleichtern sie das Umkrempeln eines beliebigen Objekttyps? Das Lesen von https://github.com/graphql/graphql-relay-js/blob/master/src/node/node.js und anderer Dateien in diesem Repo hat mir sehr geholfen, aber dieses Zeug in Worte zu fassen, hätte mir viel erspart von Zeit. –

+0

Für eine kurze (Sie können bis zum Ende für die Zusammenfassung zu überspringen) & Code-illustrierte Erklärung, was die mysteriösen nodeInterface, nodeField, globalFieldId sind, vielleicht https://medium.com/p/relay-graphql-de-mystifying- node-id-38757121b9c – nethsix