diff --git a/docs/NEWS b/docs/NEWS index 6224eb0a..b5d546df 100644 --- a/docs/NEWS +++ b/docs/NEWS @@ -3,6 +3,8 @@ Version 1.4 () ------------------------------------------------------------------------ + * Added SMF importer [1.4-beta2] + * Fix setting cookies for 30 Days, not only ~43 Minutes. Thanks to konus! [1.4-beta2] diff --git a/include/admin/importers/smf.inc.php b/include/admin/importers/smf.inc.php new file mode 100644 index 00000000..587424c4 --- /dev/null +++ b/include/admin/importers/smf.inc.php @@ -0,0 +1,311 @@ + 'SMF'); + var $data = array(); + var $inputFields = array(); + var $categories = array(); + + function getImportNotes() { + return 'SMF uses salted MD5 passwords that Serendipity cannot import. Thus, those passwords are incompatible with the MD5 hashing of Serendipity. The passwords for all users have been set to a random string. You need to modify the passwords manually for each user, we are sorry for that inconvenience.
'; + } + + function Serendipity_Import_smf($data) { + $this->data = $data; + $this->inputFields = array(array('text' => INSTALL_DBHOST, + 'type' => 'input', + 'name' => 'host'), + + array('text' => INSTALL_DBUSER, + 'type' => 'input', + 'name' => 'user'), + + array('text' => INSTALL_DBPASS, + 'type' => 'protected', + 'name' => 'pass'), + + array('text' => INSTALL_DBNAME, + 'type' => 'input', + 'name' => 'name'), + + array('text' => INSTALL_DBPREFIX, + 'type' => 'input', + 'name' => 'prefix', + 'default' => 'smf_'), + + array('text' => CHARSET, + 'type' => 'list', + 'name' => 'charset', + 'value' => 'native', + 'default' => $this->getCharsets(false)), + + array('text' => CONVERT_HTMLENTITIES, + 'type' => 'bool', + 'name' => 'use_strtr', + 'default' => 'true'), + + array('text' => ACTIVATE_AUTODISCOVERY, + 'type' => 'bool', + 'name' => 'autodiscovery', + 'default' => 'false') + ); + } + + function validateData() { + return sizeof($this->data); + } + + function getInputFields() { + return $this->inputFields; + } + + function import() { + global $serendipity; + + // Save this so we can return it to its original value at the end of this method. + $noautodiscovery = isset($serendipity['noautodiscovery']) ? $serendipity['noautodiscovery'] : false; + + if ($this->data['autodiscovery'] == 'false') { + $serendipity['noautodiscovery'] = 1; + } + + $this->getTransTable(); + + $this->data['prefix'] = serendipity_db_escape_string($this->data['prefix']); + $users = array(); + $entries = array(); + + if (!extension_loaded('mysql')) { + return MYSQL_REQUIRED; + } + + $gdb = @mysql_connect($this->data['host'], $this->data['user'], $this->data['pass']); + if (!$gdb) { + return sprintf(COULDNT_CONNECT, $this->data['host']); + } + + if (!@mysql_select_db($this->data['name'])) { + return sprintf(COULDNT_SELECT_DB, mysql_error($gdb)); + } + + /* Users */ + $res = @$this->nativeQuery("SELECT ID_MEMBER AS ID, + memberName AS user_login, + passwd AS user_pass, + emailAddress AS user_email, + ID_GROUP AS user_level + FROM {$this->data['prefix']}members + WHERE is_activated = 1", $gdb); + if (!$res) { + return sprintf(COULDNT_SELECT_USER_INFO, mysql_error($gdb)); + } + + for ($x=0, $max_x = mysql_num_rows($res); $x < $max_x ; $x++ ) { + $users[$x] = mysql_fetch_assoc($res); + + $data = array('right_publish' => 1, + 'realname' => $users[$x]['user_login'], + 'username' => $users[$x]['user_login'], + 'email' => $users[$x]['user_email'], + 'userlevel' => ($users[$x]['user_level'] == 1 ? USERLEVEL_ADMIN : USERLEVEL_EDITO), + 'password' => $users[$x]['user_pass']); // MD5 compatible + + if ($serendipity['serendipityUserlevel'] < $data['userlevel']) { + $data['userlevel'] = $serendipity['serendipityUserlevel']; + } + + serendipity_db_insert('authors', $this->strtrRecursive($data)); + echo mysql_error(); + $users[$x]['authorid'] = serendipity_db_insert_id('authors', 'authorid'); + } + + /* Categories */ + $res = @$this->nativeQuery("SELECT ID_CAT AS cat_ID, + name AS cat_name + FROM {$this->data['prefix']}categories", $gdb); + if (!$res) { + return sprintf(COULDNT_SELECT_CATEGORY_INFO, mysql_error($gdb)); + } + + // Get all the info we need + for ($x=0, $max_x = mysql_num_rows($res) ; $x < $max_x ; $x++) { + $parent_categories[] = mysql_fetch_assoc($res); + } + + for ($x=0, $max_x = sizeof($parent_categories) ; $x < $max_x ; $x++ ) { + $cat = array('category_name' => $parent_categories[$x]['cat_name'], + 'category_description' => '', + 'parentid' => 0, // <--- + 'category_left' => 0, + 'category_right' => 0); + + serendipity_db_insert('category', $this->strtrRecursive($cat)); + $parent_categories[$x]['categoryid'] = serendipity_db_insert_id('category', 'categoryid'); + } + + /* Categories */ + $res = @$this->nativeQuery("SELECT ID_BOARD AS cat_ID, + ID_CAT AS parent_cat_id, + name AS cat_name, + description AS category_description + FROM {$this->data['prefix']}boards ORDER BY boardOrder;", $gdb); + if (!$res) { + return sprintf(COULDNT_SELECT_CATEGORY_INFO, mysql_error($gdb)); + } + + // Get all the info we need + for ($x=0, $max_x = mysql_num_rows($res) ; $x < $max_x ; $x++) { + $categories[] = mysql_fetch_assoc($res); + } + + // Insert all categories as top level (we need to know everyone's ID before we can represent the hierarchy). + for ($x=0, $max_x = sizeof($categories) ; $x < $max_x ; $x++ ) { + $pcatid = 0; + foreach($parent_categories AS $pcat) { + if ($pcat['cat_ID'] == $categories[$x]['parent_cat_id']) { + $pcatid = $pcat['cat_ID']; + break; + } + } + + $cat = array('category_name' => $categories[$x]['cat_name'], + 'category_description' => $categories[$x]['category_description'], + 'parentid' => $pcatid, // <--- + 'category_left' => 0, + 'category_right' => 0); + + serendipity_db_insert('category', $this->strtrRecursive($cat)); + $categories[$x]['categoryid'] = serendipity_db_insert_id('category', 'categoryid'); + } + + serendipity_rebuildCategoryTree(); + + /* Entries */ + $res = @$this->nativeQuery("SELECT + + tm.subject AS post_subject, + t.ID_MEMBER_STARTED AS topic_poster, + t.ID_BOARD AS forum_id, + tm.posterTime AS post_time, + tm.body AS post_text, + t.ID_TOPIC AS topic_id, + t.ID_FIRST_MSG AS post_id, + t.numReplies AS ccount + + FROM {$this->data['prefix']}topics AS t + JOIN {$this->data['prefix']}messages AS tm + ON tm.ID_MSG = t.ID_FIRST_MSG + + GROUP BY t.ID_TOPIC", $gdb); + if (!$res) { + return sprintf(COULDNT_SELECT_ENTRY_INFO, mysql_error($gdb)); + } + + for ($x=0, $max_x = mysql_num_rows($res) ; $x < $max_x ; $x++ ) { + $entries[$x] = mysql_fetch_assoc($res); + + $entry = array('title' => $this->decode($entries[$x]['post_subject']), + 'isdraft' => 'false', + 'allow_comments' => 'true', + 'timestamp' => $entries[$x]['post_time'], + 'body' => $this->strtr($entries[$x]['post_text']), + 'extended' => '' + ); + + $entry['authorid'] = ''; + $entry['author'] = ''; + foreach ($users as $user) { + if ($user['ID'] == $entries[$x]['topic_poster']) { + $entry['authorid'] = $user['authorid']; + $entry['author'] = $user['user_login']; + break; + } + } + + if (!is_int($entries[$x]['entryid'] = serendipity_updertEntry($entry))) { + return $entries[$x]['entryid']; + } + + /* Entry/category */ + foreach ($categories as $category) { + if ($category['cat_ID'] == $entries[$x]['forum_id'] ) { + $data = array('entryid' => $entries[$x]['entryid'], + 'categoryid' => $category['categoryid']); + serendipity_db_insert('entrycat', $this->strtrRecursive($data)); + break; + } + } + + /* Comments */ + $topic_id = $entries[$x]['topic_id']; + $c_res = @$this->nativeQuery("SELECT + tm.subject AS post_subject, + tm.body AS post_text, + tm.ID_MSG AS post_id, + tm.posterTime AS post_time, + tm.ID_BOARD AS forum_id, + tm.posterName AS poster_name, + tm.posterEmail AS poster_email + + FROM {$this->data['prefix']}topics AS t + JOIN {$this->data['prefix']}messages AS tm + ON tm.ID_TOPIC = t.ID_TOPIC + WHERE t.ID_TOPIC = {$topic_id} + ", $gdb); + + if (!$c_res) { + return sprintf(COULDNT_SELECT_COMMENT_INFO, mysql_error($gdb)); + } + + while ($a = mysql_fetch_assoc($c_res)) { + if ($a['post_id'] == $entries[$x]['post_id']) { + continue; + } + $author = $a['poster_name']; + $mail = $a['poster_email']; + $url = ''; + + foreach($users AS $user) { + if ($user['ID'] == $a['poster_id']) { + $author = $user['user_login']; + $mail = $user['user_email']; + $url = $user['user_url']; + break; + } + } + $a['post_text'] = html_entity_decode($a['post_text']); + + $comment = array('entry_id ' => $entries[$x]['entryid'], + 'parent_id' => 0, + 'timestamp' => $a['post_time'], + 'author' => $author, + 'email' => $mail, + 'url' => $url, + 'ip' => '', + 'status' => 'approved', + 'body' => $a['post_text'], + 'subscribed'=> 'false', + 'type' => 'NORMAL'); + + serendipity_db_insert('comments', $this->strtrRecursive($comment)); + $cid = serendipity_db_insert_id('comments', 'id'); + serendipity_approveComment($cid, $entries[$x]['entryid'], true); + } + } + + $serendipity['noautodiscovery'] = $noautodiscovery; + + // That was fun. + return true; + } +} + +return 'Serendipity_Import_smf'; + +/* vim: set sts=4 ts=4 expandtab : */