'HandleWbBackupAction', $wbBackupDelAction => 'HandleWbBackupDelAction', ) ); SDVA( $HandleAuth, array( $wbBackupAction => $wbBackupAuthLevel, $wbBackupDelAction => $wbBackupDelAuthLevel, ) ); SDV($RecipeInfo['wbBackup']['Version'], '2008-10-11'); $FmtPV['$wbBackupVersion'] = "'wbBackup-{$RecipeInfo['wbBackup']['Version']}'"; $wbBackupLocalDir = getcwd(); $wbBackupLocalDir = str_replace ( '\\', '/', $wbBackupLocalDir ); $wbBackupStat = array( files => 0, ignored_dirs => 0, ); $wbBackupHTML = array(); $wbBackupList = array(); /** main function; called by pmwiki when $wbBackupAction is set */ function HandleWbBackupAction ( $pagename, $auth='read' ) { global $wbBackupFile, $wbOverwrite, $wbBackupFileName, $wbBackupDirs, $wbBackupUrl, $wbBackupStat, $wbBackupIgnoreDirs, $wbBackupSendToBrowser, $wbBackupDir, $wbBackupHTML, $wbBackupAction, $wbBackupAuthLevel, $wbBackupList, $wbBackupLocalDir, $wbBackupShowLink; global $PageStartFmt, $PageEndFmt; global $FarmD, $Action, $HandleAuth; // let the config.php in a field overwrite the auth level when // using a wiki farm // (this can normally only be done _before_ the script is included) $HandleAuth[$wbBackupAction] = $wbBackupAuthLevel; $page = RetrieveAuthPage( $pagename, $auth ); if ( ! $page ) { Abort("?you are not permitted to perform this action"); return; } if ( file_exists( $wbBackupFile ) ) { if ( ! $wbOverwrite ) { PrintFmt($pagename,$PageStartFmt); echo "Backup file [$wbBackupFileName] already exists and ", "\$wbOverwrite set to [FALSE]!
\n"; PrintFmt($pagename,$PageEndFmt); exit; } else { wbBackupTrace( "delete existing [$wbBackupFile]" ); unlink( $wbBackupFile ); } } foreach ( $wbBackupDirs as $dir ) { if ( wbToIgnore( $dir ) ) { continue; } ## get full path (as $dir is only the subdir name) $currentdir = getcwd().'/'.$dir; wbBackupScanDir( $currentdir ); } if ( ! empty( $wbBackupList ) ) { $removedir = preg_replace( "#^[a-z]:#i", "", $wbBackupLocalDir ); if ( ! is_dir( $wbBackupDir ) ) { mkdir( $wbBackupDir, 0777 ); } require_once("$FarmD/cookbook/pclzip/pclzip.lib.php"); $zipfile = new PclZip($wbBackupFile); $list = $zipfile->add( $wbBackupList, PCLZIP_OPT_REMOVE_PATH, $removedir ); if ($list == 0) { PrintFmt( $pagename, array( &$PageStartFmt, "
\Error : ".$zipfile->errorInfo(true), &$PageEndFmt ) ); exit; } } // create the HTML $wbBackupHTML[] = "Directories to scan: "; $wbBackupHTML[] = implode( ', ', $wbBackupDirs ) . "
"; $wbBackupHTML[] = "Directories to ignore: "; $wbBackupHTML[] = implode( ', ', $wbBackupIgnoreDirs ) . "
"; $wbBackupHTML[] = ""; foreach ( $wbBackupList as $file ) { $wbBackupHTML[] = "\n \n"; } $wbBackupHTML[] = "
$file
"; $wbBackupHTML[] = "Statistics:
"; foreach ( $wbBackupStat as $item => $value ) { $wbBackupHTML[] = "$item: " . $value . "
"; } if ( $wbBackupShowLink ) { // then offer it to the user to download: $wbBackupHTML[] = "Click here to download the new zip file."; } if ( $wbBackupSendToBrowser ) { header("Content-type: application/zip"); header("Content-disposition: attachment; filename=$wbBackupFileName"); header("Location: $wbBackupUrl"); } PrintFmt( $pagename, array( &$PageStartFmt, implode( "\n", $wbBackupHTML ), &$PageEndFmt ) ); exit; } /** main function for backup file deletion; called by pmwiki when $wbBackupDelAction is set */ function HandleWbBackupDelAction ( $pagename, $auth='read' ) { global $Action, $HandleAuth, $self; global $PageStartFmt, $PageEndFmt; global $wbBackupDelAction, $wbBackupDelAuthLevel, $wbBackupDir, $wbBackupHTML; // let the config.php in a field overwrite the auth level when // using a wiki farm // (this can normally only be done _before_ the script is included) $HandleAuth[$wbBackupDelAction] = $wbBackupDelAuthLevel; $page = RetrieveAuthPage( $pagename, $auth ); if ( ! $page ) { Abort("?you are not permitted to perform this action"); return; } if ( ! empty ( $_POST['wbdelsubmit'] ) ) { foreach ( $_POST as $item => $value ) { if ( ! preg_match( "/\.zip$/i", $value ) ) { continue; } unlink( $wbBackupDir.'/'.$value ); $wbBackupHTML[] = "File [$value] deleted!
"; } } $handle = opendir( $wbBackupDir ); // check for success if ( $handle ) { $wbBackupHTML[] = "
"; $wbBackupHTML[] = "Mark the files you wish to delete and press [Continue]
"; while ( false !== ($file = readdir ($handle)) ) { // ignore files/directories beginning with '.' if ( preg_match( "/^\./i", $file ) ) { wbBackupTrace( "ignored: $file" ); continue; } // ignore files not ending with .zip if ( ! preg_match( "/\.zip$/i", $file ) ) { wbBackupTrace( "ignored: $file" ); continue; } $wbBackupHTML[] = " $file
"; } $wbBackupHTML[] = "
"; } PrintFmt( $pagename, array( &$PageStartFmt, implode( "\n", $wbBackupHTML ), &$PageEndFmt ) ); exit; } /** recursive directory scan */ function wbBackupScanDir( $dir ) { global $wbBackupLocalDir, $wbBackupIgnoreDirs, $wbBackupStat, $wbBackupList; $dir = str_replace ( '\\', '/', $dir ); if ( ! is_dir( $dir ) ) { wbBackupTrace( "[$dir] is not a directory!" ); return; } wbBackupTrace( "removing $wbBackupLocalDir from $dir" ); $relative = preg_replace( "#^$wbBackupLocalDir/?#si", "", $dir ); if ( wbToIgnore( $relative ) ) { return; } wbBackupTrace( "-----> scanning dir $dir" ); // $dir is a complete path here! $handle = opendir( $dir ); // check for success if ( $handle ) { while ( false !== ($file = readdir ($handle)) ) { // ignore files/directories beginning with '.' if ( preg_match( "/^\./i", $file ) ) { #wbBackupTrace( "ignoring $file (beginning with '.')" ); continue; } // full path to current item $currentpath = $dir.'/'.$file; $subdir = preg_replace( "#^$wbBackupLocalDir/?#si", "", $currentpath ); // check if current item is a directory if ( is_dir( $currentpath ) ) { if ( wbToIgnore( $subdir ) ) { continue; } wbBackupScanDir( $subdir ); } // add files else { wbBackupTrace( "adding $currentpath" ); $wbBackupList[] = $subdir; $wbBackupStat['files']++; } } closedir($handle); } else { wbBackupTrace( "unable to open dir $dir - $!" ); } } /** checks if the path contained in $relative is set to ignore */ function wbToIgnore ($relative) { global $wbBackupIgnoreDirs, $wbBackupStat; foreach ( $wbBackupIgnoreDirs as $ignore ) { wbBackupTrace( "checking #^$ignore# - $relative" ); if ( preg_match( "#^$ignore#si", $relative ) ) { wbBackupTrace( "ignoring sub directory $relative" ); $wbBackupStat['ignored_dirs']++; return 1; } } return 0; } /** prints trace message if $wbBackupTrace is set to TRUE */ function wbBackupTrace( $msg ) { global $wbBackupTrace; if ( $wbBackupTrace ) { echo "$msg
\n"; } return 0; } /** CONFIGURATION $wbBackupAction Default: wbbackup Can be used to change the action name for the backup. (...URL...&action=wbbackup) Please note that this must be set _before_ including the recipe! So, if you'd like to include the recipe in a wiki farm, you can only change the backup action for the whole farm. Example: $wbBackupAction = 'mybackup'; $wbBackupAuthLevel Default: admin Can be used to change the authorization level necessary for the backup. Please note: As the backup will be called in a page context, the authorisation level given here will be checked for the current page! That means, if you set the level to 'edit' and a user with edit rights for only one page calls the backup action for this page, he can backup and download all the data! This is not necessarily a security risk, but please remember this when you decide to change the level. Available settings: read, edit, attr, upload, admin (Not all make sense...) Example: $wbBackupAuthLevel = 'admin'; $wbBackupDelAction Default: wbbackupdel Can be used to change the action name for the delete action for backup files. (...URL...&action=wbbackupdel) Please note that this must be set _before_ including the recipe! So, if you'd like to include the recipe in a wiki farm, you can only change the backup action for the whole farm. You will get a page with all available backup files you can choose to delete. Beispiel: $wbBackupDelAction = 'mybackupdel'; $wbBackupDelAuthLevel Default: admin Can be used to change the authorization level necessary for the delete action for backup files. Please see $wbBackupAuthLevel for some further advice. Example: $wbBackupDelAuthLevel = 'admin'; $wbBackupFileName Default: wiki-backup-.zip Name of the ZIP file to create. Example: $wbBackupFileName = 'my-wiki-backup.zip'; $wbBackupDir Default: ./__wiki_backups Directory where the backup files are stored. The recipe will try to create the directory if it does not exist. Please note: By default, this directory is located in the current wiki field. (At the same level as the wiki.d directory.) That means, it will be accessible from outside. This is the default, because it is meant that you can directly download the backup file with your browser, without having to switch to your FTP client or such. If you'd prefer to store the backup files outside the directories accessible from the Web, please change this setting according to your needs. $wbBackupDirs Default: local, pub, cookbook, wiki.d, uploads List of directories to backup. As you can see, the names are _relative_ to the wiki base directory. Please note: You can exlude directories (or even subdirectories) with the $wbBackupIgnoreDirs option described below! Example: $wbBackupDirs = array( "local", "pub", "wiki.d" ); $wbBackupFile Default: $wbBackupDir/$wbBackupFileName It is not necessary to change this option; you should set $wbBackupDir and $wbBackupFileName instead! $wbBackupBaseUrl Default: $ScriptUrl without script file name Base-URL for the download link. You can change this if your backup directory is located outside your wiki. (But still accessible from the web.) $wbBackupUrl Default: $wbBackupBaseURL/__wiki_backups/$wbBackupFileName Complete download URL. You should prefer to set $wbBackupBaseURL to change the download location. As '__wiki_backups' is hardcoded here, you will have to change this if your backup directory is set to another name. $wbBackupShowLink Default: TRUE Set this to FALSE if you don't want a download link on the backup summary page. (F. e., if your backup files are not accessible through the web.) Example: $wbBackupShowLink = FALSE; $wbBackupOverwrite Default: FALSE Set this to TRUE if you wish to automatically overwrite existing backup files. You should prefer to leave this to FALSE and delete the files you don't need any longer using the 'wbbackupdel' action. Example: $wbBackupOverwrite = TRUE; $wbBackupTrace Default: FALSE Prints some further information about what the recipe is doing to the summary page. Useful only for testing and debugging purposes. Example: $wbBackupTrace = TRUE; $wbBackupIgnoreDirs Default: pub/skins, pub/guiedit List of (sub-)directories to skip. Can be used if the data amount is too large. (Most servers kill long running scripts after a while, and only allow a certain amount of memory usage.) The names are _relative_ to the wiki base directory. Example: $wbBackupIgnoreDirs = array( "pub/skins", "pub/guiedit", "uploads" ); $wbBackupSendToBrowser Default: FALSE Set this to TRUE if you want the recipe to send the ZIP file to the browser automatically. (You will get a download window without having to click on the download link.) Example: $wbBackupSendToBrowser = TRUE; HISTORY 2008-01-17 - First release 2008-01-22 - renamed $wbIgnoreDirs to $wbBackupIgnoreDirs to unify variable names - Fix: Text outside php was sent to browser */ ?>