Error serializing with ServiceStack JSON on MonoTouch - xamarin.ios

I am experimenting with ServiceStack's JSON engine. I grabbed the MonoTouch binary build, v2.20. Works fine from simulator, but from the iOS device (iPad2, iOS5) I get an exception thrown by the type initializer for JsonWriter (and not much other than that). I am using MonoTouch 5, MonoDevelop 2.8.1, and targeting iOS 5. I have disabled library linking because I am getting an error when enabled.
I created a sample and uploaded to https://github.com/t9mike/ServiceStack-JSON1.
I'm trying to determine whether the issue is my compilation options, Service Stack, or MonoTouch. Thanks in advance.

A quick partial answer that might help:
I have disabled library linking because I am getting an error when enabled.
The current (5.0) managed linker can eliminate some unused (from a static analysis point of view) code from your application. This generally occurs when using Link all option, i.e. where user code gets processed by the linker.
One alternative is using the Link SDK assemblies only that won't touch the user code (only the code shipped with MonoTouch itself will be processed by the linker).
Another alternative is adding [Preserve] attributes on your code to ensure the serializer requirements are still met after the linker has processed your code. More information about the linker and [Preserve] attributes can be found here.
The next (5.2) release of MonoTouch will include a bit more sophisticated step in the linker to ensure the basic XML serialization and DataContract requirements are not broken. Not sure if this will solve this specific case (ServiceStack JSON) but I'll have a look into it.
As for the rest of your question I'll try to build this myself and duplicate your issue.

I ended up grabbing the ServiceStack.Text sources from GitHub, version 3.0.3. I created a new MonoTouch library project. I had to tweak ServiceStack.Text/JsConfig.cs slightly to conditionalize away the System.Drawing.Color bits. I'll send a patch and MT csproj to the authors.
After using this new assembly, my sample MT app ran fine on the device. I have updated my sample at https://github.com/t9mike/ServiceStack-JSON1 with the new ServiceStack.Text dll.

Related

Acumatica Publishing with DLL resulting in System.BadImageFormatException

I am trying to add some external DLLs to the Acumatica Customisation project but upon publishing it results in "System.BadImageFormatException: Format of the executable (.exe) or library (.dll) is invalid."
Error Image:
I already have added multiple DLLs to the Customisation. And was using the method specified here: Acumatica unable to publish the Customization Package to skip over the errors, but in this case it does not seem to be working.
The first step should be identifying which DLL is the culprit. I suggest you create an empty project and put the files in there one by one with the ignore rules. Maybe you missed to add ignore rule for one of the files.
This error happens because Acumatica attempts to parse the DLL as a .Net framework assembly. If you add non .Net assembly such as native x86/x64 compiled libraries you need to add the ignore rule so Acumatica doesn't attempt to parse it.
If the error is coming from a DLL you compiled, make sure it was compiled in Any CPU platform. This prevents any incompatibility related to 32 bit/64 bit mismatch.

How can I use AutoMapper with my Xamarin.iOS project?

It seems that when I reference AutoMapper v3.1.0 in my Xamarin.iOS project, the build fails with this error message:
Error MT2002: Failed to resolve "System.Linq.Expressions.Expression System.Linq.Expressions.ExpressionVisitor::Visit(System.Linq.Expressions.Expression)" reference from "System.Core, Version=2.0.5.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e" (MT2002)
When I roll back to the revision before I added this, it all works fine.
Unfortunately, I've already done quite a bit of work with AutoMapper in my unit tests and it would be problematic to remove it now. I guess that's a lesson to learn: just because it works in a test doesn't mean it works in Xamarin.iOS.
I would be very grateful if anyone has any ideas.
Edit: I have now discovered a MonoTouch directory in the AutoMapper package, but referencing the AutoMapper.dll and AutoMapper.iOS.dlls found within does not solve the problem.
Edit #2: This issue only occurs when building for the device - I guess the MSIL to native converter doesn't like AutoMapper for some reason. I'm trying to find a way to "hint" to this compiler that we need these symbols, which is what I think the purpose of the LinkerPleaseInclude.cs file is.
This issue is temporarily resolved - I had to hack out the offending symbols in AutoMapper and recompile it. Please see automapper issue #429 for more information on what symbols I removed. Until AutoMapper is updated to fix this problem, that's how you have to solve it for now.
The reason for this is explained concisely in another StackOverflow question - basically there are subtle differences between the .NET and Mono frameworks that in this case are incompatible with AutoMapper.
This answer previously stated that you should turn off linking to work with AutoMapper. While you can do this for development, it's not suitable for production use as it will yield a massive binary and you will not be able to submit your app to the app store.

Using Protobuf-Net In Xamarin.iOS without full AOT

Is there any alternative to achieving serialising and deserialising of objects in Xamarin.iOS (Monotouch) using protobuf-net other than this method:
http://www.frictionpointstudios.com/blog/2011/3/31/using-protobuf-net-serialization-in-unity-iphone.html
Reading around some people claim they have managed it (without giving evidence), but my understanding is that [iOS JIT==NO] so does not quite make sense.
If the only possible solution is to fully AOT all relevant classes what might a suitable pre/post-build event command line be to perform this AOT for any relevant assemblies automatically?
I've heard a good number of people have success via that route, but I too can't give documented evidence.
That method is a bit out of date - I've simplified a few steps; there is a standalone pre-compile tool that should work:
create a project/assembly for the DTOs that you want to serialize that references the appropriate version of protobuf-net; presumably CoreOnly/ios, ideally with that dll set to copy into the output directory (it just makes life easier)
run
precompile "SomePath/YourDto.dll" -t:MySerializer -o:MySerializer.dll
(maybe with a mono before that to get mono to host the exe)
this should resolve the framework and compile a MySerializer.dll that you can reference, which involves zero JIT (MySerializer.dll will reference your dto dll and the version of protobuf-net that your dto dll referenced)
now reference your dto dll, the serializer dll, and the protobuf-net dll, and it should all work just by using new MySerializer().Serialize(...)
when you compile your solution, the projects should all AOT nicely
I'll be happy to offer guidance, but currently I am mac-less, so I can't check right now. If you get any problems let me know. If it can't resolve the framework, you can add -f:{path to the framework assemblies} to give it a clue.
I got protobuf-net 2 working on Xamarin-iOS by using the netstandard1.0 dll. You can get this dll by extracting the nuget package. No changes were needed.

Running sample projects in MvvmCross v3 (Hot Tuna)

I'm trying to run sample projects (viz. BestSellers and Conference) that are present in MvvmCross v3 branch. I resolved the strong assembly reference issues successfully. However each time I run a sample project, I get System.TypeLoadException in MvxFullBinding and MvxValueConverterRegistryFiller classes.
Exception in MvxFullBinding class:
Exception in MvxValueConverterRegistryFiller class:
Is anybody able to run the sample projects successfully? How do I get around these exceptions?
It looks like you're running this as the 'Touch' projects from Visual Studio? In which case you are way ahead of what I've managed to achieve.
If that is correct, then I suspect that what you are seeing is that you have:
built proper PCLs built in VS/Windows against the portable reference assemblies
but these cannot be executed against the current MonoTouch/Xamarin.iOS runtime.
If you try, you may see issues like: iOS black screen and MissingMethodException: Method not found: 'System.Type.op_Equality'
For some more info see 'almost portable binaries' on http://slodge.blogspot.co.uk/2013/01/almost-portable-binaries.html
There is 'proper' PCL support currently being worked on within XamLabs - so I am hopeful that there may be a solution to this problem arriving in the Xamarin.Android Alpha channel any day now - but don't expect this to be painless initially.
Of course, I might be wrong on this - this really is new territory and I will be fascinated to hear/read about your adventures. If you want to try to find more detail, then it may help to try looking deeper into the exception details, and looking into the console log trace on your mac.
For these two particular exceptions, I can confirm that both samples...
... although that is when I'm working on my Mac.

Is InternalsVisibleTo available to allow MonoTouch Unit Tests access to the internal of a MT Lib?

Can you use the InternalsVisibleTo assembly attribute in a AssemblyInfo file of a MonoTouch Library to allow MonoTouch Unit Test (Touch.Unit) access to the internals of the MonoTouch library?
This is something that is great to use in non-MonoTouch world to allow testing of internals without having to jump through hoops. However I am not able to get it working with a MonoTouch Unit Test. So before I go any futher I figured I would ask if it is even possible, since this is an iOS Application that is the test runner, so not sure if an iOS application which is compiled to native code can even do this.
Yes, it should (or it's a bug) even if I do not recall trying it myself.
The key point is that [InternalsVisibleTo] is mostly a compiler trick and it is supported by the C# compiler (smcs) shipped with MonoTouch (as it's used inside the BCL). As such there's no reason why it should not work from a Touch.Unit-based application.
Now keep in mind that all other rules still applies. E.g. if the the managed linker is enabled when all unused code will be removed (even if marked with the attribute).

Resources