如何使用node_save创建节点?

时间:2011-07-28 17:30:02

标签: php drupal drupal-7 drupal-modules

我正在尝试将当前的html网站迁移到drupal。我有超过80,000页我必须迁移,所以我想,而不是坐在电脑前面50年我会创建一个模块。我能够创建一个从每个目录中提取html的脚本,现在我到了一个需要创建节点的路障。我正在尝试使用node_save()创建一个新节点,但是当执行node_save时,我尝试了一切PDOException错误。我传入$ node,这是一个数组,然后被转换为一个对象。

  

PDOException:在field_sql_storage_field_storage_write()中(/srv/www/htdocs/modules/field/modules/field_sql_storage/field_sql_storage.module的第424行)。

这是我们当前创建节点的方式,但它会产生错误:

$node= array(
    'uid' => $user->uid,
    'name' => $user->name,
    'type' => 'page',
    'language' => LANGUAGE_NONE,
    'title' => $html['title'],
    'status' => 1,
    'promote' => 0,
    'sticky' => 0,
    'created' => (int)REQUEST_TIME,
    'revision' => 0,
    'comment' => '1',
    'menu' => array(
        'enabled' => 0,
        'mlid' => 0,
        'module' => 'menu',
        'hidden' => 0,
        'has_children' => 0,
        'customized' => 0,
        'options' => array(),
        'expanded' => 0,
        'parent_depth_limit' => 8,
        'link_title' => '',
        'description' => '',
        'parent' => 'main-menu:0',
        'weight' => '0',
        'plid' => '0',
        'menu_name' => 'main-menu',
    ),
    'path' => array(
        'alias' => '',
        'pid' => null,
        'source' => null,
        'language' => LANGUAGE_NONE,
        'pathauto' => 1,
    ),
    'nid' => null,
    'vid' => null,
    'changed' => '',
    'additional_settings__active_tab' => 'edit-menu',
    'log' => '',
    'date' => '',
    'submit' => 'Save',
    'preview' => 'Preview',
    'private' => 0,
    'op' => 'Save',
    'body' => array(LANGUAGE_NONE => array(
        array(
            'value' => $html['html'],
            'summary' => $link,
            'format' => 'full_html',
        ),
    )),
        'validated' => true,
);

node_save((object)$node);

// Small hack to link revisions to our test user.
db_update('node_revision')
    ->fields(array('uid' => $node->uid))
    ->condition('vid', $node->vid)
    ->execute();

4 个答案:

答案 0 :(得分:2)

通常我会在文档根目录中创建一个bulkimport.php脚本来执行此类操作。

以下是我用于Drupal 7的代码:

<?php

define('DRUPAL_ROOT', getcwd());

include_once './includes/bootstrap.inc';
drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL);



function _create_node($title="", $body="", $language="und") {

  $node = (object)array();

  $node->uid      = '1';
  $node->name     = 'admin';

  $node->type     = 'page';

  $node->status   = 1;
  $node->promote  = 0;
  $node->sticky   = 0;
  $node->revision = 1;
  $node->language = $language;

  $node->title    = $title;
  $node->body[$language][0] = array(
    'value'  => $body,
    'format' => 'full_html',
    );

  $node->teaser   = '';
  $node->log      = 'Auto Imported Node';

  node_submit($node); 
  node_save($node);

  return $node;

  } ### function _create_node

$sith = array(
  'Darth Vader'    => 'Master: Darth Sidious',
  'Darth Sidious'  => 'Master: Darth Plagous',
  'Darth Maul'     => 'Master: Darth Sidious',
  'Darth Tyranous' => 'Master: Darth Sidious',
  );

foreach($sith as $title=>$body) {
  print "Creating Node. Title:[".$title."] \tBody:[".$body."] ";
  $node = _create_node($title, $body);
  print "\t... Created Node ID: [".$node->nid."]\n";
  #print_r($node);
  } ### foreach

答案 1 :(得分:1)

我收到与原始帖子完全相同的错误 -    PDOException:在field_sql_storage_field_storage_write()中 - 等等。

我已经在使用上面评论中显示的stdClass代码样式了。

问题原来是我分配给Body字段的字符串中的英镑符号和重音符号;字符串来自Windows文本文件。

将字符串转换为Drupal目标编码(UTF-8)对我有用:

$cleaned_string = mb_convert_encoding($html['html'], "UTF-8", "Windows-1252");
$node->body[LANGUAGE_NONE][0]['value'] = $cleaned_string;
$node->body[LANGUAGE_NONE][0]['format'] = 'plain_text';
node_save($node);

希望这有助于某人。

答案 2 :(得分:0)

您使用的是某些CMS引擎,还是自定义编写的网站? 在第一种情况下,请看这里http://drupal.org/documentation/migrate 我强烈建议您查看给定的模块,他们应该提供帮助。另外,作为选项,迁移数据库。

答案 3 :(得分:0)

您不需要很多空白字段。此外,您可以将节点转换为对象而不是转换为对象的数组。

您的代码应该可以使用这么短的代码段来完成:

    $node = new stdClass();
    $node->title = $html['title'];
    $node->type = 'page';
    $node->body['und'][0]['value'] = $html['html'];
    node_save($node);

此外,还有许多方法可以将节点大量导入Drupal - 我是Feeds模块的粉丝(http://drupal.org/project/feeds)。这可能需要编写一种将现有内容导出为中间格式(CSV或XML)的方法,但它可靠地工作,您可以在需要时重新导入节点以更新内容。