Skip to content
This repository has been archived by the owner on Jan 11, 2021. It is now read-only.

Upgrade to Packer1.3 #21

Open
wants to merge 12 commits into
base: master
Choose a base branch
from
Open
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
/nbproject/private/
/nbproject/
17 changes: 11 additions & 6 deletions README
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
SmartOptimizer v1.8
SmartOptimizer v1.8.1 alpha
------------------------
Author: Ali Farhadi (http://farhadi.ir/)
Author: Ben Charlton (https://github.com/Narimm)
@Depreciated Original Author: Ali Farhadi (http://farhadi.ir/)
Released under the terms of the GNU Public License.
See the GPL for details (http://www.gnu.org/licenses/gpl.html).

Expand Down Expand Up @@ -39,9 +40,11 @@ Installation Instructions
------------------------
1. Upload smartoptimizer folder to your website.
2. "smartoptimizer/cache" folder should be writable (in most cases 777 permission is needed).
3. Upload .htaccess file on the folder that smartoptimizer folder is placed, if there is no another htaccess file currently.
Otherwise, Copy content of SmartOptimizer htaccess file and paste it inside your current htaccess at the beginning of the file.
4. It's ready. Enjoy it.
3. Upload htaccess-smartoptimizer.txt file on the folder that smartoptimizer folder is placed, if there is no another .htaccess file currently rename it to .htaccess
Otherwise, Copy content of htaccess-smartoptimizer.txt and paste it inside your current htaccess at the beginning of the file.
4. Access your site as normal to check everything works
5 ../Smartoptimizer/config.php has settings you can tweak and change.



Bug reports
Expand All @@ -50,4 +53,6 @@ SmartOptimizer is in beta stage and needs a large scale testing specially for it
So any feedback is greatly appreciated.

Use the issue tracker at github for bug reports:
http://github.com/farhadi/SmartOptimizer/issues
https://github.com/Narimm/SmartOptimizer/issues
Please ensure your reports include the site you are working on and any errors reported -
this program is not intended for live production sites as it is only in Beta and needs more testing.
Binary file added distributions/SmartOptimizer.zip
Binary file not shown.
10 changes: 9 additions & 1 deletion .htaccess → htaccess-smartoptimizer.txt
Original file line number Diff line number Diff line change
@@ -1,7 +1,12 @@
## Copy the lower part of this file into your current .htaccess file or rename this file to
# .htaccess if you dont have have one yet.
#######
# Begin Smartoptimizer
#
<IfModule mod_expires.c>
<FilesMatch "\.(gif|jpg|jpeg|png|swf|css|js|html?|xml|txt|ico)$">
ExpiresActive On
ExpiresDefault "access plus 10 years"
ExpiresDefault "access plus 1 years"
</FilesMatch>
</IfModule>
<IfModule mod_rewrite.c>
Expand All @@ -24,3 +29,6 @@
<FilesMatch "\.(gif|jpg|jpeg|png|swf|css|js|html?|xml|txt|ico)$">
FileETag none
</FilesMatch>
#
# End SmartOptimizer additions
######
26 changes: 21 additions & 5 deletions smartoptimizer/config.php
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
<?php
/*
/**
* SmartOptimizer Configuration File
*/

**/

//base dir (a relative path to the base directory)
$settings['baseDir'] = '../';
Expand All @@ -28,7 +27,7 @@
//use this to set file concatenation On or Off
$settings['concatenate'] = true;

//separator for files to be concatenated
//separator for files to be concatenated. Tip: Don't use '.' if you use groups and name them like suggested.
$settings['separator'] = ',';

//specifies whether to emebed files included in css files using the data URI scheme or not
Expand Down Expand Up @@ -57,4 +56,21 @@

//Setting this to false will force the browser to use cached files without checking for changes.
$settings['clientCacheCheck'] = false;
?>

//Minifier to use when parsing js files. Add yours in /minifiers directory, and implement function minify_js($text_to_minify)
//We have 2 js minifiers - the original coded by farahdi(js) or Dean Edwards Packer(packer).
$settings['jsMinifier'] = 'packer';

//Minifier to use when parsing css files. Add yours in /minifiers directory, and implement function minify_css($text_to_minify)
$settings['cssMinifier'] = 'css';

//To use groups effectively, include your files with absolute paths. Define constants for easy access.
//define('MY_JS_DIR', $_SERVER['DOCUMENT_ROOT'] . '/tkitt/js/');
//define('MY_CSS_DIR', $_SERVER['DOCUMENT_ROOT'] . '/tkitt/css/');

//groups configuration. Call a group by using /path/to/smartoptimizer/?group.group_name.
//Tip: If you use 'test.js' as your group name, you'll get a nifty file name like 'group.test.js'
//$settings['groups'] = array(
// 'test.js' => array(MY_JS_DIR.'test.js', MY_JS_DIR.'test2.js'),
// 'test.css' => array(MY_JS_DIR.'style.css', MY_JS_DIR.'print.css')
//);
180 changes: 122 additions & 58 deletions smartoptimizer/index.php
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<?php
/* SmartOptimizer v1.8
/** SmartOptimizer v1.8
* SmartOptimizer enhances your website performance using techniques
* such as compression, concatenation, minifying, caching, and embedding on demand.
*
Expand All @@ -9,7 +9,13 @@
*
* Author: Ali Farhadi ([email protected])
* Website: http://farhadi.ir/
*/
*
*
*
* @todo SET A MINIMUM FILE SIZE WHICH WILL NOT BE GZIPPED OR MINIFIED.
* @todo EXCLUDE FILES WITH .min. in the filename - from minifying (they are already done)
*
**/

//Default settings
$settings = array(
Expand All @@ -31,6 +37,8 @@
'cachePrefix' => 'so_',
'clientCache' => true,
'clientCacheCheck' => false,
'jsMinifier' => 'js',
'cssMinifier' => 'css'
);

//mime types
Expand All @@ -48,13 +56,30 @@
"swf" => "application/x-shockwave-flash",
"ico" => "image/x-icon",
);
/**Processs a time in a string
*
* @param datetime $time
* @return string Date formatted
*/

function gmdatestr($time = null) {
if (is_null($time)){ $time = time();}
return gmdate("D, d M Y H:i:s", $time) . " GMT";
}
/**Adds a status header and then exits
*
* @param string $status
*/

function headerExit($status) {
header("HTTP/1.0 $status");
exit();
}

function headerNoCache() {
/**
* Adds Headers to a returning HTTP response that tells a server not to cache the file ever
**/
function headerNoCache()
{
// already expired
header("Expires: Mon, 26 Jul 1997 05:00:00 GMT");

Expand All @@ -72,86 +97,124 @@ function headerNoCache() {
//generate a unique Etag each time
header('Etag: '.microtime());
}
/**
* Adds header to the response informing that the file never expires cache it forever.
*/

function headerNeverExpire(){
header("Expires: " . gmdatestr(time() + 315360000));
header("Cache-Control: max-age=315360000");
function headerNeverExpire() {
$exptime = time() + 31557600;
$curtime = time();
header("Expires: " . gmdatestr($exptime));
header("Cache-Control: public, max-age=31557600");
header("Last-Modified: " . gmdatestr($curtime));
header("Vary: Accept-Encoding");
}

function debugExit($msg){
global $settings;
if (!$settings['debug']) {
headerExit('404 Not Found');
}
headerNoCache();
header('Content-Type: text/html; charset='.$settings['charSet']);
header("Content-Encoding: none");
echo "//<script>\n";
echo "alert('SmartOptimizer Error: ".str_replace("\n", "\\n", addslashes($msg))."');\n";
echo "//</script>\n";
exit();
/**
* Adds Headers to a file pls echo a Error that smartoptimizer couldnt process the file
* If Debug is set true this will 404 the file else it will return the file with a Script header.
*
* @global array $settings
* @param string $msg The message to ruturn if Debug is false
*/
function debugExit($msg) {
global $settings;
if (!$settings['debug']) {
headerExit('404 Not Found');
}
headerNoCache();
header('Content-Type: text/html; charset=' . $settings['charSet']);
header("Content-Encoding: none");
echo "//<script>\n";
echo "alert('SmartOptimizer Error: " . str_replace("\n", "\\n", addslashes($msg)) . "');\n";
echo "//</script>\n";
exit();
}

function gmdatestr($time = null) {
if (is_null($time)) $time = time();
return gmdate("D, d M Y H:i:s", $time) . " GMT";
}
/**Gets the input files modification time and compares it to the modification time of /smartoptimizer/index.php and config.php
* and returns the larges of the 3 (ie the most recent time)
*
* @global array $files
* @global string $fileType
* @staticvar datetime $filesmtime
* @return datetime
**/

function filesmtime() {
global $files, $fileType;
global $files, $fileMinifier;
static $filesmtime;
if ($filesmtime) return $filesmtime;
$filesmtime = max(@filemtime("minifiers/$fileType.php"), filemtime('index.php'), filemtime('config.php'));
if ($filesmtime){return $filesmtime;}
$filesmtime = max(filemtime("minifiers/$fileMinifier.php"), filemtime('index.php'), filemtime('config.php'));
foreach ($files as $file) {
if (!file_exists($file)) debugExit("File not found ($file).");
if (!file_exists($file)) {debugExit("File not found ($file).");}
$filesmtime = max(filemtime($file), $filesmtime);
}
return $filesmtime;
}

@include('config.php');
require 'config.php';

list($query) = explode('?', urldecode($_SERVER['QUERY_STRING']));

//if(isset($settings['groups']) && substr($query, 0, 6) == 'group.'){
// //we have a pre-defined group to include
// $group_name = str_replace('group.','',$query);
// if(isset($settings['groups'][$group_name])){
// $fileNames = $settings['groups'][$group_name];
// $fileDir = '';
// }
// else {debugExit("Group ($group_name) not set. Please edit config.");}
//} else {
if (preg_match('/^\/?(.+\/)?(.+)$/', $query, $matchResult)) {
$fileNames = $matchResult[2];
$fileDir = $settings['baseDir'].$matchResult[1];
} else debugExit("Invalid file name ($query)");

if (strpos(realpath($fileDir), realpath($settings['baseDir'])) !== 0) debugExit("File is out of base directory.");
$fileNames = $matchResult[2];
$fileDir = $settings['baseDir'] . $matchResult[1];
} else {
debugExit("Invalid file name ($query)");
}
//}
//check the file exists and is relative to the base directory.
if (strpos(realpath($fileDir), realpath($settings['baseDir'])) !== 0) {debugExit("File is out of base directory.");}

if ($settings['concatenate']) {
$files = explode($settings['separator'], $fileNames);
if(!is_array($fileNames)){
$files = explode($settings['separator'], $fileNames);
} else {
$files = $fileNames;
}
$settings['concatenate'] = count($files) > 1;
} else $files = array($fileNames);
} else {$files = array($fileNames);}

foreach ($files as $key => $file) {
if (preg_match('/^[^\x00]+\.([a-z0-9]+)$/i', $file, $matchResult)) {
$fileTypes[] = strtolower($matchResult[1]);
} else debugExit("Unsupported file ($file)");
} else {debugExit("Unsupported file ($file)");}

$files[$key] = $fileDir.$file;
}

if ($settings['concatenate']) {
if (count(array_unique($fileTypes)) > 1) debugExit("Files must be of the same type.");
if (count(array_unique($fileTypes)) > 1) {debugExit("Files must be of the same type.");}
}

//check we have a minifier
$fileType = $fileTypes[0];

if (!isset($mimeTypes[$fileType])) debugExit("Unsupported file type ($fileType)");
$fileMinifier = $settings[$fileType.'Minifier'];
if(!file_exists('minifiers/'.$fileMinifier.'.php')) {debugExit($fileType.'Minifier not found. Please create "minifiers/'.$fileMinifier.'.php" or change minifier in config.php');}
//check the file meets our filetypes list or
if (!isset($mimeTypes[$fileType])){ debugExit("Unsupported file type ($fileType)");}
header("Content-Type: {$mimeTypes[$fileType]}; charset=".$settings['charSet']);

// lets check and see if the client accepts compression and change our variable if it doesnt also check the filetype to ensure we want to compress.
$settings['gzip'] =
($settings['gzip'] &&
!in_array($fileType, $settings['gzipExceptions']) &&
in_array('gzip', array_map('trim', explode(',' , @$_SERVER['HTTP_ACCEPT_ENCODING']))) &&
in_array('gzip', array_map('trim', explode(',' , htmlspecialchars($_SERVER['HTTP_ACCEPT_ENCODING'], ENT_QUOTES)))) &&
function_exists('gzencode'));

if ($settings['gzip']) header("Content-Encoding: gzip");

$settings['minify'] = $settings['minify'] && file_exists('minifiers/'.$fileType.'.php');
$settings['embed'] = $settings['embed'] && $fileType == 'css' && (!preg_match('/msie/i', $_SERVER['HTTP_USER_AGENT']) || preg_match('/msie 8|opera/i', $_SERVER['HTTP_USER_AGENT']));
// ok client likes compression - lets tell it we are sending a compressed file.
if ($settings['gzip']){ header("Content-Encoding: gzip");}
//check we have a minifier
$settings['minify'] = $settings['minify'] && file_exists('minifiers/'.$fileMinifier.'.php');
//if its css and we have an opera browser embed the css
$settings['embed'] = $settings['embed'] && $fileType == 'css' && (!preg_match('/msie/i', htmlspecialchars($_SERVER['HTTP_USER_AGENT'])) || preg_match('/msie 8|opera/i', htmlspecialchars($_SERVER['HTTP_USER_AGENT'])));
//check if we want to call the cache.
$settings['serverCache'] = $settings['serverCache'] && ($settings['minify'] || $settings['gzip'] || $settings['concatenate'] || $settings['embed']);

if ($settings['serverCache']) {
Expand All @@ -162,9 +225,9 @@ function_exists('gzencode'));
($settings['serverCache'] && (!file_exists($cachedFile) || ($settings['serverCacheCheck'] && filesmtime() > filemtime($cachedFile)))));

if ($settings['clientCache'] && $settings['clientCacheCheck']) {
if ($settings['serverCache'] && !$generateContent) $mtime = filemtime($cachedFile);
elseif ($settings['serverCache']) $mtime = time();
else $mtime = filesmtime();
if ($settings['serverCache'] && !$generateContent) {$mtime = filemtime($cachedFile);}
elseif ($settings['serverCache']) {$mtime = time();}
else {$mtime = filesmtime();}
$mtimestr = gmdatestr($mtime);
}

Expand All @@ -174,15 +237,18 @@ function_exists('gzencode'));
header("Cache-Control: must-revalidate");
} elseif ($settings['clientCache']) {
headerNeverExpire();
} else headerNoCache();
} else { headerNoCache();}

if ($generateContent) {
if ($settings['minify']) include('minifiers/'.$fileType.'.php');
if ($settings['minify']){
include 'minifiers/'.$fileMinifier.'.php';

}
$content = array();
foreach ($files as $file) (($content[] = @file_get_contents($file)) !== false) || debugExit("File not found ($file).");
foreach ($files as $file){(($content[] = file_get_contents($file)) !== false) || debugExit("File not found ($file).");}
$content = implode("\n", $content);
if ($settings['minify']) $content = call_user_func('minify_' . $fileType, $content);
if ($settings['gzip']) $content = gzencode($content, $settings['compressionLevel']);
if ($settings['minify']) {$content = call_user_func('minify_' . $fileType, $content);}
if ($settings['gzip']){ $content = gzencode($content, $settings['compressionLevel']);}
if ($settings['serverCache']) {
$handle = @fopen($cachedFile, 'w') or debugExit("Could not create cache file($cachedFile).");
fwrite($handle, $content);
Expand All @@ -194,6 +260,4 @@ function_exists('gzencode'));
header('Content-Length: ' . filesize($cachedFile));
readfile($cachedFile);
}
} else headerExit('304 Not Modified');

?>
} else {headerExit('304 Not Modified');}
9 changes: 6 additions & 3 deletions smartoptimizer/minifiers/css.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,12 @@ function convertUrl($url, $count)
if (preg_match('@^[^/]+:@', $url)) return $url;

$fileType = substr(strrchr($url, '.'), 1);
if (isset($mimeTypes[$fileType])) $mimeType = $mimeTypes[$fileType];
elseif (function_exists('mime_content_type')) $mimeType = mime_content_type($url);
else $mimeType = null;
if (isset($mimeTypes[$fileType]))
$mimeType = $mimeTypes[$fileType];
elseif (function_exists('mime_content_type') && file_exists($fileDir.$url))
$mimeType = mime_content_type($fileDir.$url);
else
$mimeType = null;

if (!$settings['embed'] ||
!file_exists($fileDir.$url) ||
Expand Down
Loading