Using SignalR, how do I send a dictionary (associative array) to Javascript? - javascript

dictionary isn't serializeable, and therefore can't be sent to my clients JavaScript code via SignalR as a Javascript (pseudo) associative array...
in .net, my complex type is:
public class MyClass {
public [primitive] whatever {get;set;}
...
public Dictionary<string, string> Properties { get; set; }
}
and in Javascript, I'd like to be able to reference the data like this:
data.Properties["key"]
Update:
I'm trying to serialize to and from a string first because I route the instance through SQL Service Broker. On this line:
XmlSerializer serializer = new XmlSerializer(typeof(T));
Where T is typeof MyClass
There was an error reflecting type [MyClass]
Cannot serialize member [MyClass].Properties of type System.Collections.Generic.Dictionary`2[[System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089],[System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]], because it implements IDictionary.
I feel like I'm about to answer my own question...

SignalR uses Json.NET which is definitely able to to serialize a Dictionary<string, string>. You should be able to access the dictionary from JS code in the exact manner you suggest in your question.
Have you tried sending an instance of your MyClass using SignalR? If so, how does it fail?

I changed:
XmlSerializer serializer = new XmlSerializer(typeof(T));
to:
DataContractSerializer serializer = new DataContractSerializer(typeof(T));
(and dealt with some namespace issues...)

Related

how to return js object to unity

I'm using the Google Draco decoder to decode mesh the following.
var dracoGeometry;
dracoGeometry = new decoderModule.Mesh();
decodingStatus = decoder.DecodeBufferToMesh(buffer, dracoGeometry);
when I check the type of the draceGeometrytry:
console.log( typeof dracoGeometry);
I get the
"object" type.
Now my problem is "how can I return this object to unity". What return type supported in C# to accept js object?
You can send strings or numbers, so what I would do is create a js object that has the data you need then call JSON.stringify on it to convert it to a string then send that over using unityInstance.SendMessage:
function sendToUnity(obj) {
unityInstance.SendMessage('MyGameObject', 'MyMethod', JSON.stringify(obj));
}
// in a script attached to a gameobject named "MyGameObject"
void MyMethod(string s)
{
Debug.Log(s);
// decode from json, do stuff with result etc
}
As for what you can do with that data while it is in JSON string form, you can use a variety of solutions to decode the JSON string once you have it in Unity. See Serialize and Deserialize Json and Json Array in Unity for more information.
So if your js looks like this:
function sendToUnity(obj) {
unityInstance.SendMessage('MyGameObject', 'MyMethod', JSON.stringify(obj));
}
sendToUnity({
playerId: "8484239823",
playerLoc: "Powai",
playerNick:"Random Nick"
});
You could do something like this in Unity:
[Serializable]
public class Player
{
public string playerId;
public string playerLoc;
public string playerNick;
}
...
void MyMethod(string s)
{
Player player = JsonUtility.FromJson<Player>(s);
Debug.Log(player.playerLoc);
}
Source: Programmer's answer
There are some methods available, but it doesn't seem possible at the moment to send a mesh from js to unity. If you are working with google draco, I recommend you to follow this fork

converting JSON object in spring MVC

in the example below i have one method sendJsonResponce method which is nothing but the putting string values to Map and we are returning that map from createChildSalesPosition method to our webpage.
we are using Spring MVC here, as i have gone through some websites saying that you need to change the object to JSON type when you want to send a JSON response but in my project i find this which is sending JSON response without any type conversion in JSON.
since the guy who had developed the application is no more available i got stuck here.
#RequestMapping(value="createChildSalesPositions.json",produces="application/json")
#ResponseBody
public Map<String,String> createChildSalesPositions(#RequestParam("tId") Integer templateId,#RequestParam("prnSalesPosId") Long prnSalesPosId,#RequestParam("prnSalesHierId") Long prnSalesHierId,
HttpServletRequest request,#ModelAttribute("ALIGNMENTINFO") AlignmentInfo alignmentInfo,#ModelAttribute("USERSESSION") UserDetails userDetails)throws BusinessException, IOException{
try{
return sendJosnResponse(crId);
}
}catch(Exception e){
return sendErrorResponse(e);
}
}
private Map<String,String> sendJosnResponse(long crId) throws IOException{
Map<String,String> tosend =new HashMap<String,String>();
tosend.put("code", "200");
tosend.put("message", "CR "+crId+" has been generated successfully.");
tosend.put("crId", String.valueOf(crId));
return tosend;
}
You need to tell the spring framework how to convert the java object to json. The spring framework uses HttpMessageConverter to do that, to convert the java object to json spring can use the jackson libraray.
To enable this support you can either use the #EnableWebMvc annotation or <mvc:annotation-driven/> xml configuration and add the jackson library to your classpath.

Error using dynamic keyword in asp.net mvc 4

I am getting this long error when i accpet the parameter as dynamic on my server side action method in mvc 4.
{"Message":"An error has
occurred.","ExceptionMessage":"'Newtonsoft.Json.Linq.JObject' does not
contain a definition for
'TournamentId'","ExceptionType":"Microsoft.CSharp.RuntimeBinder.RuntimeBinderException","StackTrace":"
at CallSite.Target(Closure , CallSite , Object )\r\n at
System.Dynamic.UpdateDelegates.UpdateAndExecute1[T0,TRet](CallSite
site, T0 arg0)\r\n at
ManagerDeTorneos.Web.Controllers.TournamentDateController.Create(Object
data) in
F:\Prince\Projects\Juan\trunk\ManagerDeTorneos.Web\Controllers\TournamentDateController.cs:line
133\r\n at lambda_method(Closure , Object , Object[] )\r\n at
System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.<>c_DisplayClass13.b_c(Object
instance, Object[] methodParameters)\r\n at
System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.Execute(Object
instance, Object[] arguments)\r\n at
System.Threading.Tasks.TaskHelpers.RunSynchronously[TResult](Func`1
func, CancellationToken cancellationToken)"}
[HttpPost]
public HttpResponseMessage AddMatch(dynamic data)
{
int tournamentDateId = (int)data.TournamentDateId.Value;
var tournamentDate = Catalog.TournamentDateRepository.GetById(tournamentDateId);
if (tournamentDate == null)
{
throw ExceptionHelper.NotFound("Fecha no encontrada!");
}
In The above method data Contains tournamentId as sent from ajax call as JSON.Stringify({'TournamentId':'5'}).
Can anybody tell me what is the cause of error. I even replaced the dll of Newtonsoft.Json as well
You are right dan but i fixed my issue by removing that dll from GAC. May be in GAC it was using old assembly
The error is caused by the fact that you typed your parameter as dynamic, which means that the model binder doesn't know what to make it. It's the same as if you were to declare it as an object. Since you are providing JSON, it serializes the object as a Json.Net JObject. Just because you define it as a dynamic doesn't mean that it's going to magically take whatever shape you need it to.
Change it to a concrete type - something that matches the structure of the provided JSON:
public class TournamentInfo
{
public int TournamentId { get; set; }
}
[HttpPost]
public HttpResponseMessage AddMatch(TournamentInfo data)
{
int tournamentDateId = data.TournamentId;
var tournamentDate = Catalog.TournamentDateRepository.GetById(tournamentDateId);
if (tournamentDate == null)
{
throw ExceptionHelper.NotFound("Fecha no encontrada!");
}
This way, the binder knows what it's supposed to turn the JSON into, and since TournamentInfo matches the structure of the JSON, it won't have any trouble serializing it.
Don't misuse dynamic. It was not introduced into C# so developers could stop defining classes.

JSON representation of a list of keyvaluepairs

I have an MVC JSON controller method that I call from frontend. It looks like this:
public JsonResult FacetedSearch(string searchString, List<KeyValuePair<string,string>> facets)
I'm calling it via jQuery ajax at the frontend, I'm serializing the data in the following manner:
JSON.stringify({searchString: "the matrix", facets: [{Key: "TypeName", Value: "Feature Film"}, {Key:"TypeName", Value:"Series"}]}
When I debug through my application code, I see that searchString gets passed successfully over to the MVC method, but the variable facets gives me a list of 2 KeyValuePairs with null Key and Value.
I've looked at my serialization and it seems valid but for whatever reason it isn't going over to my application correctly. What gives?
Rather than expect two objects in your signature, it would make more sense to expect a single object that contains both of your parameters. This would be something like the following.
public JsonResult FacetedSearch(RequestObject requestObject)
{ }
public class RequestObject
{
public string searchString { get; set; }
public List<KeyValuePair<string,string>> facets { get; set; }
}
This way, when you send your JSON object, the signature is an object with two properties, just like the object that you are sending.
Per Is there a serializable generic Key/Value pair class in .NET?
I found out why it's not serializing it. Apparently it's unserializable.

Model DataAnnotation for asp.net mvc

Is there any way to get dataanotations for my models directly from my database?
I have a database with lot's of data and tables, so i am generating my model with entity framework from database, so i get classes, but i want to know can entity framework or some other orm get properities and constrains directly from database and put them in classes as data anotation like [required] or [datatype(datatype.emailadress)]
Yes. You can inherit the ModelMetadataProvider class:
public class LocalizedModelMetadataProvider : DataAnnotationsModelMetadataProvider
{
protected override ModelMetadata CreateMetadata(IEnumerable<Attribute> attributes, Type containerType,
Func<object> modelAccessor, Type modelType, string propertyName)
{
var metadata = base.CreateMetadata(attributes, containerType, modelAccessor, modelType, propertyName);
if (containerType == null || propertyName == null)
return metadata;
// Load all metadata from your database here.
return metadata;
}
}
I'm creating a project called Griffin.MvcContrib which is almost done and has a administration area where you can handle all localization (zero-code) for both models and validation messages.
By using it you can just implement the following interface to get support for your database:
// the actual code file has detailed explanations of each method.
public interface ILocalizedStringProvider
{
string GetModelString(Type model, string propertyName);
string GetModelString(Type model, string propertyName, string metadataName);
string GetValidationString(Type attributeType);
string GetEnumString(Type enumType, string name);
}
Update
Where is not important. And you do not have to use DataAnnotation attributes on your models (the [Display] attribute). I just inherit the DataAnnotationsModelMetadataProvider to be able to use the attributes.
Create the class anywhere.
Read from the database
Configure MVC to use it in global.asax
Example:
ModelMetadataProviders.Current = new YourModelMetadataProvider();

Categories

Resources