├── .gitignore ├── LICENSE ├── README.md ├── composer.json ├── lib └── DocumentAuthentication │ ├── FrontControllerPlugin.php │ └── Plugin.php └── plugin.xml /.gitignore: -------------------------------------------------------------------------------- 1 | .idea -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2015, Christoph Luehr 2 | All rights reserved. 3 | 4 | Redistribution and use in source and binary forms, with or without 5 | modification, are permitted provided that the following conditions are met: 6 | 7 | * Redistributions of source code must retain the above copyright notice, 8 | this list of conditions and the following disclaimer. 9 | * Redistributions in binary form must reproduce the above copyright 10 | notice, this list of conditions and the following disclaimer in the 11 | documentation and/or other materials provided with the distribution. 12 | * Neither the name of basilicom GmbH nor the names of its contributors may 13 | be used to endorse or promote products derived from this software 14 | without specific prior written permission. 15 | 16 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 17 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19 | ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 20 | LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 21 | CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 22 | SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 23 | INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 24 | CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 25 | ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 26 | POSSIBILITY OF SUCH DAMAGE. 27 | 28 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Document Authentication Plugin 2 | ================================================ 3 | 4 | [![Scrutinizer Code Quality](https://scrutinizer-ci.com/g/basilicom/pimcore-plugin-document-authentication/badges/quality-score.png?b=master)](https://scrutinizer-ci.com/g/basilicom/pimcore-plugin-document-authentication/?branch=master) 5 | [![Codacy Badge](https://www.codacy.com/project/badge/99428c40b3214dc4a68c43ca502ff6f9)](https://www.codacy.com/public/christophluehr_3288/pimcore-plugin-document-authentication) 6 | [![Build Status](https://scrutinizer-ci.com/g/basilicom/pimcore-plugin-document-authentication/badges/build.png?b=master)](https://scrutinizer-ci.com/g/basilicom/pimcore-plugin-document-authentication/build-status/master) 7 | [![SensioLabsInsight](https://insight.sensiolabs.com/projects/abcbcad7-4642-4882-a234-43321c705d45/mini.png)](https://insight.sensiolabs.com/projects/abcbcad7-4642-4882-a234-43321c705d45) 8 | [![Dependency Status](https://www.versioneye.com/user/projects/54c9071ea888b903fa000002/badge.svg?style=flat)](https://www.versioneye.com/user/projects/54c9071ea888b903fa000002) 9 | 10 | Developer info: [Pimcore at basilicom](http://basilicom.de/en/pimcore) 11 | 12 | ## Synopsis 13 | 14 | This Pimcore plugin adds a 15 | front controller plugin to enable selective HTTP Basic Authentication 16 | on a per-document basis via document properties. 17 | 18 | ## Code Example / Method of Operation 19 | 20 | Just enable the plugin, adapt the website properties (username and password) 21 | in the website settings and add the predefined property to a document in 22 | the document tree. 23 | 24 | ## Motivation 25 | 26 | An existing website might be extended with new document pages which 27 | should be inaccessible to ordinary users for preview. The built-in 28 | HTTP Basic Authentication feature of Pimcore is global. This 29 | plugin enables password protection on a document level. 30 | 31 | ## Installation 32 | 33 | Add "basilicom-pimcore-plugin/document-authentication" as a requirement to the 34 | composer.json in the toplevel directory of your Pimcore installation. 35 | 36 | Example: 37 | 38 | { 39 | "require": { 40 | "basilicom-pimcore-plugin/document-authentication": ">=1.0.0" 41 | } 42 | } 43 | 44 | ## API Reference 45 | 46 | * n/a 47 | 48 | ## Tests 49 | 50 | * none 51 | 52 | ## Contributors 53 | 54 | * Conrad Guelzow 55 | 56 | ## License 57 | 58 | * BSD-3-Clause 59 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "basilicom-pimcore-plugin/document-authentication", 3 | "description": "Enables selective HTTP Basic Auth via document properties", 4 | "type": "pimcore-plugin", 5 | "license": "BSD-3-Clause", 6 | "keywords": ["pimcore","authentication","password"], 7 | "homepage": "http://basilicom.de/en/pimcore", 8 | "authors": [ 9 | { 10 | "name": "basilicom Team", 11 | "email": "info@basilicom.de", 12 | "homepage": "http://basilicom.de/", 13 | "role": "Developer" 14 | } 15 | ], 16 | "require": { 17 | "php": ">=5.3.0", 18 | "pimcore/installer-plugin": "~1.3" 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /lib/DocumentAuthentication/FrontControllerPlugin.php: -------------------------------------------------------------------------------- 1 | getParam("document") instanceof Page) { 18 | 19 | $this->handleDocumentAuthentication($request->getParam("document")); 20 | } 21 | 22 | } 23 | 24 | /** 25 | * @param Page $document 26 | */ 27 | private function handleDocumentAuthentication($document) 28 | { 29 | if (is_object($document)) { 30 | 31 | if (!$document->getProperty(Plugin::DOC_PROPERTY_DOCUMENT_AUTHENTICATION_ENABLED)) { 32 | return; // all OK, show page 33 | } 34 | } 35 | 36 | $user = Authentication::authenticateSession(); 37 | if ($user instanceof User) { 38 | return; // all OK, show page 39 | } 40 | 41 | if (self::isDocumentAuthenticationValid()) { 42 | return; // all OK, show page 43 | } 44 | 45 | $this->sendHttpBasicAuthResponse(); 46 | exit; 47 | } 48 | 49 | /** 50 | * @return bool 51 | */ 52 | private function isDocumentAuthenticationValid() 53 | { 54 | 55 | $config = Frontend::getWebsiteConfig(); 56 | 57 | $username = $config->get(Plugin::CONFIG_DOCUMENT_AUTHENTICATION_USERNAME, 'preview'); 58 | $password = $config->get(Plugin::CONFIG_DOCUMENT_AUTHENTICATION_PASSWORD, ''); 59 | 60 | if (trim($password) == '') { 61 | // empty password - this is not good; Deny access! 62 | return false; 63 | } 64 | 65 | if (($_SERVER['PHP_AUTH_USER'] === $username) && ($_SERVER['PHP_AUTH_PW'] === $password)) { 66 | return true; 67 | } 68 | 69 | return false; 70 | } 71 | 72 | private function sendHttpBasicAuthResponse() 73 | { 74 | $config = Frontend::getWebsiteConfig(); 75 | $password = $config->get(Plugin::CONFIG_DOCUMENT_AUTHENTICATION_PASSWORD, null); 76 | 77 | if (($password === null) || (trim($password) == '')) { 78 | 79 | $notice = 'Missing or empty Website Property ' 80 | . Plugin::CONFIG_DOCUMENT_AUTHENTICATION_PASSWORD; 81 | 82 | } else { 83 | 84 | $notice = 'Authentication required'; 85 | } 86 | 87 | /** @var $response \Zend_Controller_Response_Http */ 88 | $response = $this->getResponse(); 89 | 90 | $response->setHeader('Cache-Control', 'max-age=0'); 91 | $response->setHttpResponseCode(401); 92 | $response->setHeader( 93 | 'WWW-Authenticate', 94 | 'Basic realm="' . $notice . '"' 95 | ); 96 | 97 | $response->setBody('Unauthorized.'); 98 | $response->sendResponse(); 99 | } 100 | } 101 | -------------------------------------------------------------------------------- /lib/DocumentAuthentication/Plugin.php: -------------------------------------------------------------------------------- 1 | attach("system.startup", function ($event) { 27 | 28 | $front = \Zend_Controller_Front::getInstance(); 29 | 30 | $frontControllerPlugin = new FrontControllerPlugin(); 31 | $front->registerPlugin($frontControllerPlugin); 32 | }); 33 | } 34 | 35 | public static function install() 36 | { 37 | $database = Db::get(); 38 | 39 | if (!self::isInstalled()) { 40 | 41 | $prop = new PropertyPredefined(); 42 | $prop->setName(self::DOC_PROPERTY_DOCUMENT_AUTHENTICATION_ENABLED); 43 | $prop->setKey(self::DOC_PROPERTY_DOCUMENT_AUTHENTICATION_ENABLED); 44 | $prop->setType('bool'); 45 | $prop->setInheritable(1); 46 | $prop->setCtype('document'); 47 | $prop->save(); 48 | 49 | $database->insert(self::DB_TABLE_WEBSITE_SETTINGS, array( 50 | 'name' => self::CONFIG_DOCUMENT_AUTHENTICATION_USERNAME, 51 | 'type' => 'text', 52 | 'data' => 'preview' 53 | )); 54 | 55 | $database->insert(self::DB_TABLE_WEBSITE_SETTINGS, array( 56 | 'name' => self::CONFIG_DOCUMENT_AUTHENTICATION_PASSWORD, 57 | 'type' => 'text', 58 | 'data' => md5(uniqid('', true)) 59 | )); 60 | } 61 | 62 | return 'Successfully installed plugin DocumentAuthentication.'; 63 | } 64 | 65 | public static function uninstall() 66 | { 67 | $database = Db::get(); 68 | 69 | $prop = PropertyPredefined::getByKey(self::DOC_PROPERTY_DOCUMENT_AUTHENTICATION_ENABLED); 70 | $prop->delete(); 71 | 72 | $sqlQuery = "DELETE FROM " . self::DB_TABLE_WEBSITE_SETTINGS . " WHERE name = ?"; 73 | $database->query($sqlQuery, array(self::CONFIG_DOCUMENT_AUTHENTICATION_USERNAME)); 74 | $database->query($sqlQuery, array(self::CONFIG_DOCUMENT_AUTHENTICATION_PASSWORD)); 75 | 76 | return 'Successfully removed plugin DocumentAuthentication.'; 77 | } 78 | 79 | public static function isInstalled() 80 | { 81 | return (PropertyPredefined::getByKey(self::DOC_PROPERTY_DOCUMENT_AUTHENTICATION_ENABLED) 82 | != null); 83 | } 84 | 85 | public static function needsReloadAfterInstall() 86 | { 87 | return false; // backend only functionality! 88 | } 89 | 90 | } 91 | -------------------------------------------------------------------------------- /plugin.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | DocumentAuthentication 7 | 8 | 9 | Document specific password protection via HTTP Basic Authentication 10 | 11 | 12 | 2.0 13 | 1 14 | 0 15 | 16 | 17 | DocumentAuthentication\Plugin 18 | 19 | 20 | 21 | /DocumentAuthentication/lib 22 | 23 | 24 | 25 | 26 | DocumentAuthentication 27 | 28 | 29 | 30 | 31 | --------------------------------------------------------------------------------