Prisma1: Break up functions into seperate top-level fields in project configuration

Created on 25 Sep 2017  路  9Comments  路  Source: prisma/prisma1

Currently functions is a top-level field in graphcool.yml containing a handler and a type + extra configuration depending on the type.

We will remove the top level functions field and instead introduce three specific fields:

  • subscriptions
  • hooks
  • cronjobs

containing the handler and configuration appropriate for the specific type.

The reasoning for this is that we want to introduce handlers that are not functions as described in #585

In addition we will introduce the top-level handlers field which can be used to define named handlers:

handlers:
  send-welcome-email:
    code:
      src: ./code/sendEmail.js

subscriptions:
  user-signed-up:
    subscription: ./subscriptions/userSignedUp.graphql
    handler: send-welcome-mail

This is especially useful for #543 that will reference a named handler from the types.graphql file as below

handlers:
  facebook-authentication:
    code:
      src: ./code/facebook-authentication.js
type FacebookUser @model {
  id: ID! @isUnique
  facebookUserId: String @isUnique
  facebookEmail: String
  createdAt: DateTime!
  updatedAt: DateTime!
}

type AuthenticateFacebookUserPayload {
  token: String!
}

extend type Mutation {
  authenticateFacebookUser(facebookToken: String!) @resolver(handler: "facebook-authentication"): AuthenticateFacebookUserPayload
}

Most helpful comment

I ment a serverside subscription like in the example above:

handlers:
  send-welcome-email:
    code:
      src: ./code/sendEmail.js

subscriptions:
  user-signed-up:
    subscription: ./subscriptions/userSignedUp.graphql
    handler: send-welcome-mail

What I am trying to understand is whether we should keep the handler terminology or we should simply call it resolver in all places.

@marktani @nikolasburk @timsuchanek I would love some input on this :-)

All 9 comments

I'm not entirely convinced about the naming of the top-level handlers field. The alternative is to call it functions, but I like to clearly indicate that this is describing a handler.

Would love to get some input. cc @schickling

Resolvers? That might change the attribute to @resolver(name: '...') instead of @resolver(resolver: '...') though...

@kbrandwijk If they are used only for actual GraphQL resolvers, I think that would be appropriate.

My current thinking is that they should also work as named handlers that can be referenced from a subscription for example.

Do you think calling them resolvers would work in that case?
Do you think we should rather say that they can only be used as actual GraphQL resolvers?

@sorenbs I can't really visualize what you're saying about referencing handlers from a subscription. I think you should stay as close as possible to the GraphQL principles, so resolvers fit right into that.

Also, with regards to subscriptions, if you would use a function as implementation for a subscription (if that's what you meant), than that's still called a resolver (for example: http://dev.apollodata.com/tools/graphql-subscriptions/subscriptions-to-schema.html#subscription-server)

I ment a serverside subscription like in the example above:

handlers:
  send-welcome-email:
    code:
      src: ./code/sendEmail.js

subscriptions:
  user-signed-up:
    subscription: ./subscriptions/userSignedUp.graphql
    handler: send-welcome-mail

What I am trying to understand is whether we should keep the handler terminology or we should simply call it resolver in all places.

@marktani @nikolasburk @timsuchanek I would love some input on this :-)

@sorenbs Thank you for clarifying that. I think resolver is still closest to what it actually is in GraphQL terminology, both for 'former SE'-resolvers as for 'former SSS'-resolvers.

To me, it would be like this:

  • a handler is invoked by some trigger/event. in our case, that's a hook, a subscription event, or a query/mutation. later we will have other triggers.
  • a resolver is the component responsible for handling a mutation or query.

I don't see how a handler for server side subscriptions or hooks would fit the resolver terminology. That's why I like the top-level term handler better, because it's more generic. Resolvers referenced in types.graphql would use @resolver(handler: "send-welcome-email").

Thanks for the input!

We have decided to stick with handlers and the

@resolver(handler: "facebook-authentication")

syntax for resolvers in types.graphql

We have decided to backtrack on this :-)

Introducing multiple top-level fields for different kind of functions makes it difficult to group functions in a big graphcool.yml file. It's possible to achieve grouping by using modules, but we feel that having one graphcool.yml file will be so common that we need to optimise for this case.

resolver functions will be referenced like this:

functions:
  facebook-auth:
    handler:
      code:
        src: ./code/facebook-authentication.js
    type: resolver
type FacebookUser @model {
  id: ID! @isUnique
  facebookUserId: String @isUnique
  facebookEmail: String
  createdAt: DateTime!
  updatedAt: DateTime!
}

type AuthenticateFacebookUserPayload {
  token: String!
}

extend type Mutation {
  authenticateFacebookUser(facebookToken: String!) @resolver(function: "facebook-auth"): AuthenticateFacebookUserPayload
}
Was this page helpful?
0 / 5 - 0 ratings

Related issues

notrab picture notrab  路  3Comments

schickling picture schickling  路  3Comments

AlessandroAnnini picture AlessandroAnnini  路  3Comments

schickling picture schickling  路  3Comments

MitkoTschimev picture MitkoTschimev  路  3Comments