Bidirectional Relationship

5 posts, 2 answers
  1. David Weinberg
    David Weinberg avatar
    18 posts
    Member since:
    Jul 2015

    Posted 28 Jan Link to this post

    Hi All,

    I am new to Telerik and NoSQL databases. I am trying to create a relationship that can be queried in both directions.

    For example I have a Person Content Type that has an Employer field that is a relation to the Organisation Content Type. I can expand the field and see all of the Organisation's fields on the Person. All good so far.

    I also want to be able to see a list of Employees for the Organisation. For this I have added a Employees field as a multiple relation to Person and can select people that work for this organisation. However this is not automatic based on the Person's Employer field.

    Am I looking at this the right way? Is there a better way?

    If this is right, what is the best way to ensure that the Empolyer field and Employees list are kept in sync.

    Thanks,

    David

  2. Answer
    Martin
    Admin
    Martin avatar
    67 posts

    Posted 01 Feb Link to this post

    Hi David,

    1. From you explanation I am assuming that you have the following content types/"tables" with the following sample fields that hold the reference:

    1. Person
      • Person name
      • Employer (reference to Organization)
    2. Organization
      • Organization name
      • Employees (multiple references to Person)

    2. Telerik Platform uses NoSQL data storage. For an example about how to model the data relationships in your use case you can read here.

    3. In your case you may want to hold the relation in one place, either in Person or in Organization:

    1. Person content type (each person will know what is his employer)
    2. Organization content type (the organization will have information which are its employees).

    For example, you may consider keeping the reference only in Person content type as otherwise the array of employees in the Organization content type can become quite big which might not be preferable. However, this choice depends on the data access patterns of the app, the security on type level and item level, etc. I'd also suggest that you examine the Design considerations when using a Relation expanding here.

    4. After you have defined the reference in one of the content types, you can query both on:

    Request:
        GET http://api.everlive.com/v1/your-app-id-here/Person
    Headers:
        X-Everlive-Expand {
            "Employer": {
                "TargetTypeName": "Organization"
            }
        }

        Request:
        GET http://api.everlive.com/v1/your-app-id-here/Organization
    Headers:
        X-Everlive-Expand {
            "Person.Employer": {
                "ReturnAs": "Employees"
            }
        }

    Let me know if that helped.

    Regards

    Martin
    Telerik
     
    Everlive is now Telerik Backend Services, and is part of the Telerik Platform.
     
  3. David Weinberg
    David Weinberg avatar
    18 posts
    Member since:
    Jul 2015

    Posted 04 Feb in reply to Martin Link to this post

    Hi Martin,

    Thanks, that is really helpful. I will keep the relationship just at Person level.

    I have another related question. So I am getting my expanded Person into a Kendo Datasource and using it with a hybrid application. I am displaying it in a ListView and allowing it to be edited, and saved via sync(). When it updated, however, the expanded fields are saved to the backend, as the object, not just the reference as originally.

    I have found a workaround by using the ReturnAs property, for example oEmployer. However I know have a new property that gets saved. This means that next time the record is loaded,oEmployer already exists and is not expanded again. I have found another solution by deleting the new oEmployer property just before calling sync(), but then it is missing when returning to the list and details.

    Is there a better way that I am missing?

    David

     

  4. Answer
    Martin
    Admin
    Martin avatar
    67 posts

    Posted 08 Feb Link to this post

    Hi David,

    Indeed, this is a known consideration when the expand functionality is used. You can find an explanation in the documentation article here.

    To avoid writing back the expanded field(s) you may want to delete them from the object before writing it back to the server. One approach is to use the beforeExecute event available in the client JavaScript SDK and to add a code in it to delete the additional expanded field(s).

    Also, for more business critical scenarios you may consider adding such code in the Cloud Code for Data layer.

    Let me know if this works for you.

    Regards,
    Martin
    Telerik
     
    Everlive is now Telerik Backend Services, and is part of the Telerik Platform.
     
  5. David Weinberg
    David Weinberg avatar
    18 posts
    Member since:
    Jul 2015

    Posted 24 Feb in reply to Martin Link to this post

    Hi Martin,

    Thanks. It took me a while to work out exactly what I should do but pointing me to Cloud Code for Data. I have added:

    Everlive.Events.beforeUpdate(function(request, context, done) {
     
        // Remove temporary fields and those from the expand expression
        delete request.data.$set.oEmployer;
          
        done();
    });

    And I am both removing the expanded objects from the database but keeping them in memory for the app.

    Thanks,

    David

Back to Top