New test.
[mono.git] / mcs / class / System.Web / System.Web.Configuration_2.0 / WebConfigurationManager.cs
index 67b3db6889f9a2d8497d352dc9273d1b6d3a4189..fd87f12d0854ce5c5c70fb91d6e32237c9e1e52b 100644 (file)
@@ -43,8 +43,56 @@ namespace System.Web.Configuration {
 
        public static class WebConfigurationManager
        {
+#if !TARGET_J2EE
                static IInternalConfigConfigurationFactory configFactory;
                static Hashtable configurations = new Hashtable ();
+#else
+        static internal IInternalConfigConfigurationFactory configFactory
+        {
+            get{
+                IInternalConfigConfigurationFactory factory = (IInternalConfigConfigurationFactory)AppDomain.CurrentDomain.GetData("WebConfigurationManager.configFactory");
+                if (factory == null){
+                    lock (AppDomain.CurrentDomain){
+                        object initialized = AppDomain.CurrentDomain.GetData("WebConfigurationManager.configFactory.initialized");
+                        if (initialized == null){
+                            PropertyInfo prop = typeof(ConfigurationManager).GetProperty("ConfigurationFactory", BindingFlags.Static | BindingFlags.NonPublic);
+                            if (prop != null){
+                                factory = prop.GetValue(null, null) as IInternalConfigConfigurationFactory;
+                                configFactory = factory;
+                            }
+                        }
+                    }
+                }
+                return factory != null ? factory : configFactory;
+            }
+            set{
+                AppDomain.CurrentDomain.SetData("WebConfigurationManager.configFactory", value);
+                AppDomain.CurrentDomain.SetData("WebConfigurationManager.configFactory.initialized", true);
+            }
+        }
+
+        static internal Hashtable configurations
+        {
+            get{
+                Hashtable table = (Hashtable)AppDomain.CurrentDomain.GetData("WebConfigurationManager.configurations");
+                if (table == null){
+                    lock (AppDomain.CurrentDomain){
+                        object initialized = AppDomain.CurrentDomain.GetData("WebConfigurationManager.configurations.initialized");
+                        if (initialized == null){
+                            table = new Hashtable();
+                            configurations = table;
+                        }
+                    }
+                }
+                return table != null ? table : configurations;
+
+            }
+            set{
+                AppDomain.CurrentDomain.SetData("WebConfigurationManager.configurations", value);
+                AppDomain.CurrentDomain.SetData("WebConfigurationManager.configurations.initialized", true);
+            }
+        }
+#endif
                
                static WebConfigurationManager ()
                {
@@ -129,11 +177,12 @@ namespace System.Web.Configuration {
 
                        string basePath = GetBasePath (path);
                        _Configuration conf;
+
                        
                        lock (configurations) {
                                conf = (_Configuration) configurations [basePath];
                                if (conf == null) {
-                                       conf = ConfigurationFactory.Create (typeof(WebConfigurationHost), null, path, site, locationSubPath, server, userName, password);
+                                       conf = ConfigurationFactory.Create (typeof(WebConfigurationHost), null, basePath, site, locationSubPath, server, userName, password);
                                        configurations [basePath] = conf;
                                }
                        }
@@ -188,16 +237,31 @@ namespace System.Web.Configuration {
                        return OpenMappedMachineConfiguration (fileMap);
                }
 
-               [MonoTODO ("apparently this bad boy can return null, but GetWebApplicationSection doesn't")]
                public static object GetSection (string sectionName)
                {
-                       return GetWebApplicationSection (sectionName);
+                       _Configuration c;
+                       if (HttpContext.Current != null
+                           && HttpContext.Current.Request != null)
+                               c = OpenWebConfiguration (HttpContext.Current.Request.Path);
+                       else
+                               c = OpenWebConfiguration (HttpRuntime.AppDomainAppVirtualPath);
+
+                       if (c == null)
+                               return null;
+                       else
+                               return c.GetSection (sectionName);
                }
 
                [MonoTODO]
                public static object GetSection (string sectionName, string path)
                {
-                       throw new NotImplementedException ();
+                       try {
+                               _Configuration c = OpenWebConfiguration (path);
+                               return c.GetSection (sectionName);
+                       }
+                       catch {
+                               return null;
+                       }
                }
 
                static _Configuration GetWebApplicationConfiguration ()
@@ -206,25 +270,31 @@ namespace System.Web.Configuration {
 
                        if (HttpContext.Current == null
                            || HttpContext.Current.Request == null
-                           || HttpContext.Current.Request.PhysicalApplicationPath == null
-                           || HttpContext.Current.Request.PhysicalApplicationPath == "") {
+                           || HttpContext.Current.Request.ApplicationPath == null
+                           || HttpContext.Current.Request.ApplicationPath == "") {
                                config = OpenWebConfiguration ("");
                        }
                        else {
-                               config = OpenWebConfiguration (HttpContext.Current.Request.PhysicalApplicationPath);
+                               config = OpenWebConfiguration (HttpContext.Current.Request.ApplicationPath);
                        }
 
                        return config;
                }
 
+               static MethodInfo get_runtime_object = typeof (ConfigurationSection).GetMethod ("GetRuntimeObject", BindingFlags.NonPublic | BindingFlags.Instance);
+
                [MonoTODO]
                public static object GetWebApplicationSection (string sectionName)
                {
                        _Configuration config = GetWebApplicationConfiguration ();
+                       if (config == null)
+                               return null;
 
                        ConfigurationSection section = config.GetSection (sectionName);
-
-                       return section;
+                       if (section == null)
+                               return null;
+                       
+                       return get_runtime_object.Invoke (section, new object [0]);
                }
 
                public static NameValueCollection AppSettings {
@@ -243,23 +313,34 @@ namespace System.Web.Configuration {
                {
                        if (path == "/" || path == "")
                                return path;
-                       
-                       string pd = HttpContext.Current.Request.MapPath (path);
 
-                       if (!Directory.Exists (pd)) {
-                               int i = path.LastIndexOf ('/');
-                               path = path.Substring (0, i);
-                       } 
+                       /* first if we can, map it to a physical path
+                        * to see if it corresponds to a file */
+                       if (HttpContext.Current != null
+                           && HttpContext.Current.Request != null) {
+                               string pd = HttpContext.Current.Request.MapPath (path);
+
+                               if (!Directory.Exists (pd)) {
+                                       /* if it does, remove the file from the url */
+                                       int i = path.LastIndexOf ('/');
+                                       path = path.Substring (0, i);
+                               } 
+                       }
                        
+                       if (path.Length == 0)
+                               return path;
+
+                       /* remove excess /'s from the end of the virtual path */
                        while (path [path.Length - 1] == '/')
                                path = path.Substring (0, path.Length - 1);
+
                        return path;
                }
 
 
 #region stuff copied from WebConfigurationSettings
 #if TARGET_J2EE
-               static private IConfigurationSystem oldConfig {
+               static internal IConfigurationSystem oldConfig {
                        get {
                                return (IConfigurationSystem)AppDomain.CurrentDomain.GetData("WebConfigurationManager.oldConfig");
                        }
@@ -270,20 +351,30 @@ namespace System.Web.Configuration {
 
                static private Web20DefaultConfig config {
                        get {
-                               return (Web20DefaultConfig)AppDomain.CurrentDomain.GetData("WebConfigurationManager.config");
+                               return (Web20DefaultConfig) AppDomain.CurrentDomain.GetData ("Web20DefaultConfig.config");
+                       }
+                       set {
+                               AppDomain.CurrentDomain.SetData ("Web20DefaultConfig.config", value);
+                       }
+               }
+
+               static private IInternalConfigSystem configSystem {
+                       get {
+                               return (IInternalConfigSystem) AppDomain.CurrentDomain.GetData ("IInternalConfigSystem.configSystem");
                        }
                        set {
-                               AppDomain.CurrentDomain.SetData("WebConfigurationManager.config", value);
+                               AppDomain.CurrentDomain.SetData ("IInternalConfigSystem.configSystem", value);
                        }
                }
 #else
+               static internal IConfigurationSystem oldConfig;
                static Web20DefaultConfig config;
                static IInternalConfigSystem configSystem;
 #endif
                const BindingFlags privStatic = BindingFlags.NonPublic | BindingFlags.Static;
                static readonly object lockobj = new object ();
 
-               public static void Init ()
+               internal static void Init ()
                {
                        lock (lockobj) {
                                if (config != null)
@@ -300,7 +391,7 @@ namespace System.Web.Configuration {
                                                throw new ConfigurationException ("Cannot find method CCS");
 
                                        object [] args = new object [] {settings};
-                                       changeConfig.Invoke (null, args);
+                                       oldConfig = (IConfigurationSystem)changeConfig.Invoke (null, args);
                                        config = settings;
 
                                        config.Init ();
@@ -356,7 +447,23 @@ namespace System.Web.Configuration {
 
                public object GetConfig (string sectionName)
                {
-                       return WebConfigurationManager.GetWebApplicationSection (sectionName);
+                       object o = WebConfigurationManager.GetWebApplicationSection (sectionName);
+
+                       if (o == null || o is IgnoreSection) {
+                               /* this can happen when the section
+                                * handler doesn't subclass from
+                                * ConfigurationSection.  let's be
+                                * nice and try to load it using the
+                                * 1.x style routines in case there's
+                                * a 1.x section handler registered
+                                * for it.
+                                */
+                               object o1 = WebConfigurationManager.oldConfig.GetConfig (sectionName);
+                               if (o1 != null)
+                                       return o1;
+                       }
+
+                       return o;
                }
 
                public void Init ()