Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

dynamices crm annotations #411

Open
vladimirsakic opened this issue Jun 28, 2017 · 17 comments
Open

dynamices crm annotations #411

vladimirsakic opened this issue Jun 28, 2017 · 17 comments
Assignees
Milestone

Comments

@vladimirsakic
Copy link

dynamics crm odata service returns annotations like this one:
{
"@odata.count":1,
"value":[
{
"@odata.etag":"W/"1608905"",
"[email protected]":"Address Boulevard",
"_dot_propertyid_value":"9a11328b-5c15-e711-80e5-1458d043b558",
}
]
}

I have field _dot_propertyid_value, but how can I map to [email protected]

Thanks

@object
Copy link
Member

object commented Jul 9, 2017

Hi,
Currently the library doesn't support handling of custom annotations (it only supports standard annotations defined by OData protocol: id, count, deltaLink, nextPageLink etc.) So I am afraid it's not possible to achieve what you want without intercepting the response using custom rewriter.

@vladimirsakic
Copy link
Author

Maybe it's good idea to write that rewriter for dynamics crm, because as I know, most developers use this library for communicating with web api endpoint

@object
Copy link
Member

object commented Jul 10, 2017

That can make sense. Unfortunately I have never used Dynamics CRM, so I have no knowledge of what kind of annotations such rewriter should be aware of.

@vladimirsakic
Copy link
Author

vladimirsakic commented Jul 10, 2017 via email

@object
Copy link
Member

object commented Jul 10, 2017

This sounds like a candidate for the next major version upgrade. And it has to be opted in in a smart way, i.e. developers not using Dynamic CRM shouldn't be aware of that. But if you have a reference to documentated annotations as well as some examples, it's worth taking into account.

@vladimirsakic
Copy link
Author

As far as I know @OData.Community.Display.V1.FormattedValue is only field level annotation, as I sad, purpose id to get some string value along with guid or int id. Header to turn on this annotations is "Prefer: odata.include-annotations=OData.Community.Display.V1.FormattedValue"

https://msdn.microsoft.com/en-us/library/gg334767.aspx#bkmk_includeFormattedValues

@vladimirsakic
Copy link
Author

Sorry, there's two more: @Microsoft.Dynamics.CRM.associatednavigationproperty and @Microsoft.Dynamics.CRM.lookuplogicalname

@vladimirsakic
Copy link
Author

and @odata.nextLink

@object
Copy link
Member

object commented Jul 12, 2017

But this one is a part of OData spec.

@ericleigh007
Copy link

Any further thoughts on this?
If I had time, I'd look at how to do this and offer a PR, but unfortunately, I don't.

@object object added this to the 6.0 milestone May 23, 2018
@object object self-assigned this May 23, 2018
@object
Copy link
Member

object commented May 23, 2018

So far no progress, but I see this request is coming from several people, so I plan to start working on it.

@bdebaere
Copy link

bdebaere commented Jul 4, 2018

@object Isn't this already implemented seeing as https://github.com/OData/vocabularies/blob/master/OData.Community.Display.V1.md speaks of using it for property values? I can't find an example online on how to code it though.

@toryb
Copy link

toryb commented Aug 10, 2018

@object I need to get field-level annotations for Dynamics CRM.

Could you provide a little more information about your suggestion earlier in this thread that someone could "intercept the response using custom rewriter"?

I assume you mean to assign an action to ODataClientSettings.AfterResponse in order to intercept the response. If I do that, what I am going to do with the annotations to surface them in the value returned by FindEntriesAsync(annotations)? Any direction would be helpful.

Thanks.

@flieks
Copy link

flieks commented Aug 14, 2018

@toryb I also can't find any examples on how to implement the odata.include-annotations defined in the odata web api docs

@vladimirsakic did you find a solution?

@object ODataClientSettings.AfterResponse is for the client side right ? But the server has to include other values in the response based on Display attributes.

@toryb
Copy link

toryb commented Nov 21, 2018

@flieks You are correct, the server does need to include annotations. This is done based on the request to include annotations in the prefer header of the request (i.e. Prefer: odata.include-annotations="*"). I have used the ODataClientSettings.BeforeResponse to add the request to the header so I get all annotations with each request.

@vladimirsakic The way I have implemented the handling of CRM annotations is in the ODataClientSettings.AfterResponse. The way I handle them is to parse the content into a JObject and find the properties that contain an "@" (but don't start with "@"). Here is that line of code:

var annotationProperties = contentObject.Properties().Where(x => x.Name.Contains("@") && !x.Name.StartsWith("@"));

Then, by splitting the property name by '@' I get the property it applies to and the annotation to be applied:

 foreach (var prop in annotationProperties)
 {
    // Get the field name
    var values = prop.Name.Split(new char[] { '@' }, StringSplitOptions.RemoveEmptyEntries);
    if (values.Length != 2) break;
    if (Entity.FieldDictionary.ContainsKey(values[0]))
    {
      var entityField = Entity[values[0]];
      string value = prop.Value.ToString();
      string annotationType = values[1];
      switch (annotationType)
      {
        case "OData.Community.Display.V1.FormattedValue":
          {
            PropertyInfo pi = entityField.FieldType.GetProperty("FormattedValue");
            pi.SetValue(Entity[values[0]].FieldImpl, value);
          }
          break;
        case "Microsoft.Dynamics.CRM.lookuplogicalname":
          {
            PropertyInfo pi = entityField.FieldType.GetProperty("LookupLogicalName");
            // System.Diagnostics.Debug.Assert(prop.Value is string);
            pi.SetValue(Entity[values[0]].FieldImpl, value);
          }
          break;
        case "Microsoft.Dynamics.CRM.associatednavigationproperty":
          {
            PropertyInfo pi = entityField.FieldType.GetProperty("AssociatedNavigationProperty");
            // System.Diagnostics.Debug.Assert(prop.Value is string);
            pi.SetValue(Entity[values[0]].FieldImpl, value);
          }
          break;
      }
    } // end switch annotation type
  } // end foreach

There is probably much in there that needs explanation, but the essence of it is to search the response for field-level annotations and apply them to your implementation of the object as appropriate.

I hope that helps.

@EduardoRomo
Copy link

Any updates on this feature?

@Soulfire86
Copy link

Needing this here in 2024. Any ideas?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

8 participants