PluginProbe
Import WP – CSV & XML Import Export for WordPress / 2.8.1
Import WP – CSV & XML Import Export for WordPress v2.8.1
2.15.1 2.15.0 2.14.24 2.14.23 2.7.0 2.7.1 2.7.10 2.7.11 2.7.12 2.7.13 2.7.14 2.7.2 2.7.3 2.7.4 2.7.5 2.7.6 2.7.7 2.7.8 2.7.9 2.8.0 2.8.1 2.8.2 2.8.3 2.9.0 2.9.1 All 144 releases
jc-importer / class / Common / Importer / Template / PostTemplate.php

PostTemplate.php in Import WP – CSV & XML Import Export for WordPress 2.8.1, at class/Common/Importer/Template/PostTemplate.php

1,031 lines 37.0 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace ImportWP\Common\Importer\Template;
4
5 use ImportWP\Common\Attachment\Attachment;
6 use ImportWP\Common\Filesystem\Filesystem;
7 use ImportWP\Common\Ftp\Ftp;
8 use ImportWP\Common\Importer\ParsedData;
9 use ImportWP\Common\Importer\TemplateInterface;
10 use ImportWP\Common\Model\ImporterModel;
11 use ImportWP\Common\Util\Logger;
12 use ImportWP\Container;
13 use ImportWP\EventHandler;
14
15 class PostTemplate extends Template implements TemplateInterface
16 {
17 protected $name = 'Post';
18 protected $mapper = 'post';
19 protected $field_map = [
20 'ID' => 'post.ID',
21 'post_title' => 'post.post_title',
22 'post_content' => 'post.post_content',
23 'post_excerpt' => 'post.post_excerpt',
24 'post_name' => 'post.post_name',
25 'post_status' => 'post.post_status',
26 'menu_order' => 'post.menu_order',
27 'post_password' => 'post.post_password',
28 'post_date' => 'post.post_date',
29 'comment_status' => 'post.comment_status',
30 'ping_status' => 'post.ping_status',
31 'post_parent' => 'post._parent.parent',
32 ];
33
34 protected $optional_fields = [
35 'ID',
36 'post_excerpt',
37 'post_name',
38 'post_status',
39 'menu_order',
40 'post_password',
41 'post_date',
42 'comment_status',
43 'ping_status'
44 ];
45
46 protected $_taxonomies = [];
47 protected $_attachments = [];
48
49 private $virtual_fields = [];
50
51 public function __construct(EventHandler $event_handler)
52 {
53 parent::__construct($event_handler);
54
55 $this->groups[] = 'post';
56 $this->groups[] = 'taxonomies';
57 $this->groups[] = 'attachments';
58
59 $this->default_template_options['post_type'] = 'post';
60
61 $this->field_options = array_merge($this->field_options, [
62 'post._parent.parent' => [$this, 'get_post_parent_options'],
63 'taxonomies.*.tax' => [$this, 'get_taxonomy_options'],
64 ]);
65 }
66
67 /**
68 * @param string $message
69 * @param int $id
70 * @param ParsedData $data
71 * @return $string
72 */
73 public function display_record_info($message, $id, $data)
74 {
75 $message = parent::display_record_info($message, $id, $data);
76
77 if (!empty($this->_taxonomies)) {
78 foreach ($this->_taxonomies as $tax => $terms) {
79 $message .= ', ' . $tax . ': (' . implode(', ', $terms) . ')';
80 }
81 }
82
83 if (!empty($this->_attachments)) {
84 $message .= ', Attachments: (' . implode(', ', $this->_attachments) . ')';
85 }
86
87 return $message;
88 }
89
90 public function register()
91 {
92 $groups = [];
93
94 // Post
95 $groups[] = $this->register_group('Post Fields', 'post', [
96 $this->register_field('ID', 'ID', [
97 'tooltip' => __('ID is only used to reference existing records', 'importwp')
98 ]),
99 $this->register_core_field('Title', 'post_title', [
100 'tooltip' => __('Title of the post.', 'importwp')
101 ]),
102 $this->register_core_field('Content', 'post_content', [
103 'tooltip' => __('Main WYSIWYG editor content of the post.', 'importwp')
104 ]),
105 $this->register_field('Excerpt', 'post_excerpt', [
106 'tooltip' => __('A custom short extract for the post.', 'importwp')
107 ]),
108 $this->register_field('Slug', 'post_name', [
109 'tooltip' => __('The slug is the user friendly and URL valid name of the post.', 'importwp')
110 ]),
111 $this->register_field('Status', 'post_status', [
112 'default' => 'publish',
113 'options' => [
114 ['value' => 'draft', 'label' => 'Draft'],
115 ['value' => 'publish', 'label' => 'Published'],
116 ['value' => 'pending', 'label' => 'Pending'],
117 ['value' => 'future', 'label' => 'Future'],
118 ['value' => 'private', 'label' => 'Private'],
119 ['value' => 'trash', 'label' => 'Trash']
120 ],
121 'tooltip' => __('Whether the post can accept comments. Accepts open or closed', 'importwp')
122 ]),
123 $this->register_group('Parent Settings', '_parent', [
124 $this->register_field('Parent', 'parent', [
125 'default' => '',
126 'options' => 'callback',
127 'tooltip' => __('Set this for the post it belongs to', 'importwp')
128 ]),
129 $this->register_field('Parent Field Type', '_parent_type', [
130 'default' => 'id',
131 'options' => [
132 ['value' => 'id', 'label' => 'ID'],
133 ['value' => 'slug', 'label' => 'Slug'],
134 ['value' => 'name', 'label' => 'Name'],
135 ['value' => 'column', 'label' => 'Reference Column'],
136 ],
137 'type' => 'select',
138 'tooltip' => __('Select how the parent field should be handled', 'importwp')
139 ]),
140 $this->register_field('Parent Reference Column', '_parent_ref', [
141 'condition' => ['_parent_type', '==', 'column'],
142 'tooltip' => __('Select the column/node that the parent field is referencing', 'importwp')
143 ])
144 ]),
145 $this->register_field('Order', 'menu_order', [
146 'tooltip' => __('The order the post should be displayed in', 'importwp')
147 ]),
148 $this->register_group('Author Settings', '_author', [
149 $this->register_field('Author', 'post_author', [
150 'tooltip' => __('The user of who added this post', 'importwp')
151 ]),
152 $this->register_field('Author Field Type', '_author_type', [
153 'default' => 'id',
154 'options' => [
155 ['value' => 'id', 'label' => 'ID'],
156 ['value' => 'login', 'label' => 'Login'],
157 ['value' => 'email', 'label' => 'Email'],
158 ],
159 'tooltip' => __('Select how the author field should be handled', 'importwp')
160 ])
161 ]),
162 $this->register_field('Password', 'post_password', [
163 'tooltip' => __('The password to access the post', 'importwp')
164 ]),
165 $this->register_field('Date', 'post_date', [
166 'tooltip' => __('The date of the post , enter in the format "YYYY-MM-DD HH:ii:ss"', 'importwp')
167 ]),
168 $this->register_field('Allow Comments', 'comment_status', [
169 'options' => [
170 ['value' => '0', 'label' => 'Disabled'],
171 ['value' => '1', 'label' => 'Enabled']
172 ],
173 'default' => '0',
174 'tooltip' => __('Whether the post can accept comments', 'importwp')
175 ]),
176 $this->register_field('Allow Pingbacks', 'ping_status', [
177 'options' => [
178 ['value' => 'closed', 'label' => 'Closed'],
179 ['value' => 'open', 'label' => 'Open']
180 ],
181 'default' => 'closed',
182 'tooltip' => __('Whether the post can accept pings', 'importwp')
183 ])
184 ]);
185
186 // Taxonomies
187 $groups[] = $this->register_taxonomy_fields();
188
189 // Attachments
190 $groups[] = $this->register_attachment_fields();
191
192 return $groups;
193 }
194
195 public function register_taxonomy_fields()
196 {
197 return $this->register_group('Taxonomies', 'taxonomies', [
198 $this->register_field('Taxonomy', 'tax', [
199 'default' => 'category',
200 'options' => 'callback',
201 'tooltip' => __('Select the type of taxonomy you are importing to.', 'importwp')
202 ]),
203 $this->register_field('Terms', 'term', [
204 'tooltip' => __('Name of the taxonomy term or terms (entered as a comma seperated list).', 'importwp')
205 ]),
206 $this->register_group('Settings', 'settings', [
207 $this->register_field('Delimiter', '_delimiter', [
208 'type' => 'text',
209 'tooltip' => 'A single character used to seperate terms when listing multiple, Leave empty to use default: ,'
210 ]),
211 $this->register_field('Term Type', '_type', [
212 'tooltip' => 'Select what type the term values are (e.g. Name, Slug, or ID)',
213 'default' => 'name',
214 'options' => [
215 ['value' => 'name', 'label' => 'Name'],
216 ['value' => 'slug', 'label' => 'Slug'],
217 ['value' => 'term_id', 'label' => 'ID'],
218 ],
219 'type' => 'select'
220 ]),
221 $this->register_field('Enable Hierarchy', '_hierarchy', [
222 'default' => 'no',
223 'options' => [
224 ['value' => 'no', 'label' => 'No'],
225 ['value' => 'yes', 'label' => 'Yes'],
226 ],
227 'type' => 'select'
228 ]),
229 $this->register_field('Hierarchy Character', '_hierarchy_character', [
230 'default' => '>',
231 'condition' => ['_hierarchy', '==', 'yes'],
232 ]),
233 $this->register_field('Append Terms', '_append', [
234 'default' => 'no',
235 'options' => [
236 ['value' => 'no', 'label' => 'No'],
237 ['value' => 'yes', 'label' => 'Yes'],
238 ],
239 'type' => 'select'
240 ]),
241 ], ['type' => 'settings'])
242 ], ['type' => 'repeatable', 'row_base' => true]);
243 }
244
245 public function register_settings()
246 {
247 }
248
249 public function register_options()
250 {
251 return [];
252 }
253
254 /**
255 * Alter fields before they are parsed
256 *
257 * @param array $fields
258 * @return array
259 */
260 public function field_map($fields)
261 {
262 if ($this->importer->isEnabledField('post._parent') && $fields['post._parent._parent_type'] === 'column' && !empty($fields["post._parent._parent_ref"])) {
263 $fields['_iwp_ref_post_parent'] = $fields["post._parent._parent_ref"];
264 $this->virtual_fields[] = '_iwp_ref_post_parent';
265 }
266 return $fields;
267 }
268
269 /**
270 * Process data before record is importer.
271 *
272 * Alter data that is passed to the mapper.
273 *
274 * @param ParsedData $data
275 * @return ParsedData
276 */
277 public function pre_process(ParsedData $data)
278 {
279 $data = parent::pre_process($data);
280
281 $post_field_map = [];
282 foreach ($this->field_map as $field_id => $field_map_key) {
283 $post_field_map[$field_id] = $data->getValue($field_map_key);
284 }
285
286 // remove fields that have not been set
287 foreach ($post_field_map as $field_key => $field_map) {
288
289 if ($field_map === false) {
290 unset($post_field_map[$field_key]);
291 continue;
292 }
293 }
294
295 foreach ($this->optional_fields as $optional_field) {
296 if (true !== $this->importer->isEnabledField('post.' . $optional_field)) {
297 unset($post_field_map[$optional_field]);
298 }
299 }
300
301 if (isset($post_field_map['post_date'])) {
302 $post_field_map['post_date_gmt'] = get_gmt_from_date($post_field_map['post_date']);
303 }
304
305 if (true !== $this->importer->isEnabledField('post._parent')) {
306 unset($post_field_map['post_parent']);
307 }
308
309 if (true !== $this->importer->isEnabledField('post._author')) {
310 unset($post_field_map['post_author']);
311 }
312
313 if (!empty($this->virtual_fields)) {
314 foreach ($this->virtual_fields as $virtual_field) {
315 $value = $data->getValue($virtual_field);
316 if (false !== $value) {
317 $post_field_map[$virtual_field] = $value;
318 }
319 }
320 }
321
322 if ($this->importer->isEnabledField('post._author')) {
323 $post_author = $data->getValue('post._author.post_author');
324 $post_author_type = $data->getValue('post._author._author_type');
325
326 $user_id = 0;
327
328 if ($post_author_type === 'id') {
329
330 $user = get_user_by('ID', $post_author);
331 if ($user) {
332 $user_id = intval($user->ID);
333 }
334 } elseif ($post_author_type === 'login') {
335
336 $user = get_user_by('login', $post_author);
337 if ($user) {
338 $user_id = intval($user->ID);
339 }
340 } elseif ($post_author_type === 'email') {
341
342 $user = get_user_by('email', $post_author);
343 if ($user) {
344 $user_id = intval($user->ID);
345 }
346 }
347
348 if ($user_id > 0) {
349 $post_field_map['post_author'] = $user_id;
350 } else {
351 $post_field_map['post_author'] = '';
352 }
353 }
354
355 // post_name is a unique field, so generate slug from title if no slug present
356 // if (!isset($post_field_map['post_name']) || empty($post_field_map['post_name'])) {
357 // $post_field_map['post_name'] = sanitize_title($post_field_map['post_title']);
358
359 // // set flag to say slug has been generated
360 // $data->add(['post_name' => 'yes'], '_generated');
361 // }
362
363 if ($this->importer->isEnabledField('post._parent') && isset($post_field_map['post_parent'])) {
364
365 $parent_id = 0;
366 $parent_field_type = $data->getValue('post._parent._parent_type');
367
368 if ($parent_field_type === 'name' || $parent_field_type === 'slug') {
369
370 // name or slug
371 $page = get_posts(array('name' => sanitize_title($post_field_map['post_parent']), 'post_type' => $this->importer->getSetting('post_type')));
372 if ($page) {
373 $parent_id = intval($page[0]->ID);
374 }
375 } elseif ($parent_field_type === 'id') {
376
377 // ID
378 $parent_id = intval($post_field_map['post_parent']);
379 } elseif ($parent_field_type === 'column') {
380
381 // reference column
382 $temp_id = $this->get_post_by_cf('post_parent', $post_field_map['post_parent']);
383 if (intval($temp_id > 0)) {
384 $parent_id = intval($temp_id);
385 }
386 }
387
388 if ($parent_id > 0) {
389 $post_field_map['post_parent'] = $parent_id;
390 }
391 }
392
393 foreach ($post_field_map as $key => $value) {
394 $post_field_map[$key] = apply_filters('iwp/template/process_field', $value, $key, $this->importer);
395 }
396
397 $data->replace($post_field_map, 'default');
398
399 return $data;
400 }
401
402 /**
403 * Find existing post/page/custom by reference field
404 *
405 * @param string $field Reference Field Name
406 * @param string $value Value to check against reference
407 *
408 * @return bool
409 */
410 public function get_post_by_cf($field, $value)
411 {
412
413 $query = new \WP_Query(array(
414 'post_type' => $this->importer->getSetting('post_type'),
415 'posts_per_page' => 1,
416 'fields' => 'ids',
417 'cache_results' => false,
418 'update_post_meta_cache' => false,
419 'meta_query' => array(
420 array(
421 'key' => '_iwp_ref_' . $field,
422 'value' => $value
423 )
424 ),
425 'post_status' => 'any'
426 ));
427 if ($query->have_posts()) {
428 return $query->posts[0];
429 }
430 return false;
431 }
432
433 /**
434 * Process data after record is importer.
435 *
436 * Use data that is returned from the mapper.
437 *
438 * @param int $post_id
439 * @param ParsedData $data
440 * @return void
441 */
442 public function post_process($post_id, ParsedData $data)
443 {
444 /**
445 * @var Filesystem $filesystem
446 */
447 $filesystem = Container::getInstance()->get('filesystem');
448
449 /**
450 * @var Ftp $ftp
451 */
452 $ftp = Container::getInstance()->get('ftp');
453
454 /**
455 * @var Attachment $attachment
456 */
457 $attachment = Container::getInstance()->get('attachment');
458
459 $this->featured_set = false;
460 $this->process_taxonomies($post_id, $data);
461 $this->process_attachments($post_id, $data, $filesystem, $ftp, $attachment);
462
463 parent::post_process($post_id, $data);
464 }
465
466 /**
467 * Process taxonomy group
468 *
469 * TODO: Possibly move this into parser?
470 *
471 * @param int $post_id
472 * @param ParsedData $data
473 * @return void
474 */
475 public function process_taxonomies($post_id, $data)
476 {
477 // reset list of taxonomies
478 $this->_taxonomies = [];
479
480 $group = 'taxonomies';
481 $taxonomes_data = $data->getData($group);
482 $total_rows = isset($taxonomes_data[$group . '._index']) ? intval($taxonomes_data[$group . '._index']) : 0;
483 $base_delimiter = apply_filters('iwp/value_delimiter', ',');
484 $base_delimiter = apply_filters('iwp/taxonomy/value_delimiter', $base_delimiter);
485
486 $processed_taxonomies = [];
487 $term_hierarchy = [];
488 $term_hierarchy_enabled = [];
489 $term_types = [];
490 $term_append = [];
491
492 // Pre-Process taxonomy data
493 for ($i = 0; $i < $total_rows; $i++) {
494
495 $prefix = $group . '.' . $i . '.';
496
497 $sub_rows = [$taxonomes_data];
498 if (isset($taxonomes_data[$prefix . 'row_base']) && !empty($taxonomes_data[$prefix . 'row_base'])) {
499 $sub_group_id = $group . '.' . $i;
500 $sub_rows = $data->getData($sub_group_id);
501 }
502
503 foreach ($sub_rows as $row) {
504 $tax = isset($row[$prefix . 'tax']) ? $row[$prefix . 'tax'] : null;
505 $terms = isset($row[$prefix . 'term']) ? $row[$prefix . 'term'] : null;
506
507 $term_append[$tax] = isset($row[$prefix . 'settings._append']) && $row[$prefix . 'settings._append'] == 'yes';
508
509 $delimiter = apply_filters('iwp/taxonomy=' . $tax . '/value_delimiter', $base_delimiter);
510
511 $term_types[$tax] = isset($row[$prefix . 'settings._type']) && !empty($row[$prefix . 'settings._type']) ? $row[$prefix . 'settings._type'] : 'name';
512
513 $hierarchy_enabled = isset($row[$prefix . 'settings._hierarchy']) && $row[$prefix . 'settings._hierarchy'] === 'yes' ? true : false;
514 $hierarchy_character = isset($row[$prefix . 'settings._hierarchy_character']) ? $row[$prefix . 'settings._hierarchy_character'] : null;
515
516 $delimiter = isset($row[$prefix . 'settings._delimiter']) && strlen(trim($row[$prefix . 'settings._delimiter'])) === 1 ? trim($row[$prefix . 'settings._delimiter']) : $delimiter;
517
518 if (empty($hierarchy_character)) {
519 $hierarchy_enabled = false;
520 }
521
522 if (!is_null($tax) && !is_null($terms)) {
523 $terms = explode($delimiter, $terms);
524 foreach ($terms as $term) {
525
526 $term = trim($term);
527 $permission_key = 'taxonomy.' . $tax; //taxonomy.category | taxonomy.post_tag
528
529 if ($data->permission()) {
530 $allowed = $data->permission()->validate([$permission_key => ''], $data->getMethod(), $group);
531 $is_allowed = isset($allowed[$permission_key]) ? true : false;
532
533 if (!$is_allowed || empty($term)) {
534 continue;
535 }
536 }
537
538 // handle taxonomies
539 if (!isset($processed_taxonomies[$tax])) {
540 $processed_taxonomies[$tax] = [];
541 }
542
543 $processed_taxonomies[$tax][] = $term;
544
545 // Handle hierarchy
546 if (!isset($term_hierarchy[$tax])) {
547 $term_hierarchy[$tax] = [];
548 }
549
550 if ($hierarchy_enabled) {
551 $hierarchy_parts = explode($hierarchy_character, $term);
552 if (count($hierarchy_parts) > 0) {
553 $hierarchy_parts = array_filter(array_map('trim', $hierarchy_parts));
554 $term_hierarchy[$tax][] = $hierarchy_parts;
555 $term_hierarchy_enabled[$tax] = true;
556 }
557 } else {
558 $term_hierarchy[$tax][] = [$term];
559 }
560 }
561 }
562 }
563 }
564
565 // TODO: Process term hierarchy
566 foreach ($term_hierarchy as $processed_tax => $term_hierarchy_list) {
567
568 // clear existing taxonomies
569 if (!isset($term_append[$processed_tax]) || !$term_append[$processed_tax]) {
570 wp_set_object_terms($post_id, null, $processed_tax);
571 }
572
573 if (empty($term_hierarchy_list)) {
574 continue;
575 }
576
577 foreach ($term_hierarchy_list as $hierarchy_list) {
578
579 $prev_term = isset($term_hierarchy_enabled[$processed_tax]) ? 0 : null;
580 $type = $term_types[$processed_tax];
581
582 foreach ($hierarchy_list as $term) {
583 if (!isset($this->_taxonomies[$processed_tax])) {
584 $this->_taxonomies[$processed_tax] = [];
585 }
586
587 $term_result = $this->create_or_get_taxonomy_term($post_id, $processed_tax, $term, $prev_term, $type);
588 if ($term_result) {
589 $prev_term = $term_result->term_id;
590 $this->_taxonomies[$processed_tax][] = $term_result->name;
591 }
592 }
593 }
594 }
595 }
596
597 private function create_or_get_taxonomy_term($post_id, $tax, $term, $parent, $term_type = 'name')
598 {
599 if (!in_array($term_type, ['slug', 'name', 'term_id'])) {
600 $term_type = 'name';
601 }
602
603 if (is_null($parent)) {
604
605 // we do not care about parent, just fetch first
606 $tmp_term = get_term_by($term_type, $term, $tax);
607 if ($tmp_term) {
608 wp_set_object_terms($post_id, $tmp_term->term_id, $tax, true);
609 return $tmp_term;
610 }
611 } else {
612
613 if ($term_type === 'slug') {
614
615 $terms = get_terms([
616 'taxonomy' => $tax,
617 'slug' => $term,
618 'hide_empty' => false
619 ]);
620 } elseif ($term_type === 'term_id') {
621
622 // ID will only return a single record
623 $terms = [];
624 $tmp_term = get_term_by($term_type, $term, $tax);
625 if ($tmp_term) {
626 $terms[] = $tmp_term;
627 }
628 } else {
629
630 $terms = get_terms([
631 'taxonomy' => $tax,
632 'name' => $term,
633 'hide_empty' => false
634 ]);
635 }
636
637 if (!empty($terms)) {
638 foreach ($terms as $tmp_term) {
639 if (intval($tmp_term->parent) === intval($parent)) {
640
641 // attach term to post
642 wp_set_object_terms($post_id, $tmp_term->term_id, $tax, true);
643 return $tmp_term;
644 }
645 }
646 }
647 }
648
649 // should not create new term since we are using the term_id
650 if ($term_type === 'term_id') {
651 return false;
652 }
653
654 // add term
655 $term_id = wp_insert_term($term, $tax, ['parent' => $parent]);
656 if (!is_wp_error($term_id)) {
657 wp_set_object_terms($post_id, $term_id['term_id'], $tax, true);
658 return get_term($term_id['term_id'], $tax);
659 }
660
661 return false;
662 }
663
664 /**
665 * Process attachments group
666 *
667 * TODO: Possibly move this into parser?
668 *
669 * @param int $post_id
670 * @param ParsedData $data
671 * @param Filesystem $filesystem
672 * @param FTP $ftp
673 * @param Attachment $attachment
674 * @return void
675 */
676 public function process_attachments($post_id, $data, $filesystem, $ftp, $attachment, $group = 'attachments')
677 {
678 // reset list of attachments
679 $this->_attachments = [];
680 $attachment_ids = [];
681
682 $attachment_data = $data->getData($group);
683 $total_rows = isset($attachment_data[$group . '._index']) ? intval($attachment_data[$group . '._index']) : 0;
684 $skipped = 0;
685
686 for ($i = 0; $i < $total_rows; $i++) {
687
688 $permission_key = $group . '.' . $i; //attachment.0 | attachment.1
689 if ($data->permission()) {
690 $allowed = $data->permission()->validate([$permission_key => ''], $data->getMethod(), $group);
691 $is_allowed = isset($allowed[$permission_key]) ? true : false;
692 if (!$is_allowed) {
693 $skipped++;
694 continue;
695 }
696 }
697
698 // Process Attachments
699 $row_prefix = $group . '.' . $i . '.';
700
701 $sub_rows = [$attachment_data];
702 if (isset($attachment_data[$row_prefix . 'row_base']) && !empty($attachment_data[$row_prefix . 'row_base'])) {
703 $sub_group_id = $group . '.' . $i;
704 $sub_rows = $data->getData($sub_group_id);
705 }
706
707 foreach ($sub_rows as $row) {
708 $ids = $this->process_attachment($post_id, $row, $row_prefix, $filesystem, $ftp, $attachment);
709 $attachment_ids = array_merge($attachment_ids, $ids);
710 }
711 }
712
713 if ($skipped == $total_rows) {
714 return false;
715 }
716
717 return $attachment_ids;
718 }
719
720 /**
721 * Get list of posts
722 *
723 * @param ImporterModel $importer_model
724 *
725 * @return array
726 */
727 public function get_post_parent_options($importer_model)
728 {
729 $query = new \WP_Query(array(
730 'post_type' => $importer_model->getSetting('post_type'),
731 'posts_per_page' => -1,
732 'cache_results' => false,
733 'update_post_meta_cache' => false,
734 ));
735
736 if (is_wp_error($query)) {
737 return $query;
738 }
739
740 $result = [];
741 foreach ($query->posts as $post) {
742 $result[] = [
743 'value' => '' . $post->ID,
744 'label' => $post->post_title
745 ];
746 }
747
748 return $result;
749 }
750
751 /**
752 * Get list taxonomies
753 *
754 * @param ImporterModel $importer_model
755 *
756 * @return array
757 */
758 public function get_taxonomy_options($importer_model)
759 {
760 $taxonomies = get_object_taxonomies($importer_model->getSetting('post_type'), 'objects');
761
762 if (empty($taxonomies)) {
763 return [];
764 }
765
766 $result = [];
767 /**
768 * @var \WP_Taxonomy[] $taxonomies
769 */
770 foreach ($taxonomies as $key => $taxonomy) {
771 $result[] = [
772 'value' => '' . $key,
773 'label' => $taxonomy->label
774 ];
775 }
776
777 return $result;
778 }
779
780 /**
781 * Convert fields/headings to data map
782 *
783 * @param mixed $fields
784 * @param ImporterModel $importer
785 * @return array
786 */
787 public function generate_field_map($fields, $importer)
788 {
789 $result = parent::generate_field_map($fields, $importer);
790 $map = $result['map'];
791 $enabled = $result['enabled'];
792
793 $taxonomies = [];
794 $attachments = [];
795 $author = [];
796 $parent = [];
797
798 foreach ($fields as $index => $field) {
799
800 if (preg_match('/^image\.(.*?)$/', $field, $matches) === 1) {
801
802 // Capture featured image.
803 // image.id,url, title, alt, caption, description
804 if (!isset($attachments['image'])) {
805 $attachments['image'] = [
806 'map' => []
807 ];
808 }
809
810 $attachments['image']['map'][$matches[1]] = sprintf('{%d}', $index);
811 $attachments['image']['map']['featured'] = 'yes';
812 } elseif (preg_match('/^tax_([a-zA-Z0-9_]+)\.(.*?)$/', $field, $matches) === 1) {
813
814 // Capture Taxonomies.
815 // tax_{taxonomy}.name,slug,id,hierarchy::id,hierarchy::name,hierarchy::slug
816
817 $taxonomy = $matches[1];
818 if (!isset($taxonomies[$taxonomy])) {
819 $taxonomies[$taxonomy] = [
820 'map' => []
821 ];
822 }
823
824 $taxonomies[$taxonomy]['map'][$matches[2]] = sprintf('{%d}', $index);
825 } elseif (preg_match('/^author\.(.*?)$/', $field, $matches) === 1) {
826
827 // Capture author.
828 // author.ID, author.user_login,author.user_nicename,author.user_email,author.user_url,author.display_name
829 if (!isset($author['map'])) {
830 $author['map'] = [];
831 }
832
833 $author['map'][$matches[1]] = sprintf('{%d}', $index);
834 } elseif (preg_match('/^parent\.(.*?)$/', $field, $matches) === 1) {
835
836 // Capture parent
837 // parent.id,parent.name,parent.slug
838 if (!isset($parent['map'])) {
839 $parent['map'] = [];
840 }
841
842 $parent['map'][$matches[1]] = sprintf('{%d}', $index);
843 } elseif (isset($this->field_map[$field])) {
844
845 // Handle core fields
846 $field_key = $this->field_map[$field];
847 $map[$field_key] = sprintf('{%d}', $index);
848
849 if (in_array($field, $this->optional_fields)) {
850 $enabled[] = $field_key;
851 }
852
853 if (in_array($field, ['post_status', 'comment_status', 'ping_status'])) {
854 $map[$field_key . '._enable_text'] = 'yes';
855 }
856 }
857 }
858
859 $taxonomies = apply_filters('iwp/importer/generate_field_map/taxonomies', $taxonomies, $fields, $importer);
860 $attachments = apply_filters('iwp/importer/generate_field_map/attachments', $attachments, $fields, $importer);
861 $author = apply_filters('iwp/importer/generate_field_map/author', $author, $fields, $importer);
862 $parent = apply_filters('iwp/importer/generate_field_map/parent', $parent, $fields, $importer);
863
864 if (!empty($taxonomies)) {
865
866 $taxonomy_counter = 0;
867 $defaults = [
868 'row_base' => '',
869 'tax' => '',
870 'term' => '',
871 'settings._append' => 'no',
872 'settings._delimiter' => '',
873 'settings._hierarchy' => 'no',
874 'settings._hierarchy_character' => '>',
875 ];
876
877 foreach ($taxonomies as $taxonomy => $taxonomy_data) {
878 $data = [];
879
880 if (isset($taxonomy_data['map']['hierarchy::name'])) {
881 $data['term'] = $taxonomy_data['map']['hierarchy::name'];
882 $data['settings._hierarchy'] = 'yes';
883 } elseif (isset($taxonomy_data['map']['hierarchy::slug'])) {
884 $data['term'] = $taxonomy_data['map']['hierarchy::slug'];
885 $data['settings._hierarchy'] = 'yes';
886 } elseif (isset($taxonomy_data['map']['name'])) {
887 $data['term'] = $taxonomy_data['map']['name'];
888 } elseif (isset($taxonomy_data['map']['slug'])) {
889 $data['term'] = $taxonomy_data['map']['slug'];
890 } else {
891 continue;
892 }
893
894 $data['tax'] = $taxonomy;
895
896 $data = wp_parse_args($data, $defaults);
897
898 $map = array_merge($map, array_reduce(array_keys($data), function ($carry, $key) use ($data, $taxonomy_counter) {
899 $carry[sprintf('taxonomies.%d.%s', $taxonomy_counter, $key)] = $data[$key];
900 return $carry;
901 }, []));
902
903 $taxonomy_counter++;
904 }
905
906 $map['taxonomies._index'] = $taxonomy_counter;
907 }
908
909 if (!empty($attachments)) {
910
911 $attachment_counter = 0;
912 $defaults = [
913 'row_base' => '',
914 'location' => '',
915 'settings._delimiter' => '',
916 'settings._download' => 'remote',
917 'settings._enable_image_hash' => 'yes',
918 'settings._featured' => 'no',
919 'settings._ftp_host' => '',
920 'settings._ftp_pass' => '',
921 'settings._ftp_path' => '',
922 'settings._ftp_user' => '',
923 'settings._local_url' => '',
924 'settings._meta._alt' => '',
925 'settings._meta._caption' => '',
926 'settings._meta._description' => '',
927 'settings._meta._enabled' => 'no',
928 'settings._meta._title' => '',
929 'settings._remote_url' => '',
930 ];
931
932 foreach ($attachments as $attachment_data) {
933
934 $data = [];
935
936 if (!isset($attachment_data['map']['url'])) {
937 continue;
938 }
939
940 // location
941 $data['location'] = $attachment_data['map']['url'];
942
943 if (isset($attachment_data['map']['featured'])) {
944 $data['settings._featured'] = $attachment_data['map']['featured'];
945 }
946
947 // Meta
948 if (isset($attachment_data['map']['title'])) {
949 $data['settings._meta._title'] = $attachment_data['map']['title'];
950 $data['settings._meta._enabled'] = 'yes';
951 }
952 if (isset($attachment_data['map']['alt'])) {
953 $data['settings._meta._alt'] = $attachment_data['map']['alt'];
954 $data['settings._meta._enabled'] = 'yes';
955 }
956 if (isset($attachment_data['map']['description'])) {
957 $data['settings._meta._description'] = $attachment_data['map']['description'];
958 $data['settings._meta._enabled'] = 'yes';
959 }
960 if (isset($attachment_data['map']['caption'])) {
961 $data['settings._meta._caption'] = $attachment_data['map']['caption'];
962 $data['settings._meta._enabled'] = 'yes';
963 }
964
965 $data = wp_parse_args($data, $defaults);
966
967 $map = array_merge($map, array_reduce(array_keys($data), function ($carry, $key) use ($data, $attachment_counter) {
968 $carry[sprintf('attachments.%d.%s', $attachment_counter, $key)] = $data[$key];
969 return $carry;
970 }, []));
971
972 $attachment_counter++;
973 }
974
975 $map['attachments._index'] = $attachment_counter;
976 }
977
978 if (!empty($author)) {
979
980 // TODO: enable field? this is a seperate field list
981 $enabled_key = 'post._author';
982 if (isset($author['map']['user_email'])) {
983
984 $enabled[] = $enabled_key;
985 $map['post._author.post_author'] = $author['map']['user_email'];
986 $map['post._author._author_type'] = 'email';
987 } elseif (isset($author['map']['user_login'])) {
988
989 $enabled[] = $enabled_key;
990 $map['post._author.post_author'] = $author['map']['user_login'];
991 $map['post._author._author_type'] = 'login';
992 } elseif (isset($author['map']['ID'])) {
993
994 $enabled[] = $enabled_key;
995 $map['post._author.post_author'] = $author['map']['ID'];
996 $map['post._author._author_type'] = 'id';
997 }
998 }
999
1000 if (!empty($parent)) {
1001
1002 // parent.id,parent.name,parent.slug
1003 $enabled_key = 'post._parent';
1004 if (isset($parent['map']['name'])) {
1005
1006 $enabled[] = $enabled_key;
1007 $map['post._parent.parent'] = $parent['map']['name'];
1008 $map['post._parent.parent._enable_text'] = 'yes';
1009 $map['post._parent._parent_type'] = 'name';
1010 } elseif (isset($parent['map']['slug'])) {
1011
1012 $enabled[] = $enabled_key;
1013 $map['post._parent.parent'] = $parent['map']['slug'];
1014 $map['post._parent.parent._enable_text'] = 'yes';
1015 $map['post._parent._parent_type'] = 'slug';
1016 } elseif (isset($parent['map']['id'])) {
1017
1018 $enabled[] = $enabled_key;
1019 $map['post._parent.parent'] = $parent['map']['name'];
1020 $map['post._parent.parent._enable_text'] = 'yes';
1021 $map['post._parent._parent_type'] = 'id';
1022 }
1023 }
1024
1025 return [
1026 'map' => $map,
1027 'enabled' => $enabled
1028 ];
1029 }
1030 }
1031