WordPress, concrete5, ZF2, PHP, mysql database dump
March 22nd, 2017Here is a very simple script that once uploaded locks onto various architectures and extracts the database using the captured details.
For example, wordpress and concrete5 have been detected here:
When nothing is detected it will still offer the manual entering of the username and password.
It currently supports Concrete5 and WordPress, but I can easily upgrade it to support many more like ZF1, ZF2, Magento, Drupal, Joomla, etc, if there is any interest.
This is handy when you need to quickly copy a database, you simply upload this script to the doc_root and the script will attempt to handle the rest for you.
The script comes with password protection to prevent unauthorised usage, or it will not just be you downloading the database.
The script stores the username and password of those authorised to use it within the code, the password can be entered in plain text, or you can define your own algorithm and store the password encrypted in this way, within the code.
The script can be downloaded from github here and the full source code is below.
/* Adrian Callaghan 21 Mar 2017 Very lightweight database dumper that automatically locks access details provided by other PHP frameworks ****** How to use ****** Enter your usernames and passwords into the constructor in either plain text (insecure if read by someone else) or encypted Example 1: allowing bob access with the password 1234 and joe access with password 5678 - no encryption dbDump::Init(array( 'users' => array( array('username'=>'bob','password'=>'1234'), array('username'=>'joe','password'=>'5678'), ))); Example 2: allowing bob access with the password 1234 and joe access with password 5678 - with encyption method and hashed passwords that must match the method result dbDump::Init(array( 'users' => array( array('username'=>'bob','password'=>'81dc9bdb52d04dc20036dbd8313ed055'), array('username'=>'joe','password'=>'674f3c2c1a8a6f90461e8a66fb5550ba'), ), 'passwordEncryption'=>function($pass){ return md5($pass); } )); */ /****************** Constructor *******************/ dbDump::Init(array( 'users' => array( array('username'=>'bob','password'=>'81dc9bdb52d04dc20036dbd8313ed055'), array('username'=>'joe','password'=>'674f3c2c1a8a6f90461e8a66fb5550ba'), ), 'passwordEncryption'=>function($pass){ return md5($pass); } )); /****************** Class starts... *******************/ final class dbDump{ const APP_STATE = 'state'; const APP_AUTH = 'MY_TOKEN'; const APP_SALT = 'MY_SALT'; private $_users; private $_passwordEncryption; protected function destroySession(){ $this->initSession(); session_destroy(); return $this; } protected function initSession(){ if (session_status() == PHP_SESSION_NONE) { session_start(); } return $this; } protected function getSession($object = true){ $this->initSession(); return $object ? (object) $_SESSION : $_SESSION; } protected function getSessionVar($var = ''){ return isset($this->session->{$var}) ? $this->session->{$var} : false; } protected function setSessionVar($key, $val){ $session = $this->session; $session->{$key} = $val; $this->session = (array) $session; } protected function setSession(array $values){ $this->initSession(); $_SESSION = $values; return $this; } protected function getGet($object = true){ return $object ? (object) $_GET : $_GET; } protected function getGetVar($var = ''){ return isset($this->post->{$var}) ? $this->post->{$var} : false; } protected function isPost(){ return empty($this->getPost(false)) ? false : true; } protected function getPost($object = true){ return $object ? (object) $_POST : $_POST; } protected function getPostVar($var = ''){ return isset($this->post->{$var}) ? $this->post->{$var} : false; } protected function getState(){ return $this->getSessionVar(self::APP_STATE); } protected function setState($state = ''){ $this->setSessionVar(self::APP_STATE, $state); return $this; } protected function is_constant($token) { return $token == T_CONSTANT_ENCAPSED_STRING || $token == T_STRING || $token == T_LNUMBER || $token == T_DNUMBER; } protected function strip($value) { return preg_replace('!^([\'"])(.*)\1$!', '$2', $value); } protected function getDefinitions($php){ $defines = array(); $state = 0; $key = ''; $value = ''; $tokens = token_get_all($php); $token = reset($tokens); while ($token) { // dump($state, $token); if (is_array($token)) { if ($token[0] == T_WHITESPACE || $token[0] == T_COMMENT || $token[0] == T_DOC_COMMENT) { // do nothing } else if ($token[0] == T_STRING && strtolower($token[1]) == 'define') { $state = 1; } else if ($state == 2 && $this->is_constant($token[0])) { $key = $token[1]; $state = 3; } else if ($state == 4 && $this->is_constant($token[0])) { $value = $token[1]; $state = 5; } } else { $symbol = trim($token); if ($symbol == '(' && $state == 1) { $state = 2; } else if ($symbol == ',' && $state == 3) { $state = 4; } else if ($symbol == ')' && $state == 5) { $defines[$this->strip($key)] = $this->strip($value); $state = 0; } } $token = next($tokens); } return $defines; } protected function generateDbForm($fields = null, $forceDisplay = false){ if ($fields===null && !$forceDisplay){ return; } $form = "<form method='post' name='dbForm' class='form-horizontal col-vert-20' role='form'>"; $form.= "<div class='form-group'><label class='col-sm-2 control-label'>Host</label><div class='col-sm-10'><input name='host' type='text' placeholder='Enter host name' required='required' class='form-control' value='".(isset($fields->host) ? $fields->host : '')."'></div></div>"; $form.= "<div class='form-group'><label class='col-sm-2 control-label'>Table</label><div class='col-sm-10'><input name='table' type='text' placeholder='Enter table name' required='required' class='form-control' value='".(isset($fields->table) ? $fields->table : '')."'></div></div>"; $form.= "<div class='form-group'><label class='col-sm-2 control-label'>User</label><div class='col-sm-10'><input name='username' type='text' placeholder='Enter user name' required='required' class='form-control' value='".(isset($fields->username) ? $fields->username : '')."'></div></div>"; $form.= "<div class='form-group'><label class='col-sm-2 control-label'>Password</label><div class='col-sm-10'><input name='password' type='text' placeholder='Enter password' required='required' class='form-control' value='".(isset($fields->password) ? $fields->password : '')."'></div></div>"; $form.= "<div class='form-group'><div class='col-sm-12'><button type='submit' name='button-submit' class='btn btn-success btn-lg pull-right' value=''> <span class='glyphicon glyphicon-download'></span> Download</button></div></div>"; $form.= "</form>"; return $form; } protected function getPlatform($options){ $error = '<div class="pull-right text-warning"><span class="glyphicon glyphicon-warning-sign status"></span></div>'; $notFound = '<div class="pull-right text-danger"><span class="glyphicon glyphicon-remove status"></span></div>'; $found = '<div class="pull-right text-success"><span class="glyphicon glyphicon-ok status"></span></div>'; $out = '<li class="list-group-item">'; $logoW = isset($options->logoW) ? $options->logoW : '213'; $logoH = isset($options->logoH) ? $options->logoH : '120'; $logo = "<img src='".(isset($options->logo) ? $options->logo : "holder.js/{$logoW}x{$logoH}")."' height='{$logoH}' width='{$logoW}' alt='platform logo' longdesc='logo representing the platform option' />"; $dbArgs = new StdClass(); if (isset($options->conf) && file_exists($options->conf)){ if (($fp = fopen($options->conf, "r"))!==false){ $params = (object) $this->getDefinitions(stream_get_contents($fp)); foreach(array('host','table','username','password') AS $option){ $dbArgs->{$option} = isset($options->{$option}) && isset($params->{$options->{$option}}) ? $params->{$options->{$option}} : ''; } $out .= $found.$logo.$this->generateDbForm($dbArgs, isset($options->force) ? $options->force : null); fclose($fp); } else { $out .= $error.$logo.$this->generateDbForm(null, isset($options->force) ? $options->force : null); } } else { $out .= $notFound.$logo.$this->generateDbForm(null, isset($options->force) ? $options->force : null); } $out.= '</li>'; return $out; } protected function getPlatforms(){ $out = '<ul class="list-group">'; $out .= $this->getPlatform((object) array( 'conf' => 'wp-config.php', 'logo' => 'https://s.w.org/about/images/logos/wordpress-logo-32-blue.png', 'logoW' => '32', 'logoH' => '32', 'host' => 'DB_HOST', 'table' => 'DB_NAME', 'username' => 'DB_USER', 'password' => 'DB_PASSWORD' )); $out .= $this->getPlatform((object) array( 'conf' => 'config/site.php', 'logo' => 'https://www.concrete5.org/files/3613/5517/8150/concrete5_Wordmark_200x37.png', 'logoW' => '200', 'logoH' => '37', 'host' => 'DB_SERVER', 'table' => 'DB_DATABASE', 'username' => 'DB_USERNAME', 'password' => 'DB_PASSWORD' )); /*$out .= $this->getPlatform((object) array( 'conf' => 'config/autoload/local.php', 'logo' => 'http://clloh.com/wp-content/uploads/2015/08/zf2-logo-128x128.png', 'logoW' => '128', 'logoH' => '128', 'host' => 'DB_SERVER', 'table' => 'DB_DATABASE', 'username' => 'DB_USERNAME', 'password' => 'DB_PASSWORD' ));*/ $out .= $this->getPlatform((object) array( 'logo' => 'https://www.mysql.com/common/logos/logo-mysql-170x115.png', 'logoW' => '170', 'logoH' => '115', 'force' => true, )); return $out.'</ul>'; } protected function getHeader(){ return '<html><head><title>Restricted area</title><link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous"><script src="https://code.jquery.com/jquery-3.2.1.js" integrity="sha256-DZAnKJ/6XZ9si04Hgrsxu/8s717jcIzLy3oi35EouyE=" crossorigin="anonymous"></script><script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js" integrity="sha384-Tc5IQib027qvyjSMfHjOMaLkfuWVxZxUPnCJA7l2mCWNIpG9mGCD8wGNIcPD7Txa" crossorigin="anonymous"></script><script src="https://cdnjs.cloudflare.com/ajax/libs/holder/2.9.4/holder.js"></script><META NAME="ROBOTS" CONTENT="NOINDEX, NOFOLLOW"><style>.col-vert-20{margin-top:20px;}.col-vert-100{margin-top:100px;}.status{font-size:30px;}</style></head><body><div class="container-fluid"><div class="row">'; } protected function getFooter(){ $footer = '</div></div>'; if ($this->authentication) { $footer .= '<div class="modal fade" id="confirmationModal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel"> <div class="modal-dialog modal-sm" role="document"> <div class="modal-content"> <div class="modal-header"> <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button> <h4 class="modal-title" id="myModalLabel"><span class="glyphicon glyphicon-lock"></span> Log out request.</h4> </div> <div class="modal-body"> Are you sure you wish to logout '.$this->authentication->username.'? </div> <div class="modal-footer"> <button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button> <a type="button" class="btn btn-primary" href="?logout=true">Confirm</a> </div> </div> </div> </div> </body></html>'; } return $footer; } protected function loginForm($inErrorState = false){ return '<div class="col-md-6 well well-large col-md-offset-3 col-vert-100"><h3><span class="glyphicon glyphicon-lock"></span> '.($inErrorState ? 'Access Denied' : 'Secure Area' ).'</h3><form method="post" name="login" class="form-horizontal col-vert-20" role="form"><div class="form-group '.($inErrorState ? 'has-error' : '').'"><label class="col-sm-2 control-label">Username</label><div class=" col-sm-10"><input name="username" type="text" placeholder="Enter username" required="required" class="form-control" value="">'.($inErrorState ? '<ul class="help-block"><li>Invalid username & password combination</li></ul>' : '').'</div></div><div class="form-group '.($inErrorState ? 'has-error' : '').'"><label class="col-sm-2 control-label">Password</label><div class=" col-sm-10"><input name="password" type="password" required="required" placeholder="Password" class="form-control" value="">'.($inErrorState ? '<ul class="help-block"><li>Invalid username & password combination</li></ul>' : '').'</div></div><div class="form-group "><div class=" col-sm-10 col-sm-offset-2"><button type="submit" name="button-submit" class="btn btn-default" value="">Login</button></div></div></form></div>'; } protected function getDownloadOptions($inErrorState = false){ return '<div class="col-md-6 col-md-offset-3 col-vert-100"><div class="panel panel-primary"><div class="panel-heading"><span class="glyphicon glyphicon-wrench"></span> Export options<button class="pull-right btn btn-danger btn-xs" data-toggle="modal" data-target="#confirmationModal">'.$this->authentication->username.' <span class="glyphicon glyphicon-remove-circle"></span></button></div>'.$this->platforms.'</div></div>'; } protected function setUsers(array $users = null){ if ($users==null){ $users = array(); } foreach($users AS $key=>$user){ $users[$key] = (object) $user; } $this->_users = (object) $users; return $this; } protected function getUsers(){ if (!isset($this->_users)){ $this->setUsers(); } return $this->_users; } protected function setPasswordEncryption($function = null){ if ($function==null){ $function = function($val){return $val;}; } $this->_passwordEncryption = $function; return $this; } protected function getPasswordEncryption(){ if (!isset($this->_passwordEncryption)){ $this->setPasswordEncryption(); } return $this->_passwordEncryption; } protected function PasswordEncrypt($pass = ''){ $encryptor = $this->getPasswordEncryption(); return call_user_func($encryptor, $pass); } protected function generateUserToken(\StdClass $user){ return md5((isset($user->username) ? $user->username : uniqid()).self::APP_SALT.(isset($user->password) ? $user->password : uniqid())); } protected function setAuthentication(\StdClass $user){ $this->setSessionVar(self::APP_AUTH, $this->generateUserToken($user)); return $this; } protected function getAuthentication(){ $token = $this->getSessionVar(self::APP_AUTH); foreach($this->users AS $validUser){ $validToken = $this->generateUserToken($validUser); if ($token==$validToken){ return $validUser; } } } protected function authenticateUser(\StdClass $user){ foreach($this->users AS $validUser){ if ($user->username==$validUser->username && $this->passwordEncrypt($user->password)==$validUser->password){ $this->authentication = $validUser; $this->state = 'options'; return $this->authentication; } } } public static function Init(array $options = array()){ static $inst = null; if ($inst === null) { $inst = new dbDump($options); } if (isset($inst->get->logout)){ $inst->destroySession(); header('Location: '.$_SERVER['PHP_SELF']); die; } if (!$inst->authentication){ $inst->state = null; } switch($inst->state){ case 'options': //var_dump($inst->authentication); if ($inst->isPost()){ $hostname = $inst->getPostVar('host'); $table = $inst->getPostVar('table'); $username = $inst->getPostVar('username'); $password = $inst->getPostVar('password'); $command = "mysqldump --add-drop-table --host=$hostname --user=$username --password=$password $table"; header('Content-Description: File Transfer'); header('Content-Type: application/octet-stream'); header('Content-Disposition: attachment; filename='.basename($table."_".date("Y-m-d_H-i-s").".sql")); system($command); exit(); } else { echo $inst->header; echo $inst->downloadOptions; echo $inst->footer; } break; default: if ($inst->isPost()){ if ($inst->authenticateUser($inst->post)){ $inst->state = 'options'; header("Refresh:0"); die; } else { echo $inst->header; echo $inst->loginForm(true); echo $inst->footer; } } else { echo $inst->header; echo $inst->loginForm(); echo $inst->footer; } break; } } public function __set($name, $value) { $method = 'set' . $name; if (method_exists($this, $method)) { $this->$method($value); return $this; } throw new \Exception('"'.$name.'" is an invalid property of '.__CLASS__.' assignment failed!'); } public function __get($name) { $method = 'get' . $name; if (method_exists($this, $method)) { return $this->$method(); } throw new \Exception('Invalid '.__CLASS__.' property '.$name); } public function setOptions(array $options) { $methods = get_class_methods($this); foreach ($options as $key => $value) { $method = 'set' . ucfirst($key); if (in_array($method, $methods)) { $this->$method($value); } } return $this; } private function __construct(array $options = null) { // env set_time_limit(20); if (is_array($options)) { $this->setOptions($options); } } private function __clone(){} } |
Desktop tidy
December 3rd, 2014A cluttered desktop can be a problem, typically people use the desktop becuase they know the location of the files should they have downloaded them from somewhere, and need to reuse them quickly.
I have written a script that runs on Linux that cleans the desktop up on a daily basis, by moving all the files into a folder with an easily readable date name within an archive folder, so that your desktop remains clean and ordered, and you also do not lose your files.
The beauty of this is that you can configure your applications to point at the desktop, safe in the knowledge that all the clutter from today will be gone tomorrow, and placed neatly within a folder with the date so you can find it, when somebody says “I sent it to you Tuesday”
Just run the script below and it will automatically install, any clutter on the Desktop will archive to folder with yesterday’s date found within the Archive folder located on the Desktop.
You can download it here after unzipping, simply install using terminal with:
sudo chmod a+x desktop-tidy-install.sh sudo ./desktop-tidy-install.sh
The source code is below:
#!/bin/bash ######################## # # # Install script # For Desktop tidy, compat with any distro running Gnome 3, tested on fedora 20 # # Adrian callaghan 02-12-2014 # # ######################## ######################## # are you capable? if [[ $(/usr/bin/id -u) -ne 0 ]]; then echo "You must run this install script with super user privileges, use either sudo or become root with su -" exit; fi ######################## # enviroment user=$SUDO_USER; userhome="/home/$user"; scriptPath="/usr/local/bin/dt.sh"; autostartFile="dt.desktop"; desktop="$userhome/Desktop"; archive="$desktop/Archived"; ######################## # reinstall? if [ -f "$scriptPath" ] || [ -f "$autostartPath" ]; then echo "Removing previous install" if [ -f "$scriptPath" ]; then rm "$scriptPath" fi if [ -f "$autostartPath" ]; then rm "$autostartPath" fi fi ######################## # create archive folder if none exists, permissions follow later if [ ! -d "$archive" ]; then mkdir "$archive" fi ######################## # create script echo "#!/bin/bash" > $scriptPath; echo "archive=$archive" >> $scriptPath; echo "desktop=$desktop" >> $scriptPath; echo 'curr_archive="$archive/$(date +"%d-%B-%Y" -d "1 day ago")"; # if has not been archived yet, archive if [ ! -d "$curr_archive" ]; then mkdir "$curr_archive"; for file in $desktop/*; do if [ "$file" != "$archive" ]; then mv "$file" "$curr_archive" fi done fi ' >> $scriptPath; chmod 755 $scriptPath chown "$user:$user" $scriptPath ######################## # Add autostart if [ ! -d "$userhome/.config" ]; then mkdir "$userhome/.config" fi if [ ! -d "$userhome/.config/autostart" ]; then mkdir "$userhome/.config/autostart" fi echo "[Desktop Entry] Name=DeskTidy GenericName=Creates a daily desktop Comment=Allows the user to have a clean desktop daily and keep the all the files in an ordered fashion Exec=$scriptPath Terminal=true Type=Application X-GNOME-Autostart-enabled=true " > "$userhome/.config/autostart/$autostartFile"; chmod 755 "$userhome/.config/autostart/$autostartFile" chown "$user:$user" "$userhome/.config/autostart/$autostartFile" ######################### # Trigger script! # source "$scriptPath" chmod "1775" "-R" "$archive" chown "root:$user" "-R" "$archive" ######################### # FEEDBACK echo "!! Desktop Tidy successfully installed !!" echo "When you login a desktop will be created based on todays date" echo "Should you wish to retrieve an old file, archives can be found at $archive and are named by date"3,480 views
adding password authentication for a zend cms or controller
December 13th, 2011This is a very quick way to add password protection to a controller such as a cms controller.
This code intercepts the login within the init() method of your chosen controller, if they are logged in they are free to go, if not they are required to login, the form is rendered and validated against the access model.
The session is obfuscated to deter tampering.
so firstly in your controller init() add
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 | $adminSession = new Zend_Session_Namespace('Admin'); $this->access = new Application_Model_accessControl(); // access control // logged in user $loginMsg = 'Please login'; $loginForm = new Zend_Form; $loginForm ->setMethod('post') ->setAttrib('id','login') ->addElement('text','user',array('label'=>'Username','required'=>true)) ->addElement('password','pass',array('label'=>'Password','required'=>true)) ->addElement('submit','Login'); if ($this->getRequest()->isPost() && $loginForm->isValid($_POST)){ $session = $this->access->validateUser( $loginForm->getValue('user'), $loginForm->getValue('pass') ); if ($session){ $adminSession->loggedInSession = $session; $adminSession->loggedInUser = $loginForm->getValue('user'); } $loginMsg='Access denied'; } if (!$this->access->sessionIsValid($adminSession->loggedInSession) || !$adminSession->loggedInUser){ $this->view->header=$loginMsg; $this->view->content = $loginForm; $this->render('login'); } else { // renew session, will always be the "Now" session, but three are provided, see the model $adminSession->loggedInSession = $this->access->getValidSession(); $this->view->userIdent = $adminSession->loggedInUser; } |
$this->view->userIdent will always contain the logged in user
The next step is to create the model for authentication in models/accessControl.php
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 | <?php class Application_Model_accessControl { public function __construct(){ // set users, password is the key, because this is less likely to be duplicated $this->setUsers( array( 'password1'=>'admin', 'password2'=>'admin' ) ); // salt for session key $this->setSalt('MySaltGoesHere1234'); } public function validateUser($username, $password){ /* * return session if correct, null otherwise */ $users = $this->getUsers(); if (isset($users[$password]) && $users[$password]==$username){ return $this->getValidSession(); } } public function sessionIsValid($session,$debug=false){ $validSessions = $this->getValidSessions(); if ($debug){ echo "MY KEY: $session<br >KEYS: ".print_r($validSessions,true); } return in_array($session, $validSessions) ? true : false; } public function getValidSessions(){ $sessions = array( $this->getValidSession('past'), $this->getValidSession('now'), $this->getValidSession('future') ); return $sessions; } public function getValidSession($for='now'){ /* * Three sessions are provided, * * past, now and present * * past, person logs in at 11:59 spends ten minutes editing, clicks save at 12:09, past would be the valid session * now, person is logged in during 11:00 - 11:59 * future, is provided encase of time travel, or if the british summer time kicks in while editing, unlikely but more is better than not enough... */ $hour = intval(date('H')); switch($for){ case 'past' : $validSession = ($hour-1) < 0 ? 23 : $hour-1; break; case 'now' : default: $validSession = $hour; break; case 'future' : $validSession = ($hour+1) > 23 ? 0 : $hour+1; break; } /* * obsfucation */ // firstly grab specific details to stop session hijacking $ip = $_SERVER['REMOTE_ADDR']; $browser = $_SERVER['HTTP_USER_AGENT']; // then mix it up and md5 it $validSession = $ip.$validSession.$this->getSalt().$browser; if (!getenv('APPLICATION_ENV')){ $validSession = md5($validSession); } return $validSession; } public function setUsers($users){ $this->users = $users; } public function getUsers(){ return $this->users; } public function setSalt($salt){ $this->salt = $salt; } public function getSalt(){ return $this->salt; } } |
and finally create a view login.phtml (this is just bare bones)
1 2 | <?php echo "<h2>{$this->header}</h2>"; ?> <?php echo $this->content; ?> |
Thats it!
8,572 viewsOnline md5 hasher
June 12th, 2009MD5 Hasher,
To generate an md5 hash just enter your text below
5,431 viewsHow many days old am I?
May 28th, 2009How many days old are you?
Well just fill in your birthday below to find out!
49,608 views