Programowo twórz węzły

34

Jak mogę programowo tworzyć węzły z polami daty i obrazu?

Wiem, że mogę to zrobić w Drupal 7 za pomocą następującego kodu.

global $user;

  $node = new stdClass();
  $node->title = "YOUR TITLE";
  $node->type = "YOUR_NODE_TYPE";
  node_object_prepare($node); // Sets some defaults. Invokes hook_prepare() and hook_node_prepare().
  $node->language = LANGUAGE_NONE; // Or e.g. 'en' if locale is enabled
  $node->uid = $user->uid; 
  $node->status = 1; //(1 or 0): published or not
  $node->promote = 0; //(1 or 0): promoted to front page
  //image field
  $existing_filepath = "/home/nzcodarnoc/sites/default/files/imported/picture.jpg"
  $new_filepath = "public://picture.jpg"
  // Create the file object
  $drupal_file = file_save_data(file_get_contents($existing_filepath), $new_filepath);
  $drupal_file->alt = $node->title;
  $drupal_file->title = $node->title;
  // Assign the file object to the node, as an array
  $node->field_my_file[$node->language][0] = get_object_vars($drupal_file);
  //date field
  $node->birth_date[LANGUAGE_NONE][0]['value'] = time();  
  $node = node_submit($node); // Prepare node for saving
  node_save($node);

Jaki jest równoważny kod dla Drupal 8?

Yusef
źródło
Sprawdź ten wątek drupal.org/node/178506
Aryashree Pritikrishna
Węzeł :: create ($ node_data_array) -> save ()
Eyal
@Eyal proszę podać więcej szczegółów. To pytanie będzie w przyszłości zbyt często zadawane
Yusef

Odpowiedzi:

56

Poniższy kod pomoże ci zapisać obraz w nowym węźle.

use \Drupal\node\Entity\Node;
use \Drupal\file\Entity\File;

// Create file object from remote URL.
$data = file_get_contents('https://www.drupal.org/files/druplicon.small_.png');
$file = file_save_data($data, 'public://druplicon.png', FILE_EXISTS_REPLACE);

// Create node object with attached file.
$node = Node::create([
  'type'        => 'article',
  'title'       => 'Druplicon test',
  'field_image' => [
    'target_id' => $file->id(),
    'alt' => 'Hello world',
    'title' => 'Goodbye world'
  ],
]);
$node->save();

Aby uzyskać więcej informacji, zobacz http://realityloop.com/blog/2015/10/08/programmatically-attach-files-node-drupal-8 .

amitgoyal
źródło
W tym konkretnym przykładzie nie potrzebujemy \ Drupal \ file \ Entity \ File, ponieważ bezpośrednio pobieramy plik obrazu z Internetu. Ale jeśli zobaczysz ten link realityloop.com/blog/2015/10/08/… , tam znajdziesz przykłady użycia encji pliku, // Utwórz obiekt pliku z lokalnie skopiowanego pliku. $ uri = file_unmanaged_copy ('public: //source.jpg', 'public: //destination.jpg', FILE_EXISTS_REPLACE); $ file = Plik :: Utwórz (['uri' => $ uri,]); $ file-> save ();
amitgoyal
Przykładowy obraz nie istnieje. Ten robi: drupal.org/files/druplicon-small.png
Kari
13

W drupal 8 byty są obiektami i jako takie, stworzenie bytu jest stworzeniem wystąpienia klasy typu bytu. Jeśli znasz klasę jednostki, możesz użyć nowego słowa kluczowego lub funkcji tworzenia.

IE $foo = new Foo();lub$foo = Foo::create();

Jeśli nie znasz klasy encji (tylko nazwa komputera), możesz użyć żądania klasy Storage w następujący sposób: \Drupal::entityTypeManager()->getStorage($entity_type_id)->create();

Aby wypełnić pola encji, możesz użyć $entity->set($key, $value)metody na obiekcie encji lub przekazać key=>valuetablicę do konstruktora encji. Takie jak:

$foo = new Foo([
  'name'=>'bar',
  'baz'=> TRUE,
  'multi_value' => [
    'first',
    'second',
    'third',
  ]
]);

Aby zapisać encję, wystarczy wywołać $entity->save()metodę na obiekcie encji.

Ponieważ pliki w Drupal 8 są również encjami, musisz podać jako identyfikator identyfikator encji pliku lub rzeczywistą encję pliku.

$file_1 = File::load(1);
$foo->set('bar_files', [
  $file_1,
  2
]);

Oto kod dla konkretnego scenariusza:

$node_entity_type = \Drupal::entityTypeManager()->getDefinition('node');
// The [file_save_upload][1] function returns an array of all the files that were saved.
$poster_images = file_save_upload($upload_name, $validators, $destination);
$node = new Node([
  $node_entity_type->getKey('bundle') => 'movie',
  $node_entity_type->getKey('label') => 'Foo',
  'field_release_date' => '1/1/2015',
  'field_poster_image' => $poster_images,
]);
$node->save();
Eyal
źródło
Chcę dodać jedno pole obrazu i jedno pole daty, podaj odpowiedź z tymi typami pól.
Yusef
Ale jak programowo wypełniać pola tekstowe w Drupal 8 w momencie tworzenia węzła?
WM
Dane w $ node_data są mapowane bezpośrednio na pola węzłów. Jeśli chcesz dodać tekst do pola o nazwie field_body, po prostu dodaj kolejny wpis za pomocą klucza field_body.
Eyal
Zaktualizowałem odpowiedź o więcej szczegółów. Zapraszamy.
Eyal
1
Zaktualizowałem moją odpowiedź
Eyal
12

Myślę, że ten obiektowy sposób jest wygodniejszy, prawda?

use Drupal\node\Entity\Node;

$my_article = Node::create(['type' => 'article']);
$my_article->set('title', 'My article');
$my_article->set('field_text', 'My text');
$my_article->set('field_image', FID);
$my_article->set('field_user', UID);
$my_article->enforceIsNew();
$my_article->save();
Eugene
źródło
7

Jeśli chcesz to zrobić w najczystszy sposób (testowalny), skorzystaj z entity_type.managerusługi:

$storage = $this->entityTypeManager->getStorage($entity_type_id);
$my_entity = $storage->create([
   ....
]);

Problem z Node::createfunkcją, że jest to wywołanie statyczne i dlatego tak naprawdę nie możesz już testować jednostkowo swojej klasy. Unikaj wykonywania połączeń statycznych, gdy tylko jest to możliwe. Uczyni to twój kod bardziej czytelnym (ponieważ zależności będą jasne).

ssibal
źródło
3

Innym sposobem utworzenia węzła z obrazem jest:

use \Drupal\file\Entity\File;

// Create file object from remote URL.
$data = file_get_contents('https://www.drupal.org/files/druplicon.small_.png');
$file = file_save_data($data, 'public://druplicon.png', FILE_EXISTS_REPLACE);

$node = \Drupal::entityTypeManager()->getStorage('node')->create(array(
  'type'        => 'article',
  'title'       => 'Druplicon test',
  'field_image' => [
    'target_id' => $file->id(),
    'alt' => 'Hello world',
    'title' => 'Goodbye world'
  ],
));
$node->save();
JHONATAN DAVID FERNANDEZ ROSA
źródło
2

Poniższy kod działa dla mnie

use \Drupal\node\Entity\Node;
use \Drupal\file\Entity\File;

$node = entity_create('node', array(
'type' => 'article',
'title' => $form_state->getValue('title'),
'body' => array(
'value' => $form_state->getValue('body'),
'format' => 'basic_html',
),
'uid' => $uid,
));
$node->save();
visabhishek
źródło
1
entity_create jest przestarzałe
Eyal
Jest również $form_statedostępny tylko w określonych kontekstach; w przeciwnym razie nie będziesz mieć do niego dostępu.
kiamlaluno
0
use Drupal\Core\Language\Language;


$definition = \Drupal::entityTypeManager()->getDefinition('node');
$values = [
    $definition->getKey('bundle') => 'basic_page',
    'langcode'                    => Language::LANGCODE_NOT_SPECIFIED,
    'title'                       => '...',
];
$entity = \Drupal::entityTypeManager()->getStorage('node')->create($values);
Sándor Juhász
źródło