Hi, I am trying to return a CLR object from Iron Ruby. I have the following CLR type defined in C# public class BuildMetaData { public string Description { get; set; } } I have the following IronRuby file: $:.unshift(File.dirname(__FILE__) + ''/../bin/Debug'') require ''mscorlib'' require ''Horn.Core.DSL.Domain'' class MetaDataFactory def return_meta_data() meta = Horn::Core::DSL::Domain::BuildMetaData.new meta.Description = "A description of sorts" meta end end I have the following test that is failing: [Fact] public void Then_a_build_metadata_object_is_returned() { var engine = Ruby.CreateEngine(); engine.Runtime.LoadAssembly(typeof (BuildMetaData).Assembly); engine.ExecuteFile(buildFile); var klass = engine.Runtime.Globals.GetVariable("MetaDataFactory"); var instance = (RubyObject)engine.Operations.CreateInstance(klass); var metaData = (BuildMetaData)engine.Operations.InvokeMember(instance, "return_meta_data"); Assert.Equal(metaData.Description, "A description of sorts"); } It fails when trying to cast the object returned from IronRuby with the following error. System.InvalidCastException : [A]Horn.Core.DSL.Domain.BuildMetaData cannot be cast to [B]Horn.Core.DSL.Domain.BuildMetaData. Type A originates from ''Horn.Core.DSL.Domain, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null'' in the context ''LoadNeither'' at location ''C:\Projects\horn\branches\rubydsl\src\Horn.Dsl.Specificatioin\bin\Debug\Horn.Core.DSL.Domain.dll''. Type B originates from ''Horn.Core.DSL.Domain, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null'' in the context ''Default'' at location ''C:\Users\paul.cowan\AppData\Local\Temp\gjpo5svj.0zd\Horn.Dsl.Specificatioin\assembly\dl3\6d8ae49c\7acadf2b_c798c901\Horn.Core.DSL.Domain.DLL''. The only way I can access the members of the BuildMetaData is using reflection. If you look at the error message, both types are created in different locations. Is this possible in IronRuby yet? Cheers Paul -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://rubyforge.org/pipermail/ironruby-core/attachments/20090303/92215c71/attachment.html>
The problem is that CLR/Mono assembly loader loads the assembly twice into 2 different contexts: "LoadNeither" and "Default". Therefore there are actually 2 different types "BuildMetaData" in system. require ''Horn.Core.DSL.Domain'' uses Assembly.LoadFrom to load the assembly, which loads it to one context. A static assembly reference (in C#) is loaded via Assembly.Load, which loads to a different context. You can use Kernel#load_assembly or require ''<full assembly name>'' to invoke Assembly.Load. Tomas From: ironruby-core-bounces at rubyforge.org [mailto:ironruby-core-bounces at rubyforge.org] On Behalf Of Paul Cowan Sent: Tuesday, March 03, 2009 6:53 AM To: ironruby-core at rubyforge.org Subject: [Ironruby-core] Returning a Clr type in IronRuby Hi, I am trying to return a CLR object from Iron Ruby. I have the following CLR type defined in C# public class BuildMetaData { public string Description { get; set; } } I have the following IronRuby file: $:.unshift(File.dirname(__FILE__) + ''/../bin/Debug'') require ''mscorlib'' require ''Horn.Core.DSL.Domain'' class MetaDataFactory def return_meta_data() meta = Horn::Core::DSL::Domain::BuildMetaData.new meta.Description = "A description of sorts" meta end end I have the following test that is failing: [Fact] public void Then_a_build_metadata_object_is_returned() { var engine = Ruby.CreateEngine(); engine.Runtime.LoadAssembly(typeof (BuildMetaData).Assembly); engine.ExecuteFile(buildFile); var klass = engine.Runtime.Globals.GetVariable("MetaDataFactory"); var instance = (RubyObject)engine.Operations.CreateInstance(klass); var metaData = (BuildMetaData)engine.Operations.InvokeMember(instance, "return_meta_data"); Assert.Equal(metaData.Description, "A description of sorts"); } It fails when trying to cast the object returned from IronRuby with the following error. System.InvalidCastException : [A]Horn.Core.DSL.Domain.BuildMetaData cannot be cast to [B]Horn.Core.DSL.Domain.BuildMetaData. Type A originates from ''Horn.Core.DSL.Domain, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null'' in the context ''LoadNeither'' at location ''C:\Projects\horn\branches\rubydsl\src\Horn.Dsl.Specificatioin\bin\Debug\Horn.Core.DSL.Domain.dll''. Type B originates from ''Horn.Core.DSL.Domain, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null'' in the context ''Default'' at location ''C:\Users\paul.cowan\AppData\Local\Temp\gjpo5svj.0zd\Horn.Dsl.Specificatioin\assembly\dl3\6d8ae49c\7acadf2b_c798c901\Horn.Core.DSL.Domain.DLL''. The only way I can access the members of the BuildMetaData is using reflection. If you look at the error message, both types are created in different locations. Is this possible in IronRuby yet? Cheers Paul -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://rubyforge.org/pipermail/ironruby-core/attachments/20090303/c82f6be6/attachment-0001.html>
I was running the test using the R# test runner and once I turned off the shadow-copy assemblies being tested option then the test now passes. 2009/3/3 Tomas Matousek <Tomas.Matousek at microsoft.com>> The problem is that CLR/Mono assembly loader loads the assembly twice > into 2 different contexts: ?LoadNeither? and ?Default?. > > Therefore there are actually 2 different types ?BuildMetaData? in system. > > > > require ''Horn.Core.DSL.Domain'' uses Assembly.LoadFrom to load the assembly, > which loads it to one context. > > A static assembly reference (in C#) is loaded via Assembly.Load, which > loads to a different context. > > > > You can use Kernel#load_assembly or require ?<full assembly name>? to > invoke Assembly.Load. > > > > Tomas > > > > *From:* ironruby-core-bounces at rubyforge.org [mailto: > ironruby-core-bounces at rubyforge.org] *On Behalf Of *Paul Cowan > *Sent:* Tuesday, March 03, 2009 6:53 AM > *To:* ironruby-core at rubyforge.org > *Subject:* [Ironruby-core] Returning a Clr type in IronRuby > > > > Hi, > I am trying to return a CLR object from Iron Ruby. > > I have the following CLR type defined in C# > > public class BuildMetaData > { > public string Description { get; set; } > } > > I have the following IronRuby file: > $:.unshift(File.dirname(__FILE__) + ''/../bin/Debug'') > require ''mscorlib'' > require ''Horn.Core.DSL.Domain'' > class MetaDataFactory > def return_meta_data() > meta = Horn::Core::DSL::Domain::BuildMetaData.new > meta.Description = "A description of sorts" > meta > end > end > > I have the following test that is failing: > > [Fact] > public void Then_a_build_metadata_object_is_returned() > { > var engine = Ruby.CreateEngine(); > engine.Runtime.LoadAssembly(typeof (BuildMetaData).Assembly); > engine.ExecuteFile(buildFile); > var klass = engine.Runtime.Globals.GetVariable("MetaDataFactory"); > var instance = (RubyObject)engine.Operations.CreateInstance(klass); > var metaData = (BuildMetaData)engine.Operations.InvokeMember(instance, > "return_meta_data"); > Assert.Equal(metaData.Description, "A description of sorts"); > } > > It fails when trying to cast the object returned from IronRuby with the > following error. > > System.InvalidCastException : [A]Horn.Core.DSL.Domain.BuildMetaData cannot > be cast to [B]Horn.Core.DSL.Domain.BuildMetaData. Type A originates from > ''Horn.Core.DSL.Domain, Version=1.0.0.0, Culture=neutral, > PublicKeyToken=null'' in the context ''LoadNeither'' at location > ''C:\Projects\horn\branches\rubydsl\src\Horn.Dsl.Specificatioin\bin\Debug\Horn.Core.DSL.Domain.dll''. > Type B originates from ''Horn.Core.DSL.Domain, Version=1.0.0.0, > Culture=neutral, PublicKeyToken=null'' in the context ''Default'' at location > ''C:\Users\paul.cowan\AppData\Local\Temp\gjpo5svj.0zd\Horn.Dsl.Specificatioin\assembly\dl3\6d8ae49c\7acadf2b_c798c901\Horn.Core.DSL.Domain.DLL''. > > The only way I can access the members of the BuildMetaData is using > reflection. > > If you look at the error message, both types are created in different > locations. > > Is this possible in IronRuby yet? > > Cheers > > Paul > > _______________________________________________ > Ironruby-core mailing list > Ironruby-core at rubyforge.org > http://rubyforge.org/mailman/listinfo/ironruby-core > >-------------- next part -------------- An HTML attachment was scrubbed... URL: <http://rubyforge.org/pipermail/ironruby-core/attachments/20090303/cfe996bb/attachment.html>