From 3c2ee6eb4225e32961c7433687b3220249ab5af4 Mon Sep 17 00:00:00 2001 From: eeichinger Date: Sun, 19 Oct 2008 09:52:48 +0000 Subject: [PATCH] fixed SPRNET-1059 --- .../solutions/Spring.Net.Core.2008.sln | 24 ++++ .../Web/Services/WebServiceExporter.cs | 129 ++++++++++++++---- .../Web/Support/LocalResourceManager.cs | 4 +- src/Spring/Spring.Web/Web/UI/Page.cs | 3 +- 4 files changed, 126 insertions(+), 34 deletions(-) diff --git a/build-support/solutions/Spring.Net.Core.2008.sln b/build-support/solutions/Spring.Net.Core.2008.sln index 7214bace..7d77c74d 100644 --- a/build-support/solutions/Spring.Net.Core.2008.sln +++ b/build-support/solutions/Spring.Net.Core.2008.sln @@ -15,6 +15,10 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Spring.Aop.2008", "..\..\sr EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Spring.Aop.Tests.2008", "..\..\test\Spring\Spring.Aop.Tests\Spring.Aop.Tests.2008.csproj", "{2111596A-0327-4C9D-8919-294FBD988A23}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Spring.Services.2008", "..\..\src\Spring\Spring.Services\Spring.Services.2008.csproj", "{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Spring.Services.Tests.2008", "..\..\test\Spring\Spring.Services.Tests\Spring.Services.Tests.2008.csproj", "{4374F018-9738-46BF-A399-4594CEE75B21}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|.NET = Debug|.NET @@ -95,6 +99,26 @@ Global {2111596A-0327-4C9D-8919-294FBD988A23}.Release|Any CPU.Build.0 = Release|Any CPU {2111596A-0327-4C9D-8919-294FBD988A23}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU {2111596A-0327-4C9D-8919-294FBD988A23}.Release|Mixed Platforms.Build.0 = Release|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Debug|.NET.ActiveCfg = Debug|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Debug|Any CPU.Build.0 = Debug|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Release|.NET.ActiveCfg = Release|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Release|Any CPU.ActiveCfg = Release|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Release|Any CPU.Build.0 = Release|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU + {FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}.Release|Mixed Platforms.Build.0 = Release|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Debug|.NET.ActiveCfg = Debug|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Debug|Any CPU.Build.0 = Debug|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Release|.NET.ActiveCfg = Release|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Release|Any CPU.ActiveCfg = Release|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Release|Any CPU.Build.0 = Release|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU + {4374F018-9738-46BF-A399-4594CEE75B21}.Release|Mixed Platforms.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/src/Spring/Spring.Web/Web/Services/WebServiceExporter.cs b/src/Spring/Spring.Web/Web/Services/WebServiceExporter.cs index e24e844b..4df2e96b 100644 --- a/src/Spring/Spring.Web/Web/Services/WebServiceExporter.cs +++ b/src/Spring/Spring.Web/Web/Services/WebServiceExporter.cs @@ -57,13 +57,37 @@ namespace Spring.Web.Services ///

/// /// Aleksandar Seovic - public class WebServiceExporter : IInitializingObject, IObjectFactoryAware, IFactoryObject, IObjectNameAware + public class WebServiceExporter : IInitializingObject, IObjectFactoryAware, IFactoryObject, IObjectNameAware, IDisposable { + /// + /// Holds EXPORTER_ID to WebServiceExporter instance mappings. + /// + private static readonly IDictionary s_activeExporters = new Hashtable(); + + /// + /// Returns the target object instance exported by the WebServiceExporter identified by . + /// + /// + /// + public static object GetTarget( string exporterId ) + { + WebServiceExporter exporterInstance; + lock (s_activeExporters.SyncRoot) + { + exporterInstance = (WebServiceExporter)s_activeExporters[exporterId]; + } + AssertUtils.ArgumentNotNull( exporterInstance, "exporterId", "Remoting Server object is not associated with any active SaoExporter" ); + object target = exporterInstance.GetTargetInstance(); + AssertUtils.ArgumentNotNull( target, "exporterId", string.Format( "Failed retrieving target object for SaoExporter ID {0}", exporterId ) ); + return target; + } + #region Fields #if NET_2_0 private WsiProfiles _wsiProfile = WsiProfiles.BasicProfile1_1; #endif + private readonly string EXPORTER_ID = Guid.NewGuid().ToString(); private Type _webServiceBaseType = typeof(WebService); private string _targetName; private string _description; @@ -93,11 +117,52 @@ namespace Spring.Web.Services #region Constructor(s) / Destructor /// - /// Creates a new instance of the - /// class. + /// Creates a new instance of the class. /// public WebServiceExporter() - {} + { + lock (s_activeExporters.SyncRoot) + { + s_activeExporters[EXPORTER_ID] = this; + } + } + + /// + /// Cleanup before GC + /// + ~WebServiceExporter() + { + Dispose( false ); + } + + #region IDisposable Members + + /// + /// Disconnect the remote object from the registered remoting channels. + /// + public void Dispose() + { + GC.SuppressFinalize( this ); + Dispose( true ); + } + + /// + /// Stops exporting the object identified by . + /// + /// true to release both managed and unmanaged resources; false to release only unmanaged resources. + protected virtual void Dispose( bool disposing ) + { + if (disposing) + { + lock (s_activeExporters.SyncRoot) + { + s_activeExporters.Remove( this.EXPORTER_ID ); + } + objectFactory = null; + } + } + + #endregion #endregion @@ -261,6 +326,11 @@ namespace Spring.Web.Services #region IFactoryObject Members + private object GetTargetInstance() + { + return objectFactory.GetObject( TargetName ); + } + /// /// Return an instance (possibly shared or independent) of the object /// managed by this factory. @@ -365,9 +435,9 @@ namespace Spring.Web.Services protected virtual void GenerateProxy() { #if NET_2_0 - IProxyTypeBuilder builder = new WebServiceProxyTypeBuilder(TargetName, Description, Name, Namespace, WsiProfile); + IProxyTypeBuilder builder = new WebServiceProxyTypeBuilder(this, Description, Name, Namespace, WsiProfile); #else - IProxyTypeBuilder builder = new WebServiceProxyTypeBuilder(TargetName, Description, Name, Namespace); + IProxyTypeBuilder builder = new WebServiceProxyTypeBuilder(this, Description, Name, Namespace); #endif builder.Name = WebUtils.GetPageName(objectName); builder.BaseType = WebServiceBaseType; @@ -390,13 +460,8 @@ namespace Spring.Web.Services { #region Fields - private static readonly MethodInfo GetObject = - typeof(IObjectFactory).GetMethod("GetObject", new Type[] {typeof(string)}); - - private static readonly MethodInfo GetApplicationContext = - typeof(WebApplicationContext).GetProperty("Current", BindingFlags.Public | BindingFlags.Static, null, typeof(IApplicationContext), Type.EmptyTypes, null).GetGetMethod(); - - private string targetName; + private static readonly MethodInfo WebServiceExporter_GetTargetInstance = typeof( WebServiceExporter ).GetMethod( "GetTarget", new Type[] { typeof( string ) } ); + private WebServiceExporter exporter; private CustomAttributeBuilder webServiceAttribute; #if NET_2_0 private CustomAttributeBuilder webServiceBindingAttribute; @@ -406,19 +471,17 @@ namespace Spring.Web.Services #region Constructor(s) / Destructor - public WebServiceProxyTypeBuilder( - string targetName, string description, string name, string ns) + public WebServiceProxyTypeBuilder(WebServiceExporter exporter, string description, string name, string ns) { - this.targetName = targetName; + this.exporter = exporter; // Creates a WebServiceAttribute from configuration info this.webServiceAttribute = CreateWebServiceAttribute(description, name, ns); } #if NET_2_0 - public WebServiceProxyTypeBuilder( - string targetName, string description, string name, string ns, WsiProfiles wsiProfile) + public WebServiceProxyTypeBuilder(WebServiceExporter exporter, string description, string name, string ns, WsiProfiles wsiProfile) { - this.targetName = targetName; + this.exporter = exporter; // Creates a WebServiceAttribute from configuration info this.webServiceAttribute = CreateWebServiceAttribute(description, name, ns); @@ -466,9 +529,7 @@ namespace Spring.Web.Services /// Implements constructors for the proxy class. /// /// - /// This implementation generates a constructor - /// that gets instance of the target object using - /// . + /// This implementation generates an empty noop default constructor /// /// /// The builder to use. @@ -483,17 +544,25 @@ namespace Spring.Web.Services attributes, CallingConventions.Standard, Type.EmptyTypes); ILGenerator il = cb.GetILGenerator(); - - il.Emit(OpCodes.Ldarg_0); - il.EmitCall(OpCodes.Call, GetApplicationContext, null); - il.Emit(OpCodes.Ldstr, targetName); - il.EmitCall(OpCodes.Callvirt, GetObject, null); - il.Emit(OpCodes.Stfld, targetInstance); - - il.Emit(OpCodes.Ret); } + /// + /// Generates the IL instructions that pushes + /// the target instance on which calls should be delegated to. + /// + /// + /// This will cause the builder to generate + /// WebServiceExporter.GetTarget( EXPORTER_ID ).<targetmethod>(..) + /// for each exported method. + /// + /// The IL generator to use. + public override void PushTarget( ILGenerator il ) + { + il.Emit( OpCodes.Ldstr, this.exporter.EXPORTER_ID ); + il.Emit( OpCodes.Call, WebServiceExporter_GetTargetInstance ); + } + protected override IList GetTypeAttributes(Type type) { IList attrs = base.GetTypeAttributes(type); diff --git a/src/Spring/Spring.Web/Web/Support/LocalResourceManager.cs b/src/Spring/Spring.Web/Web/Support/LocalResourceManager.cs index 01b05dd6..a3007b5e 100644 --- a/src/Spring/Spring.Web/Web/Support/LocalResourceManager.cs +++ b/src/Spring/Spring.Web/Web/Support/LocalResourceManager.cs @@ -33,7 +33,7 @@ namespace Spring.Web.Support { /// /// This ResourceManager implementation swallows s and - /// simply returns null from if no resource is found. + /// simply returns null from if no resource is found. /// /// Erich Eichinger internal class LocalResourceManager : ResourceManager @@ -81,7 +81,7 @@ namespace Spring.Web.Support return HttpContext.GetLocalResourceObject(_virtualPath, name, culture); //return base.GetObject( name, culture ); } - catch (MissingManifestResourceException ex) + catch (MissingManifestResourceException) { _isMissingManifest = true; } diff --git a/src/Spring/Spring.Web/Web/UI/Page.cs b/src/Spring/Spring.Web/Web/UI/Page.cs index 083eac96..e3b1e4bb 100644 --- a/src/Spring/Spring.Web/Web/UI/Page.cs +++ b/src/Spring/Spring.Web/Web/UI/Page.cs @@ -1601,10 +1601,9 @@ namespace Spring.Web.UI // { // return new LocalResourceManager( VirtualPathUtility.GetFileName( this.AppRelativeVirtualPath ), localResourceAssembly ); // } +// return null; return new LocalResourceManager( this.AppRelativeVirtualPath ); - // TODO: investigate HttpContext.GetLocalResourceObject() - return null; #endif }