开发者

Create node programmatically with cck location field

I try to programmatically create a node of custom contenttype "location" in Drupal 6, with the node containing a location field (http://drupal.org/project/location) called "location" (yes I know, the nomenclature could be better, but I am just experimenting on this at the moment).

Creating the node works just fine, but I cannot find a way to set the contents for the location field - i.e. the node is created with all content but the value for then location field.

I try creating the node like this:

        $newNo开发者_如何转开发de = (object) NULL;
        $newNode->type = 'location';
        $newNode->title = $locationName;
        $newNode->uid = $userId;
        $newNode->created = strtotime("now");
        $newNode->changed = strtotime("now");
        $newNode->status = 1;
        $newNode->comment = 0;
        $newNode->promote = 0;
        $newNode->moderate = 0;
        $newNode->sticky = 0;

        $newNode->field_location[0]['street'] = 'Teststraße';
        $newNode->field_location[0]['postal_code'] = '12345'; 
        $newNode->field_location[0]['city'] = 'Musterstadt'; 

        node_save($newNode);

The node gets created with the correct title, but the location fields remain unset.

How can I programmatically set the location-related fields?

Thanks in advance!


Wanted to add this as a comment, but it seems like putting code into the comment is rather problematic. So here we go: I changed the internas so that I do not use a cck field anymore, but use the default location option as suggested by googletorp.

The actual code to create a new location and assign this to a new node looks like this:

$location['street'] = "myStreet";
$location['postal_code'] = "12345";
...

$newLocationId = location_save($location);

$newNode = ...
$newNode->locations[0]['lid'] = $newLocationId;

node_save($newNode);

Thanks for the guidance :)


Instead of node_save, many people recommend using drupal_execute to programmatically submit the node edit form. This gives you the benefit of form validation.

See http://thedrupalblog.com/programmatically-create-any-node-type-using-drupal-execute for an excellent example of using drupal_execute. Don't forget to look at the comment http://thedrupalblog.com/programmatically-create-any-node-type-using-drupal-execute#comment-70 to see some additional info on CCK fields.

The advantage of drupal_execute is that you get form validation also. So after the drupal_executestatement you can see if there were any errors using form_get_errors ( http://api.drupal.org/api/function/form_get_errors/6 ). See snippet (pasted below) from http://civicactions.com/blog/cck_import_and_update for an example of using form_get_errors

$node->type = 'yourtype';
$values = array();
$values[...] = ...;
drupal_execute('yourtype_node_form', $values, $node);
$errors = form_get_errors();
if (count($errors)) {
  // do something ...
}

Another very nice resource on programmatic submission of nodes using drupal_execute can be found at http://drupal.org/node/293663


I have done this, only not with a CCK field but the default location option you can add to nodes.

What I did to make it work, was to first save the location (there's an API function for it) and then add the location id from the saved location.

Sample code:

Note, $center is from an external source, so it's not Drupal related. I know all my locations are from Denmark in my example, so that part is just hardcoded.

When you don't use a CCK field, you don't need to save the location data on the node, instead you can just save the location and pair the location yourself. It's a quick solution, instead of running through the node form like suggested. For complex nodes, that might be the better choice, but when it's simple, this is done faster.

// Update the location data.
$location = is_array($node->location) ? $node->location : array();
$location += array(
  'street' => $center->address->address2,
  'city' => $center->address->zipName,
  'postal_code' => $center->address->zip,
  'country' => 'dk',
  'country_name' => 'Denmark',
);
location_save($location);

// Insert location instance, if it's not set yet.
$criteria = array(
  ':nid' => $node->nid,
  ':vid' => $node->vid,
  ':lid' => $location['lid'],
);
if (!db_result(db_query("SELECT COUNT(*) FROM {location_instance} WHERE nid = %d AND vid = %d AND lid = %d;", $criteria))) {
  db_query("INSERT INTO {location_instance} (nid, vid, lid) VALUES (%d, %d, %d)", $criteria);
}


For Drupal 7, saving as default location tab.

$location = array(
  'latitude' => $row->gmapycord,
  'longitude' => $row->gmapxcord,
);
$lid = location_save($location);
if ($lid) {
  $entity->locations['0']['lid'] = $lid;
}

Inspired from: here

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜