You are here

protected function FeedsProcessor::map in Feeds 8.2

Execute mapping on an item.

This method encapsulates the central mapping functionality. When an item is processed, it is passed through map() where the properties of $source_item are mapped onto $target_item following the processor's mapping configuration.

For each mapping FeedsParser::getSourceElement() is executed to retrieve the source element, then FeedsProcessor::setTargetElement() is invoked to populate the target item properly. Alternatively a hook_x_targets_alter() may have specified a callback for a mapping target in which case the callback is asked to populate the target item instead of FeedsProcessor::setTargetElement().

See also

hook_feeds_parser_sources_alter()

hook_feeds_data_processor_targets_alter()

hook_feeds_node_processor_targets_alter()

hook_feeds_term_processor_targets_alter()

hook_feeds_user_processor_targets_alter()

Related topics

1 call to FeedsProcessor::map()
FeedsProcessor::process in lib/Drupal/feeds/Plugin/FeedsProcessor.php
Process the result of the parsing stage.

File

lib/Drupal/feeds/Plugin/FeedsProcessor.php, line 519
Contains FeedsProcessor and related classes.

Class

FeedsProcessor
Abstract class, defines interface for processors.

Namespace

Drupal\feeds\Plugin

Code

protected function map(FeedsSource $source, FeedsParserResult $result, $target_item = NULL) {

  // Static cache $targets as getMappingTargets() may be an expensive method.
  static $sources;
  if (!isset($sources[$this->id])) {
    $sources[$this->id] = feeds_importer($this->id)->parser
      ->getMappingSources();
  }
  static $targets;
  if (!isset($targets[$this->id])) {
    $targets[$this->id] = $this
      ->getMappingTargets();
  }
  $parser = feeds_importer($this->id)->parser;
  if (empty($target_item)) {
    $target_item = array();
  }

  // Many mappers add to existing fields rather than replacing them. Hence we
  // need to clear target elements of each item before mapping in case we are
  // mapping on a prepopulated item such as an existing node.
  foreach ($this->config['mappings'] as $mapping) {
    if (isset($targets[$this->id][$mapping['target']]['real_target'])) {
      unset($target_item->{$targets[$this->id][$mapping['target']]['real_target']});
    }
    elseif (isset($target_item->{$mapping['target']})) {
      unset($target_item->{$mapping['target']});
    }
  }

  /*
  This is where the actual mapping happens: For every mapping we envoke
  the parser's getSourceElement() method to retrieve the value of the source
  element and pass it to the processor's setTargetElement() to stick it
  on the right place of the target item.

  If the mapping specifies a callback method, use the callback instead of
  setTargetElement().
  */
  self::loadMappers();
  foreach ($this->config['mappings'] as $mapping) {

    // Retrieve source element's value from parser.
    if (isset($sources[$this->id][$mapping['source']]) && is_array($sources[$this->id][$mapping['source']]) && isset($sources[$this->id][$mapping['source']]['callback']) && function_exists($sources[$this->id][$mapping['source']]['callback'])) {
      $callback = $sources[$this->id][$mapping['source']]['callback'];
      $value = $callback($source, $result, $mapping['source']);
    }
    else {
      $value = $parser
        ->getSourceElement($source, $result, $mapping['source']);
    }

    // Map the source element's value to the target.
    if (isset($targets[$this->id][$mapping['target']]) && is_array($targets[$this->id][$mapping['target']]) && isset($targets[$this->id][$mapping['target']]['callback']) && function_exists($targets[$this->id][$mapping['target']]['callback'])) {
      $callback = $targets[$this->id][$mapping['target']]['callback'];
      $callback($source, $target_item, $mapping['target'], $value, $mapping);
    }
    else {
      $this
        ->setTargetElement($source, $target_item, $mapping['target'], $value, $mapping);
    }
  }
  return $target_item;
}