Dynamics CRM Plugin Shared variables - Object or Array - c#

We have a scenario where we need to calculate multiple fee components & share between Pre & Post stages of a Plugin. So we created the object like this.
class FeeCalculation
{
public string TotalFee { get; set; }
public string FilingFee { get; set; }
public string LegalFee { get; set; }
public string RecordFee { get; set; }
}
So far we have used single fee component & shared variable worked nicely. When tried to assign the whole object - the result is not fruitful.
context.SharedVariables.Add("fees", fcObject);
Is there a way to achieve this expected result?

The plugin infrastructure must be able to serialize/deserialize the objects that are in your SharedVariables collection. It has no knowledge of custom types like the FeeCalculation class and therefore cannot serialize it.
Use primitive types, common .NET types (e.g. a List of decimals should work) or CRM types (Entity, Money etc.). It's good to note that the SharedVariables collection is a key value pair collection. So, why not just add items to it with keys like "TotalFee", "FilingFee" etc?

I was trying to share an IEnumerable<Guid>, but collections like List did not work.
Of course you can always serialize to string, but your plugin code really shouldn't have to deal with serialization of common types.
After some trial and error, I ended up using arrays, i.e. Guid[].

Related

Assign Different Type to Class Property

I have created a class to store data from API calls I am making. It returns JSON with some meta information, and then an array of data depending on the call being made. The meta information will always have the same fields, so I have created a "Root" class for this, but the data will be different depending on the call being made, so I have created different classes for each type of data, e.g. user data, company data, etc. As shown below, I currently have the "data" property set to a list of objects, but I am trying to figure out the best way to incorporate the different types of data that can be returned, since it will vary based on the call being made.
Right now I have the data saved as a list of objects, but I would like this to change depending on what data I am receiving. Like, if I am retrieving users, I would like for it to be a list of users.
What is the ideal way to accommodate for this? The only way I can think to do it now is to create a different "Root" class for every type of data I am expecting to receive, but that doesn't feel like it should be the most concise way to do it. I was looking into making this a factory design pattern but I wasn't sure that it fit this scenario.
Just use a generic base class:
public abstract class ApiCallResult<T>
{
// With your properties
// public int Limit { get; set; }
// [...]
//
public IEnumerable<T> Data { get; set; }
}
Then define a result per api call.
public class UserApiCallResult : ApiCallResult<User>
{
}
Created a small working example here:
dotnet fiddle

Distinct event types on same collection - MongoDB and .NET Core

I want to use MongoDB to store domain events in a system written with .NET Core and C#.
I've googled a little about this, and it seems it is a common practice to have a single collection called events and simply store all events there. I've also seem people to create one field type to distinguish events. An example of this is Slide 66 of this presentation.
So if I wanted to save one UserCreated event I would add it with type user-created, and so forth.
Now I'm in doubt with respect to the mapping when it comes to using .NET Core.
Two distinct events will in general have different schema, so I think that the automatic mapping would do no good. Of course I could use the option of ignoring extra elements. But it may be the case that two events have subsets of properties which are equal, for example, all of them will have a OccurredOn DateTime. I think this could be an issue.
My idea was to query the field type. Something like:
colection.Find(BsonDocument.Parse("{type: user-created}"))
But I don't know if that is the best option, or if there is a way to set up a mapping so that the MongoDrive knows that whenever we try to get an instance of UserCreated it should look just for that type, and when we try to insert, it should create the correct type field.
In that case: given that we save distinct event types to the same collection, what is the correct approach to map this into the right C# event objects?
You could use a container like this one.
public class DomainEventContainer
{
public ObjectId Id { get; set; }
public string Type { get; set; }
public string EventData { get; set; }
}
And then based on the value of DomainEventContainer.Type, you could deserialize EventData into your desired type.

Generic comparison logic for objects

I am working on the back end of a REST API -
For a POST request (in one of the scenarios) I need to validate if the object sent by the user is the same as the one stored in the Db.
What is an efficient way of comparing two objects in C#?
PS - I want the comparison logic to withstand the test of time, i.e. being a huge team I do not rely on people adding new fields in the IComparable logic. Anyone can add a new property to the object and that would skip the validation test if they do not add that to the comparison logic.
I am thinking of Deserializing the object stored in our database and compare it to the deserialized version of that the user POSTS.
Any thoughts?
Automagically implement IComparable<T> on T for ValueObjects (objects for which their identity is all of their fields) is a form of Aspect-Oriented Programming (AOP).
There are various Aspect frameworks for C#.
In this case I would advise you use PM> Install-Package Equals.Fody.
To use it is pretty easy.
[Equals]
public class Foo
{
public int X { get; set; }
public int Y { get; set; }
}

C# Deserialize Complex Object From QueryString

I'm forced to use GET requests to pass complex objects to my application.
How can I deserialize a querystring like this:
?people[andy]=12&people[bob]=43&people[charlie]=53&items=89&items=123&x=zulu
into a custom object like this?
public class myClass {
public Dictionary<string, int> people { get; set; }
public int[] items { get; set; }
public string x { get; set; }
}
Is there a better (more sophisticated) way to do this besides splitting it by & and looping through the results to manually set each value?
Any pointers / guidance would be greatly appreciated.
If you have control over the sending side of the application, I strongly suggest you use a different encoding method to make parsing easier. I would just JSON encode the entire object, and then URIencode the JSON if it must be in the query_string.
There are often fairly small (on the order of 2K characters) limits to the size of URIs including the query_string. If you are forced to use HTTP, depending on your use case and whether you have control over this, POST may be preferable.
See this question for some methods of deserializing JSON:
C# deserialize dynamic JSON

Binding lists of objects in MVC3

I have an issue with the project I'm working on. I'm using Entity Framework. Some quick background on the db model:
public class AssetType{
public ICollection<Field> Fields { get; set; }
}
public class Field{
public int Id {get;set;
public string Name {get;set;
}
Now I'm creating a view that would create a new Asset Type. As part of this process the user must also create all of the fields they want for that type. The issue is that I'm not sure how to represent the list of "Fields" on the page. The idea is that the user can add a new field, or remove one at any time with jQuery.
I can't figure how the data could be posted back to the server as part of the form. I thought about constructing the list in JSON form, but this seemed a bit messy. Has anyone got any better ideas?
You're going to have problems with this. The object parser does not handle complex objects very well. Collections usually need to be primitive types, or collections of primitive types themselves.
There are ways to do it, but if this is a requirement for you, I would look at storing your data in a JSON string variable, and parsing it where/ when needed.

Categories