simple-odata-client / Simple.OData.Client

MIT License
329 stars 196 forks source link

Does the client support deep linking? #127

Open andygjp opened 9 years ago

andygjp commented 9 years ago

I want to create an entity and its related entities with a single request using deep linking, but when I try it doesn't work.

I'm trying to send this:

{ "Surname": "Smith", "Addresses": [ { "Address1": "End of the road", "City": "No where", "Postcode": "SW12" } ], "PhoneNumbers": [ { "Number": "01" } ] }

(Which works, by the way, if I POST it using Fiddler2)

But instead it sends this:

{ "@odata.type": "#KbContext.Customer", "Surname": "Smith", "Addresses@odata.bind": [ "http://localhost:8080/kb/api/Addresses(0)" ], "PhoneNumbers@odata.bind": [ "http://localhost:8080/kb/api/PhoneNumbers(0)" ] }

I've tried both the typed and none typed "Set" methods of the client, but both bind instead of deep link.

Is this a feature that is supported by the client? Am I doing something wrong?

object commented 9 years ago

Hi, Yes, you can insert multiple entities in a single request, look at batch examples:

https://github.com/object/Simple.OData.Client/blob/master/Simple.OData.Client.Tests.Net40/BatchTypedTests.cs

https://github.com/object/Simple.OData.Client/blob/master/Simple.OData.Client.Tests.Net40/BatchTests.cs

Are you trying something else? Can you paste an example of your code?

andygjp commented 9 years ago

Hi,

Thanks for getting back in touch.

I can't upload a sample right now as I'm at work, but I will do later this evening.

However, BatchTypedTests.InsertSingleEntityWithSingleAssociationSingleBatch looks promising. I'll give that a try.

Although, I'm not quite sure that batch is what I'm looking for - its essentially two separate requests sent together. I'd rather it make a single request.

Bind relates the new entity to existing entities (http://docs.oasis-open.org/odata/odata/v4.0/errata02/os/complete/part1-protocol/odata-v4.0-errata02-os-part1-protocol-complete.html#_Toc406398327), but I want them created at once using deep linking (thats not the correct name, its actually called "deep insert"): http://docs.oasis-open.org/odata/odata/v4.0/errata02/os/complete/part1-protocol/odata-v4.0-errata02-os-part1-protocol-complete.html#_Toc406398328

Cheers

object commented 9 years ago

Oh I see, you meant deep insert. No, currently Simple.OData.Client doesn't support deep insert - using OData batch is the only way to create multiple entries in a single request. But it doesn't seem that it will take much work to implement it, I will look into it.

andygjp commented 9 years ago

Sorry, my mistake. It'll be great if you could get it to work :)

object commented 9 years ago

Can you send me at vagif.abilov@gmail.com your metadata file and the code example that is trying to do a deep insert?

andygjp commented 9 years ago

Sure. Should have those for you in about 10-20 minutes.

object commented 9 years ago

Hi again, Thank you for the code example. I looked at it and it seems that the implementation will require API change. Since Simple.OData.Client accepts plain objects, without any annotations, there is no way for it to detect what kind of insert (or update once deep updates are supported) is meant: deep (by value) or by reference. In your example both Address and PhoneNumber can point to a newly created entity or refer to an existing one. My first thought was to reuse Expand clause without changing API, but this will overload standard OData clause with new (and unexpected) semantics. So I believe the best would be to extend Set with new overload, allowing it to specify what referenced entities should be deep-inserted. I will investigate if this is something that might be implemented as a minor release (4.9) or planned for a major upgrade (5.0) later this year.

andygjp commented 9 years ago

Cool - I'm looking forward to it :)

andygjp commented 9 years ago

Not sure why it closed...

RonakThakkar commented 8 years ago

Is this supported in current version of Simple.OData.Client

object commented 8 years ago

No deep inserts are not currently supported. Requires API change, so most likely will be part of version 5.

RonakThakkar commented 8 years ago

Hi,

Do you foresee any timeline by which this this would be integrated and Version 5 would be released.

We have requirement for Deep Inserts. So right now we are thinking of using OData for Query and RESTClient for deep Insert, Update, Delete operations.

But I would prefer If we could achieve all CRUD operations using Simple.OData.Client.

In general, I would like to thank you for such a great library and also your quick reply to our issues posted earlier.

object commented 8 years ago

Hi Ronak,

My plan for version 5 is Q1 2015, but I will look into deep insert and see if it can be released prior version 5. I will let you know if this happens.

coolOrange-Public commented 8 years ago

Hi, any update regarding this issue ? Do you have any plans, when you are going to release an update for the Deep Insert?

thanks

object commented 8 years ago

Hi, I have looked into this enhancement, but it required too many changes to fit into minor release. So this will be a part of the version 5, originally planned for Q1 but obviously postponed. Since this is my free time project I'd rather not set any date commitments. There a few features (like this one) that needs to be implemented, so it will take some time.

johnrulon commented 8 years ago

If deep insert is not supported, then this client will not work for the scenario where a Parent entity has a child object that is required and has some sort of validation between the Parent and Child.

For example, I can't POST the Parent, and then POST the Child because of validation asserting that the Parent has a Child object with XYZ property that is required. I can't POST the Child first either, because the Child can't exist without the Parent. Hopefully this makes sense. In summary, if we ever have to POST an object that requires some other child object, this OData client can't support our needs without Deep Insertion.

rahul7720 commented 7 years ago

Hi,

Is this feature implemented in Simple.OData.Client 5.0.0-alpha2 ? How deep insert will work when keys (of both parent & child entities) are auto-generated at server side? I'm using Asp.Net WebApi 2 Odata v4 with Entity Framework.

tbaart commented 7 years ago

Hi,

I also would really like this feature. I'm a happy user of this library, and this seems to be the only feature that we need that is missing. We have an object that has required child entities, and our API does not accept a POST of the parent object without any child objects.

Any update on this?

im2cre8iv commented 6 years ago

Still would really like to use this client, but am unable to without deep insert support. Any update on expected timing?

object commented 6 years ago

@im2cre8iv Since you are one of the few who needs deep insert support, can you think about how you would like API to be extended to support this feature? Also, if you can give some examples of generated payload. I've read the specs, I still need to figure out how to implement the API changes.

tbaart commented 6 years ago

Since he doesn't reply and I was notified of the comments here because I'm subscribed to this issue, I'll explain how I'd like it to work instead:

can you think about how you would like API to be extended to support this feature?

Something along the lines of: client.For<Order>().Set(order, configuration => configuration.Include(o => o.OrderLines)).InsertEntryAsync()

Or maybe: client.For<Order>().Set(order).Include(o => o.OrderLines).InsertEntryAsync()

Although I think the first one might be less ambiguous, the second one might fit the current idea of Simple OData Client better. It keeps it more simple.

Also, if you can give some examples of generated payload.

Generated Payload would be along the lines of:

{
  "OrderId": 34,
  "OrderNumber": "    23456",
  "Amount": 37.94,
  "OrderLines": [
    {
      "ItemId": 65436,
      "Quantity": 5.0,
      "Amount": 29.95
    },
    {
      "ItemId": 7356,
      "Quantity": 1,
      "Amount": 7.99
    }
  ]
}

I hope I was clear enough.

Thanks for your time,

Tim Baart

ghost commented 4 years ago

Hi,

Is support for nested objects implemented? I have a very simple case to send one level child to server. But it seems child object gets stripped from request payload. Here is my example-

C#

public class Payload
    {
        public string Prop1 { get; set; }
        public string Prop2 { get; set; }
        public Child Child { get; set; }
    }

    public class Child
    {
        public Results[] Results { get; set; }
    }

    public class Results
    {
        public string Attr1 { get; set; }
        public string Attr2 { get; set; }
    }

Expected:

{
    "Prop1": "1567653",
    "Prop2": "1568900",
    "Child": {
        "results": [
            {
                "Attr1": "10",
                "Attr2": "10"
            }
        ]
    }
}

Actual:

{
    "Prop1": "1567653",
    "Prop2": "1568900",
}
NigelWhatling commented 4 years ago

I looked at this a year or so ago and have come back to it now. I managed to get some test output that looked ok to me but it throws an error. Not sure if it's something I'm doing or if the limitations of the base OData libraries are still causing problems. 😕

mbauerdev commented 3 years ago

Hi Vagif, I'm just wondering if this Pull Request solves the issue (not sure if it only addresses updates): https://github.com/OData/odata.net/pull/1585

However, the PR made it to ODataLib 7.6.2 Release: https://docs.microsoft.com/en-us/odata/changelog/odatalib-7x#odatalib-762-release

What do you think?

drventure commented 2 years ago

The last time I tried deep inserts with the Odata client lib (7.9.3) it didn't work. I was mainly interested in Deep inserts and not Deep updates at the time, so I didn't explicitly try a Deep update.

What I can't seem to find is whether deep inserts/updates were ever implemented in Simple.Odata.Client?

Any idea?

swidz commented 11 months ago

Hi, any updates? Does current version support deep inserts?