├── .gitignore ├── .jshintrc ├── .travis.yml ├── Gruntfile.js ├── LICENSE.txt ├── README.md ├── composer.json ├── example ├── .htaccess ├── cache │ └── .gitignore ├── images │ └── viper.jpg ├── index.php └── templates │ └── index.html ├── package.json ├── phpunit.xml ├── src └── Slim │ └── Middleware │ ├── ImageResize.php │ └── ImageResize │ ├── DefaultMutator.php │ ├── MutatorAbstract.php │ ├── MutatorInterface.php │ └── ScaleAndCropMutator.php └── test ├── DefaultMutatorTest.php ├── ImageResizeTest.php └── ScaleAndCropMutatorTest.php /.gitignore: -------------------------------------------------------------------------------- 1 | report 2 | vendor 3 | node_modules 4 | .rocketeer 5 | .tm_properties 6 | .DS_Store 7 | composer.lock 8 | -------------------------------------------------------------------------------- /.jshintrc: -------------------------------------------------------------------------------- 1 | { 2 | "curly": true, 3 | "eqeqeq": true, 4 | "eqnull": true, 5 | "immed": true, 6 | "noarg": true, 7 | "quotmark": "double", 8 | "trailing": true, 9 | "undef": true, 10 | "unused": "vars", 11 | 12 | "node": true, 13 | "jquery": true, 14 | "browser": true, 15 | 16 | "predef" : [ 17 | "_", 18 | "jasmine", 19 | "describe", 20 | "xdescribe", 21 | "it", 22 | "xit", 23 | "beforeEach", 24 | "afterEach", 25 | "expect", 26 | "spyOn", 27 | "runs", 28 | "waits", 29 | "waitsFor", 30 | "Backbone", 31 | "Modernizr", 32 | "rivets" 33 | ] 34 | } -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: php 2 | 3 | php: 4 | - 5.3 5 | - 5.4 6 | - 5.5 7 | - 5.6 8 | - hhvm 9 | 10 | before_install: 11 | - sudo pip install codecov 12 | 13 | before_script: 14 | - travis_retry composer self-update 15 | - travis_retry composer install --no-interaction --dev 16 | 17 | script: 18 | - vendor/bin/phpunit --coverage-text --bootstrap vendor/autoload.php --coverage-clover=coverage.xml 19 | 20 | after_success: 21 | - if [[ $TRAVIS_PHP_VERSION != "hhvm" ]]; then codecov --min-coverage=50; fi -------------------------------------------------------------------------------- /Gruntfile.js: -------------------------------------------------------------------------------- 1 | module.exports = function(grunt) { 2 | "use strict"; 3 | 4 | grunt.initConfig({ 5 | pkg: grunt.file.readJSON("package.json"), 6 | watch: { 7 | js: { 8 | files: ["*.js"], 9 | tasks: ["jshint"] 10 | }, 11 | php: { 12 | files: ["src/**/*.php", "test/*.php"], 13 | tasks: ["testphp"] 14 | } 15 | }, 16 | jshint: { 17 | files: ["*.js"], 18 | options: { 19 | jshintrc: ".jshintrc" 20 | } 21 | }, 22 | phplint: { 23 | options: { 24 | swapPath: "/tmp" 25 | }, 26 | all: ["src/**/*.php", "test/*.php"] 27 | }, 28 | phpunit: { 29 | unit: { 30 | dir: "test" 31 | }, 32 | options: { 33 | bin: "vendor/bin/phpunit --bootstrap=vendor/autoload.php --coverage-text --coverage-html ./report", 34 | //bootstrap: "test/bootstrap.php", 35 | colors: true, 36 | testdox: false 37 | } 38 | }, 39 | phpcs: { 40 | application: { 41 | dir: ["src/**/*.php", "test/*.php"] 42 | }, 43 | options: { 44 | bin: "vendor/bin/phpcs", 45 | standard: "PSR2" 46 | } 47 | } 48 | }); 49 | 50 | require("load-grunt-tasks")(grunt); 51 | 52 | /* 53 | grunt.registerTask("build", ["concat", "uglify", "cssmin"]); 54 | grunt.registerTask("test", ["jshint", "jasmine"]); 55 | grunt.registerTask("default", ["testphp", "test", "build"]); 56 | */ 57 | grunt.registerTask("testphp", ["phplint", "phpcs", "phpunit"]); 58 | grunt.registerTask("default", ["jshint", "testphp"]); 59 | 60 | }; -------------------------------------------------------------------------------- /LICENSE.txt: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2014 Mika Tuupola 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Image Resize Middleware for Slim 2 | 3 | This middleware implements automatic image resizing based on image filename. 4 | 5 | [![Author](http://img.shields.io/badge/author-@tuupola-blue.svg?style=flat-square)](https://twitter.com/tuupola) 6 | [![Software License](https://img.shields.io/badge/license-MIT-brightgreen.svg?style=flat-square)](LICENSE.txt) 7 | [![Build Status](https://img.shields.io/travis/tuupola/slim-image-resize/master.svg?style=flat-square)](https://travis-ci.org/tuupola/slim-image-resize) 8 | [![HHVM Status](https://img.shields.io/hhvm/tuupola/slim-image-resize.svg?style=flat-square)](http://hhvm.h4cc.de/package/tuupola/slim-image-resize) 9 | [![Coverage](http://img.shields.io/codecov/c/github/tuupola/slim-image-resize.svg?style=flat-square)](https://codecov.io/github/tuupola/slim-image-resize) 10 | 11 | ## Install 12 | 13 | You can install latest version using [composer](https://getcomposer.org/). 14 | 15 | ``` 16 | $ composer require tuupola/slim-image-resize 17 | ``` 18 | 19 | ## Configuration 20 | 21 | Configuration options are passed as an array. There are no mandatory parameters. 22 | 23 | ```php 24 | $app = new \Slim\Slim(); 25 | $app->add(new Slim\Middleware\ImageResize()); 26 | ``` 27 | 28 | You can configure the allowed image extensions and cache folder. Cache folder must be writable by webserver process. Image quality applies only for jpg images. Example options shown below are also the default options used by the middleware. 29 | 30 | ```php 31 | $app = new \Slim\Slim(); 32 | $app->add(new Slim\Middleware\ImageResize([ 33 | "extensions" => ["jpg", "jpeg", "png", "gif"], 34 | "cache" => "cache", 35 | "quality" => 90 36 | ])); 37 | ``` 38 | 39 | ## Caching 40 | 41 | For caching to work you also must add the following to your [.htaccess](https://github.com/tuupola/slim-image-resize/blob/master/example/.htaccess) file. These rules should be added before Slim rewrite rules. Folder name must be the same you passed in as middleware configuration option. With caching rewrite rules in place only first request is served by PHP. All subsequent requests are served with static file from cache folder. 42 | 43 | ``` 44 | # Check for cached image in cache folder. 45 | RewriteCond %{REQUEST_METHOD} ^GET$ 46 | RewriteCond %{DOCUMENT_ROOT}/cache/%{REQUEST_URI} -f 47 | RewriteRule ^(.*)$ /cache/$1 [L,QSA] 48 | ``` 49 | 50 | If your Slim application is installed in to a subfolder use the following rewrite rule instead. This example assumes the subfolder is called `example`. 51 | 52 | ``` 53 | RewriteBase /example 54 | 55 | # Check for cached image in cache folder. 56 | RewriteCond %{REQUEST_METHOD} ^GET$ 57 | RewriteCond %{DOCUMENT_ROOT}/example/cache/%{REQUEST_URI} -f 58 | RewriteRule ^(.*)$ /example/cache/example/$1 [L,QSA] 59 | 60 | RewriteCond %{REQUEST_FILENAME} !-f 61 | RewriteRule ^ index.php [QSA,L] 62 | ``` 63 | 64 | ## Usage 65 | 66 | With middleware configured you can create different sizes of images by altering the filename. 67 | 68 | ```html 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | ``` 77 | 78 | HTML above will produce the following images. 79 | 80 | ![Original](http://www.appelsiini.net/img/viper.jpg) 81 | ![400x200](http://www.appelsiini.net/img/viper-400x200.jpg) 82 | ![x200](http://www.appelsiini.net/img/viper-x200.jpg) 83 | ![200x](http://www.appelsiini.net/img/viper-200x.jpg) 84 | ![100x100](http://www.appelsiini.net/img/viper-100x100.jpg) 85 | 86 | ## Security 87 | 88 | By default it is possible to create any size image. If images are also cached you should restrict which sizes middleware is allowed to create. Otherwise it is possible to make requests arbitary number of different sizes of images. 89 | 90 | ```php 91 | $app = new \Slim\Slim(); 92 | $app->add(new Slim\Middleware\ImageResize([ 93 | "sizes" => ["400x200", "x200", "200x", "100x100"] 94 | ])); 95 | ``` 96 | 97 | If you have arbitary number of different sizes it is also possible to sign images with secret key. 98 | 99 | ```php 100 | $app->add(new Slim\Middleware\ImageResize([ 101 | "secret" => "s11kr3t" 102 | ])); 103 | ``` 104 | 105 | You must include the signature in the image name. 106 | 107 | ```html 108 | 109 | ``` 110 | 111 | Signature for above image was generated with following code. 112 | 113 | ```php 114 | $sha1 = sha1("400x200:s11kr3t"); 115 | $signature = substr($sha1, 0, 16); 116 | ``` 117 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "tuupola/slim-image-resize", 3 | "type": "library", 4 | "description": "Image Resize Middleware for Slim Framework", 5 | "keywords": ["slim", "middleware", "image"], 6 | "homepage": "https://github.com/tuupola/slim-image-resize", 7 | "license": "MIT", 8 | "authors": [ 9 | { 10 | "name": "Mika Tuupola", 11 | "email": "tuupola@appelsiini.net", 12 | "homepage": "http://www.appelsiini.net/" 13 | } 14 | ], 15 | "require": { 16 | "slim/slim": "~2.3", 17 | "intervention/image": "~2.0" 18 | }, 19 | "autoload": { 20 | "psr-0": { "Slim\\Middleware\\": "src/" } 21 | }, 22 | "require-dev": { 23 | "phpunit/phpunit": "~4.3", 24 | "squizlabs/php_codesniffer": "~1.5" 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /example/.htaccess: -------------------------------------------------------------------------------- 1 | RewriteEngine On 2 | RewriteBase / 3 | 4 | # Check for cached image in cache folder. 5 | RewriteCond %{REQUEST_METHOD} ^GET$ 6 | RewriteCond %{DOCUMENT_ROOT}/cache/%{REQUEST_URI} -f 7 | RewriteRule ^(.*)$ /cache/$1 [L,QSA] 8 | 9 | RewriteCond %{REQUEST_FILENAME} !-f 10 | RewriteRule ^ index.php [QSA,L] -------------------------------------------------------------------------------- /example/cache/.gitignore: -------------------------------------------------------------------------------- 1 | * 2 | !.gitignore 3 | -------------------------------------------------------------------------------- /example/images/viper.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tuupola/slim-image-resize/91e3fded7fae2927b8c634368bd7fa68ad1f6b8a/example/images/viper.jpg -------------------------------------------------------------------------------- /example/index.php: -------------------------------------------------------------------------------- 1 | add(new Slim\Middleware\ImageResize()); 7 | 8 | $app->get("/", function() use ($app) { 9 | $app->render("index.html", array( 10 | "app" => $app 11 | )); 12 | }); 13 | 14 | $app->run(); -------------------------------------------------------------------------------- /example/templates/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Here be dragons 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "slim-image-resize", 3 | "version": "0.5.0", 4 | "repository": { 5 | "type": "git", 6 | "url": "git@github.com:tuupola/slim-image-resize.git" 7 | }, 8 | "author": "Mika Tuupola ", 9 | "devDependencies": { 10 | "grunt": "~0.4.1", 11 | "grunt-contrib-jshint": "~0.7.0", 12 | "grunt-contrib-uglify": "~0.2.4", 13 | "grunt-contrib-watch": "~0.5.3", 14 | "grunt-contrib-concat": "~0.3.0", 15 | "grunt-contrib-cssmin": "~0.6.2", 16 | "grunt-phpunit": "~0.3.2", 17 | "grunt-phplint": "0.0.5", 18 | "load-grunt-tasks": "^0.4.0", 19 | "grunt-phpcs": "^0.2.3" 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /phpunit.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | test/ 6 | 7 | 8 | 9 | 10 | src/ 11 | 12 | 13 | -------------------------------------------------------------------------------- /src/Slim/Middleware/ImageResize.php: -------------------------------------------------------------------------------- 1 | options = array( 32 | "extensions" => array("jpg", "jpeg", "png", "gif"), 33 | "cache" => "cache", 34 | "sizes" => null, 35 | "secret" => null, 36 | "mutator" => new DefaultMutator() 37 | ); 38 | 39 | if ($options) { 40 | $this->options = array_merge($this->options, (array)$options); 41 | } 42 | 43 | /* TODO: Use proper DI. */ 44 | $this->mutator = $this->options["mutator"]; 45 | unset($this->options["mutator"]); 46 | } 47 | 48 | public function call() 49 | { 50 | $request = $this->app->request; 51 | $response = $this->app->response; 52 | 53 | $folder = $request->getRootUri(); 54 | $resource = $request->getResourceUri(); 55 | 56 | $target = $folder . $resource; 57 | if ($matched = $this->mutator->parse($target)) { 58 | /* Extract array variables to current symbol table */ 59 | extract($matched); 60 | }; 61 | 62 | if ($matched && $this->allowed(array("extension" => $extension, "size" => $size, "signature" => $signature))) { 63 | 64 | $this->mutator->execute(); 65 | 66 | /* When requested save image to cache folder. */ 67 | if ($this->options["cache"]) { 68 | /* TODO: Make this pretty. */ 69 | $cache = $_SERVER["DOCUMENT_ROOT"] . $folder . "/" . 70 | $this->options["cache"] . $target; 71 | 72 | $dir = pathinfo($cache, PATHINFO_DIRNAME); 73 | if (false === is_dir($dir)) { 74 | mkdir($dir, 0777, true); 75 | } 76 | $this->mutator->save($cache); 77 | } 78 | 79 | $response->header("Content-type", $this->mutator->mime()); 80 | $response->body($this->mutator->encode()); 81 | } else { 82 | $this->next->call(); 83 | } 84 | } 85 | 86 | public function allowed($parameters = array()) 87 | { 88 | extract($parameters); 89 | return $this->allowedExtension($extension) && 90 | $this->allowedSize($size) && 91 | $this->validSignature($parameters); 92 | } 93 | 94 | public function allowedExtension($extension = null) 95 | { 96 | return $extension && in_array($extension, $this->options["extensions"]); 97 | } 98 | 99 | public function allowedSize($size = null) 100 | { 101 | if (false == !!$this->options["sizes"]) { 102 | /* All sizes are allowed. */ 103 | return true; 104 | } else { 105 | /* Only sizes passed in as array are allowed. */ 106 | return is_array($this->options["sizes"]) && in_array($size, $this->options["sizes"]); 107 | } 108 | } 109 | 110 | public function validSignature($parameters = null) 111 | { 112 | /* Default arguments. */ 113 | $arguments = array( 114 | "size" => null, 115 | "signature" => null 116 | ); 117 | 118 | if ($parameters) { 119 | $arguments = array_merge($arguments, (array)$parameters); 120 | } 121 | 122 | if (false == !!$this->options["secret"] && null === $arguments["signature"]) { 123 | /* No secret is set or passed. All shall pass. */ 124 | return true; 125 | } else { 126 | $signature = self::signature(array( 127 | "size" => $arguments["size"], 128 | "secret" => $this->options["secret"] 129 | )); 130 | 131 | return $arguments["signature"] === $signature; 132 | } 133 | } 134 | 135 | public static function signature($parameters = null) 136 | { 137 | /* Default arguments. */ 138 | $arguments = array( 139 | "size" => null, 140 | "secret" => null, 141 | "width" => null, 142 | "height" => null 143 | ); 144 | 145 | if ($parameters) { 146 | $arguments = array_merge($arguments, (array)$parameters); 147 | } 148 | 149 | $sha1 = sha1("{$arguments["size"]}:{$arguments["secret"]}"); 150 | 151 | /* We use only 16 first characters. Secure enough. */ 152 | return substr($sha1, 0, 16); 153 | } 154 | } 155 | -------------------------------------------------------------------------------- /src/Slim/Middleware/ImageResize/DefaultMutator.php: -------------------------------------------------------------------------------- 1 | [^-]+)-(?(?\d*)x(?\d*))-?(?[0-9a-z]*)/"; 21 | 22 | public function execute() 23 | { 24 | /* Fit or resize. */ 25 | extract($this->options); 26 | if (null !== $width && null !== $height) { 27 | $this->image->fit($width, $height); 28 | } else { 29 | $this->image->resize($width, $height, function ($constraint) { 30 | $constraint->aspectRatio(); 31 | }); 32 | } 33 | 34 | return $this; 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /src/Slim/Middleware/ImageResize/MutatorAbstract.php: -------------------------------------------------------------------------------- 1 | 90); /* Set defaults here. */ 24 | public $image; 25 | 26 | public function __construct($options = array()) 27 | { 28 | self::options($options); 29 | } 30 | 31 | public function options($options = array()) 32 | { 33 | if ($options) { 34 | $this->options = array_merge($this->options, $options); 35 | } 36 | 37 | if (isset($this->options["source"])) { 38 | $this->image = Image::make($this->options["source"]); 39 | } 40 | } 41 | 42 | public static function regexp() 43 | { 44 | return static::$regexp; 45 | } 46 | 47 | public function parse($target) 48 | { 49 | $pathinfo = pathinfo($target); 50 | if (preg_match(self::regexp(), $pathinfo["filename"], $matches)) { 51 | foreach ($matches as $key => $value) { 52 | if (empty($value)) { 53 | $matches[$key] = null; 54 | } 55 | if (is_numeric($key)) { 56 | unset($matches[$key]); 57 | } 58 | } 59 | 60 | $extra["source"] = $_SERVER["DOCUMENT_ROOT"] . "/" . $pathinfo["dirname"] . "/" . 61 | $matches["original"] . "." . $pathinfo["extension"]; 62 | 63 | $parsed = array_merge($matches, $pathinfo, $extra); 64 | $this->options($parsed); 65 | 66 | return $parsed; 67 | } 68 | return false; 69 | } 70 | 71 | public function save($file) 72 | { 73 | return $this->image->save($file, $this->options["quality"]); 74 | } 75 | 76 | public function mime() 77 | { 78 | return $this->image->mime; 79 | } 80 | 81 | public function encode() 82 | { 83 | return $this->image->encode(); 84 | } 85 | 86 | abstract public function execute(); 87 | } 88 | -------------------------------------------------------------------------------- /src/Slim/Middleware/ImageResize/MutatorInterface.php: -------------------------------------------------------------------------------- 1 | [^-]+)-(?(?\d*)-(?\d*)x(?\d*))-?(?[0-9a-z]*)/"; 22 | 23 | public function execute() 24 | { 25 | extract($this->options); 26 | 27 | /* Scale with the given percentage... */ 28 | $scaled_width = round($scale / 100 * $this->image->width()); 29 | $scaled_height = round($scale / 100 * $this->image->height()); 30 | $this->image->resize($scaled_width, $scaled_height); 31 | 32 | $width = $width ? $width : $scaled_width; 33 | $height = $height ? $height : $scaled_height; 34 | 35 | /* ... and crop. */ 36 | $this->image->crop($width, $height); 37 | 38 | return $this; 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /test/DefaultMutatorTest.php: -------------------------------------------------------------------------------- 1 | assertTrue(true); 32 | } 33 | 34 | public function testShouldParseDimensions() 35 | { 36 | $mutator = new DefaultMutator(); 37 | $parsed = $mutator->parse("images/viper-400x200.jpg"); 38 | $this->assertEquals($parsed["filename"], "viper-400x200"); 39 | $this->assertEquals($parsed["basename"], "viper-400x200.jpg"); 40 | $this->assertEquals($parsed["extension"], "jpg"); 41 | $this->assertEquals($parsed["dirname"], "images"); 42 | $this->assertEquals($parsed["original"], "viper"); 43 | $this->assertEquals($parsed["size"], "400x200"); 44 | $this->assertEquals($parsed["width"], "400"); 45 | $this->assertEquals($parsed["height"], "200"); 46 | //$this->assertEquals($parsed["source"], "/var/www/www.example.com/public/images/viper.jpg"); 47 | //$this->assertEquals($parsed["cache"], "/var/www/www.example.com/public/cache/images/viper-400x200.jpg"); 48 | $this->assertNull($parsed["signature"]); 49 | } 50 | 51 | public function testParseShouldReturnFalse() 52 | { 53 | $middleware = new ImageResize(); 54 | $parsed = $middleware->mutator->parse("images/viper-new.jpg"); 55 | $this->assertFalse($parsed); 56 | } 57 | 58 | public function testParseShouldReturnMime() 59 | { 60 | $mutator = new DefaultMutator(); 61 | $parsed = $mutator->parse("images/viper-400x200.jpg"); 62 | $this->assertEquals($mutator->mime(), "image/jpeg"); 63 | } 64 | 65 | public function testExecuteShouldReturnSelf() 66 | { 67 | $mutator = new DefaultMutator(); 68 | $parsed = $mutator->parse("images/viper-400x200.jpg"); 69 | $this->assertInstanceOf("Slim\Middleware\ImageResize\DefaultMutator", $mutator->execute()); 70 | } 71 | 72 | public function testExecuteShouldFit() 73 | { 74 | $mutator = new DefaultMutator(); 75 | $parsed = $mutator->parse("images/viper-400x200.jpg"); 76 | $mutator->execute(); 77 | $this->assertEquals($mutator->image->width(), 400); 78 | $this->assertEquals($mutator->image->height(), 200); 79 | } 80 | 81 | public function testExecuteShouldResize() 82 | { 83 | $mutator = new DefaultMutator(); 84 | $parsed = $mutator->parse("images/viper-400x.jpg"); 85 | $mutator->execute(); 86 | $this->assertEquals($mutator->image->width(), 400); 87 | $this->assertEquals($mutator->image->height(), 300); 88 | 89 | $parsed = $mutator->parse("images/viper-x200.jpg"); 90 | $mutator->execute(); 91 | $this->assertEquals($mutator->image->width(), 267); 92 | $this->assertEquals($mutator->image->height(), 200); 93 | } 94 | } 95 | -------------------------------------------------------------------------------- /test/ImageResizeTest.php: -------------------------------------------------------------------------------- 1 | assertTrue(true); 32 | } 33 | 34 | public function testShouldTestForAllowedExtension() 35 | { 36 | $middleware = new ImageResize(); 37 | $this->assertTrue($middleware->allowedExtension("jpg")); 38 | $this->assertTrue($middleware->allowedExtension("png")); 39 | $this->assertFalse($middleware->allowedExtension("pdf")); 40 | } 41 | 42 | public function testAllSizesShouldBeAllowed() 43 | { 44 | $middleware = new ImageResize(); 45 | $this->assertTrue($middleware->allowedSize("100x100")); 46 | $this->assertTrue($middleware->allowedSize("x666")); 47 | $this->assertTrue($middleware->allowedSize("666x")); 48 | } 49 | 50 | public function testSpecificSizesShouldBeAllowed() 51 | { 52 | $middleware = new ImageResize(array("sizes" => array("100x100", "150x"))); 53 | $this->assertTrue($middleware->allowedSize("100x100")); 54 | $this->assertTrue($middleware->allowedSize("150x")); 55 | $this->assertFalse($middleware->allowedSize("666x666")); 56 | } 57 | 58 | public function testShouldGenerateSignature() 59 | { 60 | $signature = ImageResize::signature(array("size" => "100x200", "secret" => "s11kr3t")); 61 | $this->assertEquals($signature, "e28fe00b3c925c09"); 62 | } 63 | 64 | public function testSignatureShouldNotBeNeeded() 65 | { 66 | $middleware = new ImageResize(); 67 | $this->assertTrue($middleware->validSignature()); 68 | } 69 | 70 | public function testShouldValidateSignature() 71 | { 72 | $middleware = new ImageResize(array("secret" => "s11kr3t")); 73 | $signature = ImageResize::signature(array("size" => "100x200", "secret" => "s11kr3t")); 74 | $this->assertFalse($middleware->validSignature()); 75 | $this->assertTrue($middleware->validSignature(array("signature" => $signature, "size" => "100x200"))); 76 | } 77 | 78 | public function testImagesShouldBeAllowed() 79 | { 80 | $middleware = new ImageResize(array( 81 | "sizes" => array("100x200", "100x100"), 82 | "secret" => "s11kr3t" 83 | )); 84 | 85 | $valid = ImageResize::signature(array("size" => "100x200", "secret" => "s11kr3t")); 86 | $valid_2 = ImageResize::signature(array("size" => "100x100", "secret" => "s11kr3t")); 87 | 88 | $this->assertTrue($middleware->allowed(array( 89 | "signature" => $valid, 90 | "size" => "100x200", 91 | "extension" => "jpg"))); 92 | 93 | $this->assertTrue($middleware->allowed(array( 94 | "signature" => $valid_2, 95 | "size" => "100x100", 96 | "extension" => "png"))); 97 | } 98 | 99 | public function testImagesShouldNotBeAllowed() 100 | { 101 | $middleware = new ImageResize(array( 102 | "extensions" => array("jpg", "png"), 103 | "sizes" => array("100x200", "100x100"), 104 | "secret" => "s11kr3t" 105 | )); 106 | 107 | $valid = ImageResize::signature(array("size" => "100x200", "secret" => "s11kr3t")); 108 | $valid_2 = ImageResize::signature(array("size" => "666x666", "secret" => "s11kr3t")); 109 | $invalid = ImageResize::signature(array("size" => "100x200", "secret" => "t00r")); 110 | 111 | $this->assertFalse($middleware->allowed(array( 112 | "signature" => $invalid, 113 | "size" => "100x200", 114 | "extension" => "jpg"))); 115 | $this->assertFalse($middleware->allowed(array( 116 | "signature" => $valid_2, 117 | "size" => "666x666", 118 | "extension" => "png"))); 119 | $this->assertFalse($middleware->allowed(array( 120 | "signature" => $valid, 121 | "size" => "100x200", 122 | "extension" => "pdf"))); 123 | } 124 | 125 | public function testShouldReturnImage() 126 | { 127 | 128 | \Slim\Environment::mock(array( 129 | /* TODO: Figure out why setting this breaks test. */ 130 | //"SCRIPT_NAME" => "/index.php", 131 | "PATH_INFO" => "/images/viper-200x200.jpg" 132 | )); 133 | $app = new \Slim\Slim(); 134 | $app->get("/foo", function () { 135 | echo "Success"; 136 | }); 137 | 138 | $middleware = new \Slim\Middleware\ImageResize(array( 139 | )); 140 | 141 | $middleware->setApplication($app); 142 | $middleware->setNextMiddleware($app); 143 | $middleware->call(); 144 | 145 | $this->assertEquals(200, $app->response()->status()); 146 | $this->assertEquals("image/jpeg", $app->response()->header("Content-Type")); 147 | } 148 | 149 | public function testShouldReturnHtml() 150 | { 151 | 152 | \Slim\Environment::mock(array( 153 | "SCRIPT_NAME" => "/index.php", 154 | "PATH_INFO" => "/foo" 155 | )); 156 | $app = new \Slim\Slim(); 157 | $app->get("/foo", function () { 158 | echo "Success"; 159 | }); 160 | 161 | $middleware = new \Slim\Middleware\ImageResize(array( 162 | )); 163 | 164 | $middleware->setApplication($app); 165 | $middleware->setNextMiddleware($app); 166 | $middleware->call(); 167 | 168 | $this->assertEquals(200, $app->response()->status()); 169 | $this->assertEquals("text/html", $app->response()->header("Content-Type")); 170 | } 171 | } 172 | -------------------------------------------------------------------------------- /test/ScaleAndCropMutatorTest.php: -------------------------------------------------------------------------------- 1 | assertTrue(true); 32 | } 33 | 34 | public function testShouldParseDimensions() 35 | { 36 | $mutator = new ScaleAndCropMutator(); 37 | $parsed = $mutator->parse("images/viper-70-400x200.jpg"); 38 | $this->assertEquals($parsed["filename"], "viper-70-400x200"); 39 | $this->assertEquals($parsed["basename"], "viper-70-400x200.jpg"); 40 | $this->assertEquals($parsed["extension"], "jpg"); 41 | $this->assertEquals($parsed["dirname"], "images"); 42 | $this->assertEquals($parsed["original"], "viper"); 43 | $this->assertEquals($parsed["size"], "70-400x200"); 44 | $this->assertEquals($parsed["width"], "400"); 45 | $this->assertEquals($parsed["height"], "200"); 46 | $this->assertEquals($parsed["scale"], "70"); 47 | //$this->assertEquals($parsed["source"], "/var/www/www.example.com/public/images/viper.jpg"); 48 | //$this->assertEquals($parsed["cache"], "/var/www/www.example.com/public/cache/images/viper-400x200.jpg"); 49 | $this->assertNull($parsed["signature"]); 50 | } 51 | 52 | public function testParseShouldReturnFalse() 53 | { 54 | $middleware = new ImageResize(); 55 | $parsed = $middleware->mutator->parse("images/viper-new.jpg"); 56 | $this->assertFalse($parsed); 57 | } 58 | 59 | public function testParseShouldReturnMime() 60 | { 61 | $mutator = new ScaleAndCropMutator(); 62 | $parsed = $mutator->parse("images/viper-70-400x200.jpg"); 63 | $this->assertEquals($mutator->mime(), "image/jpeg"); 64 | } 65 | 66 | public function testExecuteShouldReturnSelf() 67 | { 68 | $mutator = new ScaleAndCropMutator(); 69 | $parsed = $mutator->parse("images/viper-70-400x200.jpg"); 70 | $this->assertInstanceOf("Slim\Middleware\ImageResize\ScaleAndCropMutator", $mutator->execute()); 71 | } 72 | 73 | public function testExecuteShouldFit() 74 | { 75 | $mutator = new ScaleAndCropMutator(); 76 | $parsed = $mutator->parse("images/viper-70-400x200.jpg"); 77 | $mutator->execute(); 78 | $this->assertEquals($mutator->image->width(), 400); 79 | $this->assertEquals($mutator->image->height(), 200); 80 | } 81 | 82 | public function testExecuteShouldResize() 83 | { 84 | $mutator = new ScaleAndCropMutator(); 85 | $parsed = $mutator->parse("images/viper-70-400x.jpg"); 86 | $mutator->execute(); 87 | $this->assertEquals($mutator->image->width(), 400); 88 | $this->assertEquals($mutator->image->height(), 402); 89 | 90 | $parsed = $mutator->parse("images/viper-70-x200.jpg"); 91 | $mutator->execute(); 92 | $this->assertEquals($mutator->image->width(), 536); 93 | $this->assertEquals($mutator->image->height(), 200); 94 | } 95 | } 96 | --------------------------------------------------------------------------------