setBlog(DC_BLOG_ID); if (dcCore::app()->blog->id == null && DC_BLOG_ID != 'full_export') { echo 'Blog is not defined'; exit; } // Le script ne fonctionne qu'avec Dotclear >= 2.24 $dcVersion = dcCore::app()->getVersion(); if (version_compare((string) $dcVersion, '2.24', '<')) { echo "This script needs Dotclear version >= 2.24, not [$dcVersion]"; exit; } // Ajuster les paramètres suivants à ses propres besoins. $mail_to = "moi@example.com"; if (dcCore::app()->blog->id == null) { // Cas d'un export global $mail_from = "Full Dotclear dump "; $mail_subject = "[DB DUMP - ".DC_BLOG_ID."] ". date('d/m/Y'); $mail_body = "Servi tout chaud, votre dump de base de données pour le serveur " . $_SERVER['SERVER_NAME'] . " ! \\o/"; # Quelques plugins (gallery, pings, ...) essaient d'accéder aux settings depuis leurs pages d'admin... dcCore::app()->blog->settings = new dcSettings('default'); } else { $mail_from = dcCore::app()->blog->name . " "; $mail_subject = "[DB DUMP - ".DC_BLOG_ID."] ". date('d/m/Y'); $mail_body = "Servi tout chaud, votre dump de base de données pour " . dcCore::app()->blog->name . " ! \\o/"; } /***** PAS BESOIN DE TOUCHER A CE QUI SUIT. *****/ /** @function requireImportExport Recherche le plugin importExport dans les différents path de DC_PLUGINS_ROOT et fait un require_once sur la classe d'export. */ function requireImportExport() { $foundImportExport = false; $pluginPaths = explode(PATH_SEPARATOR, DC_PLUGINS_ROOT); foreach ($pluginPaths as $root) { if (!is_dir($root) || !is_readable($root)) { continue; } if (substr($root, -1) != '/') { $root .= '/'; } if (file_exists($root.'importExport/inc/flat/class.flat.export.php')) { require_once($root.'importExport/inc/flat/class.flat.export.php'); $foundImportExport = true; break; } } if (!$foundImportExport) { echo 'Could not find importExport plugin, exiting.'; exit; } } /** @function mailAttached Un pompage éhonté de la fonction de J. Coggeshall. Pourquoi ré-inventer la roue ? Par flemme, je ne détaille pas les arguments. Leurs noms sont suffisamment parlant à mon goût... Comme rien ne vaut l'original : * Homepage de John : http://www.coggeshall.org/ * Url de l'article : http://www.theukwebdesigncompany.com/articles/php-file-attachments.php */ function mailAttached($to, $from, $subject, $message, $filename, $headers = '') { $uniqueSep = md5(uniqid(time())); $headers .= "From: $from\n". "MIME-Version: 1.0\nContent-Type: multipart/mixed;boundary=\"$uniqueSep\";\n". "charset=\"iso-8859-1\"\nContent-Transfer-Encoding:7bit"; $mime = "--$uniqueSep\n". "Content-Type: text/plain; charset=\"iso-8859-1\"\n". "Content-Transfer-Encoding: 7bit\n\n". $message."\n\n"; if (is_array($filename)) { foreach ($filename as $val) { if (file_exists($val['file'])) { $mime .= "--$uniqueSep\n". "Content-Type: {$val['mimetype']}; ". "name=\"{$val['filename']}\"\n". "Content-Transfer-Encoding: base64\n". "Content-Disposition: attachment\n\n"; $filedata = file_get_contents($val['file']); $mime .= chunk_split(base64_encode($filedata)); } else { print("probleme fichier : ".$val['file']." inexistant"); return(false); } } } else { print("probleme : pas de fichiers transmis ou variable erronee"); return(false); } $mime .= "--$uniqueSep--\n"; return(mail::sendMail($to, $subject, $mime."\n".$message, $headers)); } function backupBlog($file, $blogId) { // Préparation de l'environnement nécessaire pour charger l'admin des plugins if (!defined('DC_CONTEXT_ADMIN')) { define('DC_CONTEXT_ADMIN', true); } dcCore::app()->menu[dcAdmin::MENU_BLOG] = new dcMenu('blog-menu', dcAdmin::MENU_BLOG); dcCore::app()->menu[dcAdmin::MENU_SYSTEM] = new dcMenu('system-menu', dcAdmin::MENU_SYSTEM); dcCore::app()->menu[dcAdmin::MENU_PLUGINS] = new dcMenu('plugins-menu', dcAdmin::MENU_PLUGINS); dcCore::app()->adminurl = new dcAdminURL(dcCore::app()); dcCore::app()->adminurl->register('admin.home', 'index.php'); dcCore::app()->adminurl->registercopy('load.plugin.file', 'admin.home', array('pf' => 'dummy.css')); // Chargement de l'admin des plugins (notamment pour qu'ils "activent" leur éventuel callback d'export) dcCore::app()->auth->sudo(array(dcCore::app()->plugins, 'loadModules'), DC_PLUGINS_ROOT); if ((is_file($file) && is_writable($file)) || (!file_exists($file) && is_writable(dirname($file)))) { if ($blogId != 'full_export') { $exp = new flatExport(dcCore::app()->con, $file, dcCore::app()->prefix); fwrite($exp->fp, '///DOTCLEAR|'.DC_VERSION."|single\n"); $exp->export( dcCategories::CATEGORY_TABLE_NAME, 'SELECT * FROM '.dcCore::app()->prefix.dcCategories::CATEGORY_TABLE_NAME.' '. "WHERE blog_id = '".$blogId."'" ); $exp->export( dcBlogroll::LINK_TABLE_NAME, 'SELECT * FROM '.dcCore::app()->prefix.dcBlogroll::LINK_TABLE_NAME.' '. "WHERE blog_id = '".$blogId."'" ); $exp->export( dcNamespace::NS_TABLE_NAME, 'SELECT * FROM '.dcCore::app()->prefix.dcNamespace::NS_TABLE_NAME.' '. "WHERE blog_id = '".$blogId."'" ); $exp->export( dcBlog::POST_TABLE_NAME, 'SELECT * FROM '.dcCore::app()->prefix.dcBlog::POST_TABLE_NAME.' '. "WHERE blog_id = '".$blogId."'" ); $exp->export( dcMeta::META_TABLE_NAME, 'SELECT meta_id, meta_type, M.post_id '. 'FROM '.dcCore::app()->prefix.dcMeta::META_TABLE_NAME.' M, '.dcCore::app()->prefix.dcBlog::POST_TABLE_NAME.' P '. 'WHERE P.post_id = M.post_id '. "AND P.blog_id = '".$blogId."'" ); $exp->export( dcMedia::MEDIA_TABLE_NAME, 'SELECT * FROM '.dcCore::app()->prefix.dcMedia::MEDIA_TABLE_NAME." WHERE media_path = '". dcCore::app()->con->escape(dcCore::app()->blog->settings->system->public_path)."'" ); $exp->export( dcPostMedia::POST_MEDIA_TABLE_NAME, 'SELECT media_id, M.post_id '. 'FROM '.dcCore::app()->prefix.dcPostMedia::POST_MEDIA_TABLE_NAME.' M, '.dcCore::app()->prefix.dcBlog::POST_TABLE_NAME.' P '. 'WHERE P.post_id = M.post_id '. "AND P.blog_id = '".$blogId."'" ); $exp->export( dcTrackback::PING_TABLE_NAME, 'SELECT ping.post_id, ping_url, ping_dt '. 'FROM '.dcCore::app()->prefix.dcTrackback::PING_TABLE_NAME.' ping, '.dcCore::app()->prefix.dcBlog::POST_TABLE_NAME.' P '. 'WHERE P.post_id = ping.post_id '. "AND P.blog_id = '".$blogId."'" ); $exp->export( dcBlog::COMMENT_TABLE_NAME, 'SELECT C.* '. 'FROM '.dcCore::app()->prefix.dcBlog::COMMENT_TABLE_NAME.' C, '.dcCore::app()->prefix.dcBlog::POST_TABLE_NAME.' P '. 'WHERE P.post_id = C.post_id '. "AND P.blog_id = '".$blogId."'" ); # --BEHAVIOR-- exportSingle dcCore::app()->callBehavior('exportSingleV2', $exp, $blogId); return true; } else { $exp = new flatExport(dcCore::app()->con, $file, dcCore::app()->prefix); fwrite($exp->fp, '///DOTCLEAR|'.DC_VERSION."|full\n"); $exp->exportTable(dcBlog::BLOG_TABLE_NAME); $exp->exportTable(dcCategories::CATEGORY_TABLE_NAME); $exp->exportTable(dcBlogroll::LINK_TABLE_NAME); $exp->exportTable(dcNamespace::NS_TABLE_NAME); $exp->exportTable(dcAuth::USER_TABLE_NAME); $exp->exportTable(dcWorkspace::WS_TABLE_NAME); $exp->exportTable(dcAuth::PERMISSIONS_TABLE_NAME); $exp->exportTable(dcBlog::POST_TABLE_NAME); $exp->exportTable(dcMeta::META_TABLE_NAME); $exp->exportTable(dcMedia::MEDIA_TABLE_NAME); $exp->exportTable(dcPostMedia::POST_MEDIA_TABLE_NAME); $exp->exportTable(dcLog::LOG_TABLE_NAME); $exp->exportTable(dcTrackback::PING_TABLE_NAME); $exp->exportTable(dcBlog::COMMENT_TABLE_NAME); $exp->exportTable(dcAntispam::SPAMRULE_TABLE_NAME); $exp->exportTable(dcCore::VERSION_TABLE_NAME); # --BEHAVIOR-- exportFull dcCore::app()->callBehavior('exportFullV2', $exp); return true; } } return false; } /* C'est ici que ça se passe... */ if (!is_writable(DC_TPL_CACHE)) { echo 'Impossible d\'écrire dans le dossier de cache pour le fichier temporaire. On arrête là.'; exit; } requireImportExport(); $file = DC_TPL_CACHE.'/tmp_'.DC_BLOG_ID.'.txt.gz'; backupBlog($file, DC_BLOG_ID); $backup_content = file_get_contents($file); $backup_content = gzencode($backup_content, 9); file_put_contents($file, $backup_content); $files[0]['file'] = $file; $files[0]['mimetype'] = 'application/x-gzip'; $files[0]['filename'] = 'dbdump_'.DC_BLOG_ID.'_'.date('Y-m-d').".txt.gz"; if (mailAttached($mail_to, $mail_from, $mail_subject, $mail_body, $files)) { print("Fichier de dump envoye"); unlink($files[0]['file']); } else { print("Erreur avec le fichier de dump"); }