parse-community / parse-community/parse-server

Add GraphQL parent context within `Parse.Cloud.define()`

Open
#7,621 2 comments 3 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

type:feature
Dominant language
JavaScript
Stars
21.4k
Forks
4.8k
Avg merge
7h 45m
Merged PRs (30d)
11

Description

New Feature / Enhancement Checklist
Current Limitation

It is currently not possible to get context of the "GraphQL parent". So it is not extend the GraphQL schema like so:

extend type MyParseClass {
  myParseClassCustomField: Any! @resolve(to: "myParseClassCustomField")
}

and query like this:

query GetMyParseClassAndCalculatedField($myParseClassId: ID!) {
  myParseClass(id: $myParseClassId) {
    objectId
    myParseClassCustomField
  }
}

But instead, we have to do extend it like this:

extend type Query {
  myParseClassCustomField(myParseClassId: ID!): Any! @resolve(to: "myParseClassCustomField")
}

and query like this:

query GetMyParseClassAndCalculatedField($myParseClassId: ID!) {
  myParseClass(id: $myParseClassId) {
    objectId
  }

  myParseClassCustomField(myParseClassId: $myParseClassId)
}

The above assumes there is a MyParseClass parse class defined like so:

type MyParseClass {
  objectId: ID!
  # ... other properties of MyParseClass
}

The above is a very simple example, but you can see how it gets really complicated to run cloud code functions within GraphQL when doing nested queries, like myParseClasses.edges.node.myParseClassCustomField.

This also means doing the waterfall approach when the objectId is not defined, where the query for the customField has to wait until you get the objectId from first query, then query for custom field using that id.

Feature / Enhancement Description

Add parent GraphQL context to Parse.Cloud.define request argument.

interface FunctionRequest<T extends Params = Params> {
  installationId?: string | undefined;
  master?: boolean | undefined;
  params: T;
  user?: User | undefined;
  parent: {
    typename?: string | undefined;
    objectId?: string | undefined;
  }
}

It should at minimum contain the typename and objectId of the parent, so that we can easily query using that objectId:

Parse.Cloud.define('myParseClassCustomField', (request) => {
  if (request.parent.typename === 'MyParseClass') {
    return calculateUsingObjectId(request.parent.objectId);
  } else {
    throw 'This function can only be called from within MyParseClass';
  }
});
Example Use Case

Functionality explained above.

Alternatives / Workarounds

Current workaround is to extend type Query instead of the actual class we want to extend and add all required params (objectId or other) to filter/get the class instance we want within the Parse.Cloud.define definition.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by tracing the Parse.Cloud.define request handling and the GraphQL @resolve path described in the issue. Determine how the GraphQL parent typename and objectId can reach the function request, then verify that nested class fields expose both values without requiring an additional objectId argument.

Written by the indexing model from the issue text.

Assessment

Tech stack
graphql, javascript
Domain
api, backend
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.