1 // Copyright 2004-2008 Castle Project - http://www.castleproject.org/
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
7 // http://www.apache.org/licenses/LICENSE-2.0
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
15 namespace Castle
.MonoRail
.Framework
.Routing
20 using System
.Web
.Configuration
;
21 using Castle
.MonoRail
.Framework
.Adapters
;
26 public class RoutingModuleEx
: IHttpModule
28 private static readonly RoutingEngine engine
= new RoutingEngine();
29 private string defaultUrlExtension
= ".castle";
32 /// Inits the specified app.
34 /// <param name="app">The app.</param>
35 public void Init(HttpApplication app
)
37 app
.BeginRequest
+= OnBeginRequest
;
41 HttpHandlersSection httpHandlersConfig
=
42 (HttpHandlersSection
) WebConfigurationManager
.GetSection("system.web/httpHandlers");
44 foreach(HttpHandlerAction handlerAction
in httpHandlersConfig
.Handlers
)
46 if (Type
.GetType(handlerAction
.Type
) == typeof (MonoRailHttpHandlerFactory
))
48 if (handlerAction
.Path
.StartsWith("*."))
50 defaultUrlExtension
= handlerAction
.Path
.Substring(1);
58 //just swallow and keep on using .castle as the default.
64 /// Disposes of the resources (other than memory)
65 /// used by the module that implements <see cref="T:System.Web.IHttpModule"/>.
72 /// Called when [begin request].
74 /// <param name="sender">The sender.</param>
75 /// <param name="e">The <see cref="System.EventArgs"/> instance containing the event data.</param>
76 public void OnBeginRequest(object sender
, EventArgs e
)
78 HttpContext context
= HttpContext
.Current
;
79 HttpRequest request
= context
.Request
;
81 if (File
.Exists(request
.PhysicalPath
))
83 return; // Possibly requesting a static file, so we skip routing altogether
87 engine
.FindMatch(StripAppPathFrom(request
.FilePath
, request
.ApplicationPath
) + request
.PathInfo
,
88 new RouteContext(new RequestAdapter(request
), request
.ApplicationPath
, context
.Items
));
95 string mrPath
= CreateMonoRailPath(match
);
96 string url
= request
.RawUrl
;
98 string paramsAsQueryString
= "";
100 int queryStringIndex
= url
.IndexOf('?');
102 if (queryStringIndex
!= -1)
104 paramsAsQueryString
= url
.Substring(queryStringIndex
+ 1);
107 if (paramsAsQueryString
.Length
!= 0)
109 context
.RewritePath(mrPath
, request
.PathInfo
, paramsAsQueryString
);
113 context
.RewritePath(mrPath
);
116 context
.Items
.Add(RouteMatch
.RouteMatchKey
, match
);
119 private string StripAppPathFrom(string path
, string applicationPath
)
121 if (applicationPath
.Length
!= 1)
123 return path
.Substring(applicationPath
.Length
);
128 private string CreateMonoRailPath(RouteMatch match
)
130 if (!match
.Parameters
.ContainsKey("controller"))
132 throw new MonoRailException(
133 "Parameter 'controller' is not optional. Check your routing rules to make " +
134 "sure this parameter is being added to the RouteMatch");
136 if (!match
.Parameters
.ContainsKey("action"))
138 throw new MonoRailException(
139 "Parameter 'action' is not optional. Check your routing rules to make " +
140 "sure this parameter is being added to the RouteMatch");
143 string controller
= match
.Parameters
["controller"];
144 string area
= match
.Parameters
.ContainsKey("area") ? match
.Parameters
["area"] : null;
145 string action
= match
.Parameters
["action"];
149 return "~/" + area
+ "/" + controller
+ "/" + action
+ defaultUrlExtension
;
153 return "~/" + controller
+ "/" + action
+ defaultUrlExtension
;
160 /// <value>The engine.</value>
161 public static RoutingEngine Engine
163 get { return engine; }