/** * */ public function fixPostContentURLs() { $this->logFunctionStart(__FUNCTION__, func_get_args()); // Get assets $fileOldURLtoNewURL = array(); $fileOldURLtoID = array(); $files = $this->applyWordpressFilter(File::get()); foreach ($files as $record) { // ie. 'assets/WordpressUploads/2014/12/1.jpg' // or 'assets/WordpressUploads/2014/12/01235537/1.jpg' $filename = $record->Filename; $filename = WordpressAttachmentFileResolver::extract_all_after_year($filename); $relativeLink = ltrim($this->getAssetURL($record), '/'); $fileOldURLtoNewURL[$filename] = $relativeLink; $fileOldURLtoID[$filename] = $record->ID; // If AmazonS3 style: '2014/12/01235537/1.jpg' $dirParts = explode('/', $filename); if (isset($dirParts[3])) { // Transform '2014/12/01235537/1.jpg' // to: '2014/12/1.jpg' // This handles the edge cases where Wordpress references how the assets // were stored, pre-AmazonS3 migration. unset($dirParts[2]); $filename = implode('/', $dirParts); $fileOldURLtoNewURL[$filename] = $relativeLink; $fileOldURLtoID[$filename] = $record->ID; } } // todo(Jake): Allow for setting a manual siteurl with configs that takes precedence // over this. Wordpress allows such behaviour with its define() configs. $wordpressSiteURL = $this->getOption('siteurl'); if (!$wordpressSiteURL) { throw new Exception('Unable to determine "siteurl" from options table or config.'); } // $existingWpRecords = $this->applyWordpressFilter(Page::get()); foreach ($existingWpRecords as $record) { $content = $this->getContentFromRecord($record); if (!$content) { continue; } $newContent = WordpressUtility::modify_html_attributes($content, function (&$attributes) use($record, $fileOldURLtoNewURL, $fileOldURLtoID, $wordpressSiteURL) { /** * @var $htmlAttr WordpressHTMLAttribute */ foreach ($attributes as $key => $htmlAttr) { $attrName = $htmlAttr->name; $attrValue = $htmlAttr->value; $isAssetURL = false; if ($wordpressSiteURL && strpos($attrValue, $wordpressSiteURL) !== FALSE) { // Replace any 'www.mywordpress.com' href's with a shortcode $relativeLink = str_replace($wordpressSiteURL, '', $attrValue); $page = $this->getByLink($relativeLink); if ($page) { $htmlAttr->value = '[sitetree_link,id=' . $page->ID . ']'; //$this->log('Record #'.$record->ID.' - Mismatching URLSegment depth - Unable to make URL relative on attribute "'.$attrName.'": '.$attrValue, 'error', null, 1); } else { $filename = WordpressAttachmentFileResolver::extract_year_and_month($attrValue); if ($filename) { // If able to extract a year/month/etc, then it must be an asset $isAssetURL = true; } else { $this->log('Record #' . $record->ID . ' - Unable to make URL relative on attribute "' . $attrName . '": ' . $attrValue, 'error', null, 1); continue; } } } $isAssetURL = $isAssetURL || strpos($attrValue, '.amazonaws.com/') !== FALSE; if ($isAssetURL) { // Replace: // 'http://cdn.namespace.com.au.s3-ap-southeast-2.amazonaws.com/wp-content/uploads/2014/01/21090055/Read-the-transcript-here2.pdf' // With: // 'assets/WordpressUploads/2014/01/21090055/Read-the-transcript-here2.pdf' $dimensions = array(); $filename = WordpressAttachmentFileResolver::extract_all_after_year($attrValue, $dimensions); if (!isset($fileOldURLtoNewURL[$filename])) { // Handle edge case where user uploads a file with pattern 'myname-300x300.jpg' // Subsequent thumbnails in Wordpress save as: 'myname-600x900-300x200.jpg' $filename = WordpressAttachmentFileResolver::extract_all_after_year($attrValue); } if (!isset($fileOldURLtoNewURL[$filename]) || !isset($fileOldURLtoID[$filename])) { $this->log("Record #" . $record->ID . " - Cannot find asset in File table: " . $attrValue, 'error', null, 1); continue; } $relativeLink = $fileOldURLtoNewURL[$filename]; if ($htmlAttr->name === 'href') { // For 'href' links, put it into a format Silverstripe 3.2 will expect. $relativeLink = '[file_link,id=' . $fileOldURLtoID[$filename] . ']'; } if ($attrValue !== $relativeLink) { $htmlAttr->value = $relativeLink; } } else { if (strpos($attrValue, 'http') !== FALSE) { $this->log('Record #' . $record->ID . ' - Invalid URL, not found in sitetree or asset on attribute "' . $attrName . '": ' . $attrValue, 'error', null, 1); } } } }); if ($content !== $newContent) { try { $calledWriteAlready = $this->setContentOnRecord($record, $newContent); if (!$calledWriteAlready) { $isPublished = isset($wpData['post_status']) && $wpData['post_status'] === 'publish' || $record->isPublished(); $this->writeAndPublishRecord($record, $isPublished); } } catch (Exception $e) { $this->log($record, 'error', $e); } } else { $this->log($record, 'nochange'); } } $this->logFunctionEnd(__FUNCTION__); }
public function onBeforeWrite() { if (Config::inst()->get(__CLASS__, 'disable_write_check')) { return; } $this->owner->WordpressWasLastWriteImporter = 0; if (self::$throw_error_if_blank_wordpress_data === null) { $controller = Controller::has_curr() ? Controller::curr() : null; if ($controller && ($controller instanceof DatabaseAdmin || $controller instanceof TestRunner)) { // Don't throw error if creating records in /dev/build self::$throw_error_if_blank_wordpress_data = false; } else { // Throw errors if executing from command line or TaskRunner self::$throw_error_if_blank_wordpress_data = Director::is_cli() || $controller instanceof TaskRunner; } } if ($this->owner instanceof Folder) { // Ignore Folder type as Wordpress doesn't have an equivalent return; } $wordpressData = $this->owner->getField('WordpressData'); if (self::$throw_error_if_blank_wordpress_data && !$wordpressData) { throw new Exception('Attempted to write record without WordpressData.'); } // Only run this code if an external source set "WordpressData" to an array. // This avoids this executing for an existing record that will just see WordpressData as a json-encoded array (string) if ($wordpressData && is_array($wordpressData)) { $this->owner->WordpressWasLastWriteImporter = 1; if ($wordpressData === true || $wordpressData === 1) { // Use true/1 to to hint it was created/changed in an import context but it // doesn't have any actual data attached to it. $this->owner->WordpressData = '1'; } else { $wordpressTable = isset($wordpressData[WordpressDatabase::HINT]['table']) ? $wordpressData[WordpressDatabase::HINT]['table'] : null; if ($wordpressTable) { $this->owner->WordpressTable = $wordpressTable; } // setWordpressID $wordpressID = null; if (isset($wordpressData['ID'])) { // Handle ID format for anything in wp_posts table. $wordpressID = $wordpressData['ID']; } else { if (isset($wordpressData['term_id'])) { // Handle ID format for anything in wp_terms table. $wordpressID = $wordpressData['term_id']; } else { if (isset($wordpressData['id'])) { // Handle ID format for Gravity Forms $wordpressID = $wordpressData['id']; } } } if ($wordpressID === null) { throw new Exception('Attempted to write record without setting WordpressID.'); } $this->owner->WordpressID = $wordpressID; $this->owner->WordpressParentID = isset($wordpressData['post_parent']) ? $wordpressData['post_parent'] : null; // encodeMeta $wordpressMetaData = isset($wordpressData[WordpressDatabase::HINT]['meta']) ? $wordpressData[WordpressDatabase::HINT]['meta'] : null; if ($wordpressMetaData && is_array($wordpressMetaData)) { $this->owner->WordpressMetaData = WordpressUtility::utf8_json_encode($wordpressMetaData); } // encodeData $wordpressData = $this->owner->WordpressData; if ($wordpressData && is_array($wordpressData)) { unset($wordpressData[WordpressDatabase::HINT]); // remove importer hints $this->owner->WordpressData = WordpressUtility::utf8_json_encode($wordpressData); if ($this->owner->WordpressData === false) { throw new WordpressImportException(WordpressUtility::json_last_error_msg()); } } } } }