jaydenwindle / graphene-subscriptions

A plug-and-play GraphQL subscription implementation for Graphene + Django built using Django Channels.
MIT License
115 stars 15 forks source link

Created an API to easily define django model connections #28

Open shreyas44 opened 4 years ago

shreyas44 commented 4 years ago

Created a simple API to easily define subscriptions related to django models.

Using the DjangoObjectSubscription, you can define the subscribtion like below:

from graphene_subscriptions.subscriptions import DjangoObjectSubscription

class YourModelSubscription(DjangoObjectSubscription):
  class Meta:
    model = YourModel
    output = YourModelType # the type of the subscription - can be a DjangoObjectType or a regular Graphene Type

  class Arguments:
    # define arguments

  def subsribe(root, info, operation, instance, *args, **kwargs):
    if operation == "created":
      # do something

    return something # something would be an object which would have the attributes of the output type.

class Subscriptions(graphene.ObjectType):
  your_model_subscription = YourModelSubscription.Field()

Why use this?

  1. Don't have to manually connect your model to Django signals, it is automatically done under the hood. This really makes the library Plug-and-Play!
  2. Wouldn't have to learn even the basics of the rxPy library to perform basic functions.
  3. When you define Subscriptions using DjangoObjectSubscription, the structure of it is very similar to defining mutations using graphene.Mutation.
  4. Code becomes much cleaner.

Some things that could be added:

  1. Provide only a DjangoObjectType in the Meta subclass instead of the model and output type. (Adding this as optional would probably be better)
  2. Let users define on_save, on_update, on_delete, functions separately which are run when a record from the model is created, updated and deleted respectively. (Again optional)

Let me know if it would be beneficial to add either of the features.

Also, would it be better to pass the operation and instance under a single argument event which can then be accessed from event.operation and event.instance?

I guess this would resolve #11