/*
Kooboo is a content management system based on ASP.NET MVC framework. Copyright 2009 Yardi Technology Limited.
This program is free software: you can redistribute it and/or modify it under the terms of the
GNU General Public License version 3 as published by the Free Software Foundation.
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License along with this program.
If not, see http://www.kooboo.com/gpl3/.
*/
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using System.Web.Mvc.Ajax;
using System.Globalization;
using System.IO;
using System.Text;
using System.Threading;
using System.Collections.Specialized;
using System.IO.Compression;
using Everest.Library;
using Everest.Library.ExtensionMethod;
using Everest.CmsServices;
using Everest.CmsServices.Services;
using Everest.Library.Providers.Caching;
using Everest.CmsServices.MvcHelper;
using Everest.CmsServices.Extension.Module;
using Yahoo.Yui.Compressor;
using InteSoft.Web.ExternalResourceLoader;
using Everest.Library.Web;
namespace Everest.CmsServices.Controllers{
public class ScriptController : Controller
{
/// <summary>
/// Gets the localization resource.
/// </summary>
/// <returns></returns>
public ActionResult GetLocalizationResource(string dir)
{
dir = dir ?? "Kooboojs/";
string jsFile = CmsGlobal.ToAbsolutePath(dir + "Resources.js");
string localizationFile = CmsGlobal.ToAbsolutePath(string.Format(dir + "Resources.{0}.js",
CultureInfo.CurrentUICulture.Name));
if (System.IO.File.Exists(localizationFile))
{
jsFile = localizationFile;
}
List<string> jsFiles = new List<string>();
jsFiles.Add(jsFile);
string extjsLocalizationFie = CmsGlobal.ToAbsolutePath(string.Format(dir + "ext/3.0/locale/ext-lang-{0}.js"
, CultureInfo.CurrentUICulture.Name.Replace('-', '_')));
if (System.IO.File.Exists(extjsLocalizationFie))
{
jsFiles.Add(extjsLocalizationFie);
}
return JavaScript(CompressJavascript(jsFiles));
}
public ActionResult StartPage()
{
var startPageService = UnityManager.Resolve<StartPageService>();
return Content(startPageService.GetCachedStartPage(Thread.CurrentThread.CurrentUICulture.Name));
}
public ActionResult LastestStartPage()
{
var startPageService = UnityManager.Resolve<StartPageService>();
return Content(startPageService.GetLastestStartPage(Thread.CurrentThread.CurrentUICulture.Name));
}
private string CompressJavascript(IEnumerable<string> jsFiles)
{
StringBuilder cacheKey = new StringBuilder("CompresseJavascript_Files:");
foreach (var file in jsFiles)
{
cacheKey.AppendFormat("{0};", file);
}
if (CacheManager.Get(cacheKey.ToString()) == null)
{
List<ICacheItemExpiration> dependencies = new List<ICacheItemExpiration>();
StringBuilder stringBuilder = new StringBuilder();
foreach (var file in jsFiles)
{
using (FileStream fileStream = new FileStream(file, FileMode.Open, FileAccess.Read, FileShare.Read))
{
dependencies.Add(new FileDependency(file));
var content = fileStream.ReadString();
if (!string.IsNullOrEmpty(content))
{
stringBuilder.AppendFormat("{0}\n", JavaScriptCompressor.Compress(content, false, true, false, false, -1, System.Text.Encoding.UTF8, CultureInfo.CreateSpecificCulture("en-GB")));
}
}
}
CacheManager.Add(cacheKey.ToString(), stringBuilder.ToString(), CacheItemPriority.Normal, null, dependencies.ToArray());
}
return (string)CacheManager.Get(cacheKey.ToString());
}
private string CompressCss(IEnumerable<string> cssFiles)
{
StringBuilder cacheKey = new StringBuilder("CompressCss_Files:");
foreach (var file in cssFiles)
{
cacheKey.AppendFormat("{0};", file);
}
if (CacheManager.Get(cacheKey.ToString()) == null)
{
List<ICacheItemExpiration> dependencies = new List<ICacheItemExpiration>();
StringBuilder stringBuilder = new StringBuilder();
foreach (var file in cssFiles)
{
using (FileStream fileStream = new FileStream(file, FileMode.Open, FileAccess.Read, FileShare.Read))
{
dependencies.Add(new FileDependency(file));
var content = fileStream.ReadString();
stringBuilder.AppendFormat("{0}\n", CSSMinify.Minify(Url, UrlConvertor.AbsolutePathToRelativeUrl(file), Request.Url.AbsolutePath, content));
}
}
CacheManager.Add(cacheKey.ToString(), stringBuilder.ToString(), CacheItemPriority.Normal, null, dependencies.ToArray());
}
return (string)CacheManager.Get(cacheKey.ToString());
}
/// <summary>
/// Outputs the specified content.
/// </summary>
/// <param name="content">The content.</param>
/// <param name="contentType">Type of the content.</param>
/// <param name="cacheDuration">Duration of the cache.</param>
private void Output(string content, string contentType, int cacheDuration, params string[] varyByParams)
{
HttpResponseBase response = Response;
response.ContentType = contentType;
Stream output = response.OutputStream;
// Compress
string acceptEncoding = Request.Headers["Accept-Encoding"];
if (!string.IsNullOrEmpty(acceptEncoding))
{
acceptEncoding = acceptEncoding.ToLowerInvariant();
if (acceptEncoding.Contains("gzip"))
{
response.AddHeader("Content-encoding", "gzip");
output = new GZipStream(output, CompressionMode.Compress);
}
else if (acceptEncoding.Contains("deflate"))
{
response.AddHeader("Content-encoding", "deflate");
output = new DeflateStream(output, CompressionMode.Compress);
}
}
// Write output
using (StreamWriter sw = new StreamWriter(output))
{
sw.WriteLine(content);
}
// Cache
if (cacheDuration > 0)
{
DateTime timestamp = HttpContext.Timestamp;
HttpCachePolicyBase cache = response.Cache;
int duration = cacheDuration;
cache.SetCacheability(HttpCacheability.Public);
//add SetNoServerCaching by hjf.
cache.SetNoServerCaching();
cache.SetExpires(timestamp.AddSeconds(duration));
cache.SetMaxAge(new TimeSpan(0, 0, duration));
cache.SetValidUntilExpires(true);
cache.SetLastModified(timestamp);
cache.VaryByHeaders["Accept-Encoding"] = true;
foreach (var p in varyByParams)
{
cache.VaryByParams[p] = true;
}
cache.SetOmitVaryStar(true);
}
}
#region Theme & Javascript
/// <summary>
/// Gets the theme.
/// </summary>
/// <param name="theme">The theme.</param>
/// <returns></returns>
public void GetTheme(string theme)
{
var cssFiles = new List<string>();
string themePath = TemplateFileManager.GetThemePath(theme);
var themeRulesInterpretor = new ThemeRulesInterpretor(themePath, Url);
var stylesheets = TemplateFileManager.GetThemeStylesheets(theme);
if (stylesheets != null)
{
foreach (var path in stylesheets)
{
if (!themeRulesInterpretor.Files.Contains(path, StringComparer.InvariantCultureIgnoreCase))
{
cssFiles.Add(path);
}
}
}
Output(CompressCss(cssFiles), "text/css", 2592000, "theme");
}
/// <summary>
/// Gets the javascript.
/// </summary>
/// <param name="application">The application.</param>
/// <returns></returns>
public void GetJavascript(string application)
{
List<string> jsFiles = new List<string>();
var javascripts = TemplateFileManager.GetJavascriptFiles(application);
if (javascripts != null)
{
foreach (var path in javascripts)
{
jsFiles.Add(path);
}
}
Output(CompressJavascript(jsFiles), "text/javascript", 2592000, "theme");
}
/// <summary>
/// Gets the module theme.
/// </summary>
/// <param name="runtimeApplication">The runtime application.</param>
/// <param name="moduleName">Name of the module.</param>
public void GetModuleTheme(string application, string moduleName, string theme)
{
var moduleInfo = ModuleInfo.GetModule(moduleName, application, true);
var cssFiles = new List<string>();
var themePath = moduleInfo.GetThemePath(theme);
var themeRulesInterpretor = new ThemeRulesInterpretor(themePath, Url);
var stylesheets = moduleInfo.GetThemeStylesheets(theme);
if (stylesheets != null)
{
foreach (var path in stylesheets)
{
if (!themeRulesInterpretor.Files.Contains(path, StringComparer.InvariantCultureIgnoreCase))
{
cssFiles.Add(path);
}
}
}
Output(CompressCss(cssFiles), "text/css", 2592000, "runtimeApplication", "moduleName");
}
/// <summary>
/// Gets the module javascript.
/// </summary>
/// <param name="application">The application.</param>
/// <param name="theme">The theme.(The theme value is moduleName here.)</param>
public void GetModuleJavascript(string application, string theme)
{
var moduleInfo = ModuleInfo.GetModule(theme, application, true);
var jsFiles = new List<string>();
var javascripts = moduleInfo.GetJavascriptFiles();
if (javascripts != null)
{
foreach (var path in javascripts)
{
jsFiles.Add(path);
}
}
Output(CompressJavascript(jsFiles), "text/javascript", 2592000, "runtimeApplication", "moduleName");
}
#endregion
}
}
|