protected void Application_BeginRequest(object sender, EventArgs e) { if (BeginRequest != null && !IsStaticResource(sender)) { logger.DebugFormat("BeginRequest ({0})", sender.GetHashCode()); BeginRequest(sender, e); } }
/// <summary>Adds an adapter to the list of adapters. This is typically auto-wired using the [Adapts] attribute.</summary> /// <param name="adapterToAdd">The adapter instnace to add.</param> public void RegisterAdapter(params AbstractContentAdapter[] adapterToAdd) { lock (this) { logger.DebugFormat("Registering {0} adapters", adapterToAdd); List <AbstractContentAdapter> references = new List <AbstractContentAdapter>(adapters); references.AddRange(adapterToAdd); references.Sort(); adapters = references.ToArray(); } }
/// <summary>Analyzes views in the controllers's view folder looking for dynamic template registrations.</summary> /// <typeparam name="T">The type of controller to analyze.</typeparam> /// <param name="engine">The engine from which to resolve the <see cref="ViewTemplateRegistrator"/>.</param> /// <param name="viewFileExtension">The type of view file to analyze. By the default .cshtml files are analyzed.</param> /// <returns>The singleton <see cref="ViewTemplateRegistrator"/> instance.</returns> public ViewTemplateRegistrator Add <T>(string viewFileExtension) where T : IController { var controllerType = typeof(T); string controllerName = controllerType.Name.Substring(0, controllerType.Name.Length - "Controller".Length); Type modelType = typeof(ContentItem); Type contentControllerType = Utility.GetBaseTypes(controllerType).FirstOrDefault(t => t.IsGenericType && t.GetGenericTypeDefinition() == typeof(ContentController <>)); if (contentControllerType != null) { modelType = contentControllerType.GetGenericArguments().First(); } var source = new ViewTemplateSource { ControllerName = controllerName, ModelType = modelType, ViewFileExtension = viewFileExtension }; logger.DebugFormat("Enqueuing view template for controller {0} with model {1} looking for extension {2}", controllerName, modelType, viewFileExtension); QueuedRegistrations.Enqueue(source); if (RegistrationAdded != null) { RegistrationAdded.Invoke(this, new EventArgs()); } return(this); }
public override RouteData GetRouteData(HttpContextBase httpContext) { if (HttpContext.Current.Items["RouteData"] != null) { return(((Tuple <RouteData>)HttpContext.Current.Items["RouteData"]).Item1); } string path = httpContext.Request.AppRelativeCurrentExecutionFilePath; if (path.StartsWith(managementPath, StringComparison.InvariantCultureIgnoreCase)) { return(new RouteData(this, new StopRoutingHandler())); } if (path.EndsWith(".axd", StringComparison.InvariantCultureIgnoreCase)) { return(new RouteData(this, new StopRoutingHandler())); } if (path.EndsWith(".ashx", StringComparison.InvariantCultureIgnoreCase)) { return(new RouteData(this, new StopRoutingHandler())); } RouteData routeData = null; if (httpContext.Request.QueryString[ContentPartKey] != null) { // part in query string, this is an indicator of a request to a part, takes precendence over friendly urls routeData = CheckForContentController(httpContext); } if (routeData == null) { // this might be a friendly url routeData = GetRouteDataForPath(httpContext.Request); } if (routeData == null) { // fallback to route to controller/action routeData = CheckForContentController(httpContext); } logger.DebugFormat("GetRouteData for '{0}' got values: {1}", path, new RouteExtensions.QueryStringOutput(routeData)); HttpContext.Current.Items["RouteData"] = Tuple.Create(routeData); return(routeData); }
public virtual void MapTypes(List <Type> allTypes, NHibernate.Cfg.Configuration cfg, Func <string, string> formatter) { var m = new HbmMapping(); m.Items = allTypes.Select(t => { var sc = new HbmSubclass(); sc.name = GetName(t); sc.extends = GetName(t.BaseType); sc.discriminatorvalue = map.GetOrCreateDefinition(t).Discriminator ?? t.Name; sc.lazy = false; sc.lazySpecified = true; var propertyMappings = GetPersistables(t) .Select(p => p.Attribute.GetPropertyMapping(p.DeclaringProperty, formatter)) .ToList(); if (propertyMappings.Count > 0) { if (sc.Items == null) { sc.Items = propertyMappings.ToArray(); } else { sc.Items = sc.Items.Union(propertyMappings).ToArray(); } } logger.DebugFormat("Generating subclass {0} with discriminator {1} extending {2} with {3} items ({4} property mappings)", sc.name, sc.discriminatorvalue, sc.extends, sc.Items != null ? sc.Items.Length.ToString() : "(null)", propertyMappings.Count); return(sc); }).ToArray(); if (Debugger.IsAttached) { var dbg = m.AsString(); } cfg.AddDeserializedMapping(m, "N2"); }
public void ProcessRequest(HttpContext context) { if (File.Exists(context.Request.PhysicalPath)) { var fileModified = File.GetLastWriteTimeUtc(context.Request.PhysicalPath); if (CacheUtility.IsUnmodifiedSince(context.Request, fileModified)) { CacheUtility.NotModified(context.Response); } logger.DebugFormat("Transmitting virtual file {0} available on disk {1}", context.Request.AppRelativeCurrentExecutionFilePath, context.Request.PhysicalPath); N2.Web.CacheUtility.SetValidUntilExpires(context.Response, DateTime.UtcNow); context.Response.ContentType = GetContentType(context.Request.PhysicalPath); context.Response.TransmitFile(context.Request.PhysicalPath); } else if (vpp.FileExists(context.Request.AppRelativeCurrentExecutionFilePath)) { if (Modified.HasValue && CacheUtility.IsUnmodifiedSince(context.Request, Modified.Value)) { logger.DebugFormat("Not modified: {0}", context.Request.AppRelativeCurrentExecutionFilePath); CacheUtility.NotModified(context.Response); } byte[] cached = context.Cache["VirtualPathFileHandler:" + context.Request.AppRelativeCurrentExecutionFilePath] as byte[]; if (cached != null) { logger.DebugFormat("Transmitting cached file: {0}", context.Request.AppRelativeCurrentExecutionFilePath); context.Response.ContentType = GetContentType(context.Request.AppRelativeCurrentExecutionFilePath); context.Response.OutputStream.Write(cached, 0, cached.Length); return; } var f = vpp.GetFile(context.Request.AppRelativeCurrentExecutionFilePath); using (var s = f.Open()) { byte[] buffer = new byte[131072]; int readBytes = ReadBlock(s, buffer); if (readBytes <= 0) { logger.DebugFormat("Empty file: {0}", context.Request.AppRelativeCurrentExecutionFilePath); return; } N2.Web.CacheUtility.SetValidUntilExpires(context.Response, DateTime.UtcNow); context.Response.ContentType = GetContentType(context.Request.AppRelativeCurrentExecutionFilePath); logger.DebugFormat("Writing file: {0}", context.Request.AppRelativeCurrentExecutionFilePath); context.Response.OutputStream.Write(buffer, 0, readBytes); if (readBytes < buffer.Length) { cached = new byte[readBytes]; Array.Copy(buffer, cached, readBytes); logger.DebugFormat("Adding to cache: {0}", context.Request.AppRelativeCurrentExecutionFilePath); context.Cache.Add("VirtualPathFileHandler:" + context.Request.AppRelativeCurrentExecutionFilePath, cached, vpp.GetCacheDependency(context.Request.AppRelativeCurrentExecutionFilePath, new[] { context.Request.AppRelativeCurrentExecutionFilePath }, DateTime.UtcNow), DateTime.MaxValue, TimeSpan.FromMinutes(1), System.Web.Caching.CacheItemPriority.BelowNormal, null); return; } logger.DebugFormat("Transmitting rest of file {0}", context.Request.AppRelativeCurrentExecutionFilePath); TransferBetweenStreams(buffer, s, context.Response.OutputStream); } } }
public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values) { // here we deal with people linking to non-n2 controllers but we have merged route values containing n2 stuff // scenarios: // controller: other -> not our business // controller: self -> link to same acton and page // acton: other -> link to action on same page // item: other -> link to other page // nuthin' -> link to same acton and page // x: y -> add parameter x // page: other -> not our business // item: other & action: other -> link to action other page // item: other & action: other & x:y-> link to action other page with param // app in virtual dir values = new RouteValueDictionary(values); logger.DebugFormat("GetVirtualPath for values: {0}", new RouteExtensions.QueryStringOutput(values)); var contextPath = requestContext.RouteData.CurrentPath(); var requestedItem = values.CurrentItem <ContentItem>(ContentItemKey, engine.Persister); var item = requestedItem; if (item == null) { // fallback to context item item = contextPath.CurrentItem; } else { // remove specified item from collection so it doesn't appear in the url values.Remove(ContentItemKey); } if (item == null) { // no item requested or in context .> not our bisiness return(null); } var contextController = (string)requestContext.RouteData.Values["controller"]; var requestedController = (string)values["controller"]; if (requestedItem == null && requestedController != null) { if (!string.Equals(requestedController, contextController, StringComparison.InvariantCultureIgnoreCase)) { // no item was specificlly requested, and the controller differs from context's -> we let some other route handle this return(null); } if (!controllerMapper.IsContentController(requestedController)) { // same controller not content controller -> let it be return(null); } } var itemController = controllerMapper.GetControllerName(item.GetContentType()); values["controller"] = itemController; if (item.IsPage) { return(ResolveContentActionUrl(requestContext, values, item)); } // try to find an appropriate page to use as path (part data goes into the query strings) var page = values.CurrentItem <ContentItem>(ContentPageKey, engine.Persister) ?? contextPath.CurrentPage ?? item.ClosestPage(); if (page != null) { return(ResolvePartActionUrl(requestContext, values, page, item)); } // can't find a page, don't link return(null); }
public void Start() { var staticFileExtensions = new HashSet <string>(configFactory.Sections.Web.Vpp.Zips.StaticFileExtensions.OfType <string>()); foreach (var vppElement in configFactory.Sections.Web.Vpp.Zips.AllElements) { string filePath = vppElement.FilePath; string observedPath = vppElement.ObservedPath; string path = MapPath(filePath); if (!File.Exists(path)) { N2.Engine.Logger.Warn("Did not find configured (" + vppElement.Name + ") zip vpp on disk: " + path); continue; } DateTime lastModified = File.GetLastWriteTimeUtc(path); var vpp = new SharpZipLib.Web.VirtualPathProvider.ZipFileVirtualPathProvider(path); N2.Engine.Logger.Info("Registering VPP: " + vpp); Register(vpp); broker.PostResolveAnyRequestCache += (s, a) => { var application = s as HttpApplication; var context = application.Context; var requestPath = context.Request.AppRelativeCurrentExecutionFilePath; if (!requestPath.StartsWith(observedPath, StringComparison.InvariantCultureIgnoreCase)) { return; } if (!vpp.DirectoryExists(VirtualPathUtility.GetDirectory(requestPath))) { return; } string extension = VirtualPathUtility.GetExtension(requestPath).ToLower(); if (extension == "") { requestPath = requestPath.TrimEnd('/') + "/Default.aspx"; //context.RewritePath(requestPath.TrimEnd('/') + "/Default.aspx"); } // There's a problem with RouteTable.Routes keeping storing the default vpp before we register our vpp, in which case // RouteExistingFiles will not handle files in the zip vpp. This is a workaround. switch (extension) { case "": case ".aspx": case ".axd": case ".ashx": if (vpp.FileExists(requestPath)) { logger.DebugFormat("Remapping handler for path {0}", requestPath); var handler = System.Web.Compilation.BuildManager.CreateInstanceFromVirtualPath(requestPath, typeof(IHttpHandler)); context.RemapHandler(handler as IHttpHandler); } else { logger.DebugFormat("Not found virtual path path {0}", requestPath); } break; case ".config": break; default: if (staticFileExtensions.Contains(extension) && vpp.FileExists(requestPath)) { logger.DebugFormat("Remapping to virtual path file handler {0}", requestPath); context.RemapHandler(new VirtualPathFileHandler(vpp) { Modified = lastModified }); } break; } }; } }
/// <summary>Finds the path associated with an url.</summary> /// <param name="url">The url to the template to locate.</param> /// <param name="startNode">The node to start finding path from if none supplied will start from StartNode</param> /// <param name="remainingPath">The remaining path to search</param> /// <returns>A PathData object. If no template was found the object will have empty properties.</returns> public PathData FindPath(Url url, ContentItem startNode = null, string remainingPath = null) { if (url == null) { return(PathData.Empty); } url = url.GetNormalizedContentUrl(); var urlKey = GetUrlLowerInvariantString(url); // Within the same request, we don't need to clone again! if (HttpContext.Current.Items[urlKey] != null) { return(((Tuple <PathData>)HttpContext.Current.Items[urlKey]).Item1); } // Make sure the cached path data is initialized thread safely Dictionary <string, PathData> cachedPathData = GetCachedPathData(); PathData data; bool pathDataFound; lock (pathLock) { pathDataFound = cachedPathData.TryGetValue(urlKey, out data); } if (pathDataFound) { logger.DebugFormat("Retrieving path {0} from cache for key {1} ({2})", data, urlKey, data.GetHashCode()); data = data.Attach(persister); if (data == null || data.ID == 0) { // Cached path has to CMS content HttpContext.Current.Items[urlKey] = Tuple.Create(data); return(data); } if (!string.IsNullOrEmpty(url.Query)) { data.UpdateParameters(Url.Parse(url).GetQueries()); } } else { // The requested url doesn't exist in the cached path data lock (pathLock) { if (cachedPathData.TryGetValue(urlKey, out data)) { logger.DebugFormat("Retrieving path {0} from cache (second chance) for key {1} ({2})", data, urlKey, data.GetHashCode()); data = data.Attach(persister); if (data == null || data.ID == 0) { // Cached path has to CMS content HttpContext.Current.Items[urlKey] = Tuple.Create(data); return(data); } if (!string.IsNullOrEmpty(url.Query)) { data.UpdateParameters(Url.Parse(url).GetQueries()); } } else { remainingPath = remainingPath ?? Url.ToRelative(url.Path).TrimStart('~'); string path = remainingPath; PathData partialPath = GetStartNode(url, cachedPathData, ref path, 0); if (partialPath.ID == 0) { data = inner.FindPath(url); logger.DebugFormat("Found path {0} for url {1}", data, url); } else { string subpath = remainingPath.Substring(path.Length, remainingPath.Length - path.Length); data = inner.FindPath(url, persister.Get(partialPath.ID), subpath); logger.DebugFormat("Found path {0} for subpath {1} below {2}", data, subpath, partialPath.ID); } if (data.IsCacheable) { var detached = data.Detach(); logger.DebugFormat("Adding {0} to cache for key {1} ({2})", detached, urlKey, detached.GetHashCode()); cachedPathData.Add(urlKey, detached); } } } } HttpContext.Current.Items[urlKey] = Tuple.Create(data); return(data); }
/// <summary>Finds the path associated with an url.</summary> /// <param name="url">The url to the template to locate.</param> /// <param name="startNode">The node to start finding path from if none supplied will start from StartNode</param> /// <param name="remainingPath">The remaining path to search</param> /// <returns>A PathData object. If no template was found the object will have empty properties.</returns> public PathData FindPath(Url url, ContentItem startNode = null, string remainingPath = null) { if (url == null) { return(PathData.Empty); } url = url.GetNormalizedContentUrl(); var urlKey = GetUrlLowerInvariantString(url); // Make sure the cached path data is initialized thread safely Dictionary <string, PathData> cachedPathData; if ((cachedPathData = cache.Get <Dictionary <string, PathData> >("N2.PathDataCache")) == null) { lock (pathLock) { if ((cachedPathData = cache.Get <Dictionary <string, PathData> >("N2.PathDataCache")) == null) { cachedPathData = new Dictionary <string, PathData>(); cache.Add("N2.PathDataCache", cachedPathData, new CacheOptions { SlidingExpiration = SlidingExpiration }); } } } PathData data; bool pathDataFound; lock (pathLock) { pathDataFound = cachedPathData.TryGetValue(urlKey, out data); } if (pathDataFound) { logger.DebugFormat("Retrieving path {0} from cache for key {1} ({2})", data, urlKey, data.GetHashCode()); data = data.Attach(persister); if (data == null || data.ID == 0) { // Cached path has to CMS content return(data); } if (!string.IsNullOrEmpty(url.Query)) { data.UpdateParameters(Url.Parse(url).GetQueries()); } } else { // The requested url doesn't exist in the cached path data lock (pathLock) { if (cachedPathData.TryGetValue(urlKey, out data)) { logger.DebugFormat("Retrieving path {0} from cache (second chance) for key {1} ({2})", data, urlKey, data.GetHashCode()); data = data.Attach(persister); if (data == null || data.ID == 0) { // Cached path has to CMS content return(data); } if (!string.IsNullOrEmpty(url.Query)) { data.UpdateParameters(Url.Parse(url).GetQueries()); } } else { remainingPath = remainingPath ?? Url.ToRelative(url.Path).TrimStart('~'); string path = remainingPath; PathData partialPath = GetStartNode(url, cachedPathData, ref path, 0); if (partialPath.ID == 0) { data = inner.FindPath(url); logger.DebugFormat("Found path {0} for url {1}", data, url); } else { string subpath = remainingPath.Substring(path.Length, remainingPath.Length - path.Length); data = inner.FindPath(url, persister.Get(partialPath.ID), subpath); logger.DebugFormat("Found path {0} for subpath {1} below {2}", data, subpath, partialPath.ID); } if (data.IsCacheable) { var detached = data.Detach(); logger.DebugFormat("Adding {0} to cache for key {1} ({2})", detached, urlKey, detached.GetHashCode()); cachedPathData.Add(urlKey, detached); } } } } return(data); }