marketo_suite-1.0.x-dev/src/Plugin/MarketoHandler/DefaultMarketoHandler.php

src/Plugin/MarketoHandler/DefaultMarketoHandler.php
<?php

namespace Drupal\e3_marketo\Plugin\MarketoHandler;

use Drupal\Component\Plugin\Exception\PluginException;
use Drupal\Core\Entity\FieldableEntityInterface;
use Drupal\Core\Link;
use Drupal\Core\Template\Attribute;
use Drupal\e3_marketo\Entity\MarketoFormEntityInterface;
use Drupal\e3_marketo\Plugin\MarketoHandlerBase;

/**
 * Default handler to build output for Marketo Forms.
 *
 * @MarketoHandler(
 *   id = "default_marketo_handler",
 *   label = @Translation("Default Marketo Handler"),
 *   description = @Translation("Default Marketo handler to attach a base Marketo form with prefill support."),
 *   bundles = {},
 *   priority = 100
 * )
 */
class DefaultMarketoHandler extends MarketoHandlerBase {

  /**
   * Tracks Marketo instances on the page.
   *
   * This variable is necessary in case the same form is added several times on
   * the page.
   *
   * @var array
   */
  public static array $marketoInstances;

  /**
   * HTML class of Marketo Form.
   *
   * @var string
   */
  protected string $htmlClass;

  /**
   * Current Marketo Form instance.
   *
   * For cases when same form is added multiple times on the page, this helps
   * handlers to be aware of the exact instance we're working with.
   *
   * @var int
   */
  protected int $instance;

  /**
   * {@inheritdoc}
   */
  public function embedMarketoForm(MarketoFormEntityInterface $marketo_form, array &$build) : array {
    $marketo_form_id = $marketo_form->getFormId();

    $this->htmlClass = "marketo-form-{$marketo_form_id}";

    // Do not embed the form if key Marketo settings are missing.
    if (!$this->verifyMarketoSettings()) {
      return [];
    }

    // Determine the current form instance.
    $this->instance = $this->getMarketoFormInstance($build, $marketo_form_id);

    // Only run the default processing if dynamic parameters has not been set or
    // if they were mistakenly cleared by one of the plugins.
    if (empty($build['marketo_form_embed']['#form_attributes'])
      || empty($build['marketo_form_embed']['#attached']['drupalSettings']['marketoForms'])) {

      $build['marketo_form_embed'] = [
        '#theme' => 'marketo_form_embed',
        '#form_attributes' => $this->getMarketoFormAttributes($marketo_form),
        '#marketo_form_id' => $marketo_form_id,
        '#attached' => [
          'library' => ['e3_marketo/marketo-forms'],
          'drupalSettings' => [
            'marketoForms' => $this->getMarketoScriptParameters($marketo_form),
          ],
        ],
      ];
    }
    else {
      // Otherwise only update the dynamic parameters.
      $this->alterScriptParameters($build['marketo_form_embed']['#attached']['drupalSettings']['marketoForms'][$this->htmlClass], $marketo_form);
    }

    static::$loadedMarketoSettings = $build['marketo_form_embed']['#attached']['drupalSettings']['marketoForms'];
    return $build;
  }

  /**
   * Determine Marketo Form instance of the current form.
   *
   * @param array $build
   *   Marketo Form entity build array.
   * @param string $marketo_form_id
   *   Marketo form id.
   *
   * @return int
   *   Marketo instance ID.
   */
  public function getMarketoFormInstance(array $build, string $marketo_form_id) : int {

    if (empty($build['marketo_form_embed']['#form_attributes'])
      || empty($build['marketo_form_embed']['#attached']['drupalSettings']['marketoForms'])) {

      // Set Marketo instance.
      if (!isset(static::$marketoInstances[$marketo_form_id])) {

        $request = $this->requestStack->getCurrentRequest();

        if ($request->isXmlHttpRequest()) {
          $instance = time();
        }
        else {
          $instance = 0;
        }

        static::$marketoInstances[$marketo_form_id] = $instance;
      }
      else {
        static::$marketoInstances[$marketo_form_id]++;
        $instance = static::$marketoInstances[$marketo_form_id];
      }
    }
    else {
      $instance = static::$marketoInstances[$marketo_form_id];
    }

    return $instance;
  }

  /**
   * Retrieve script parameters to pass into Marketo embed script.
   *
   * @param \Drupal\e3_marketo\Entity\MarketoFormEntityInterface $marketo_form
   *   Marketo form entity.
   *
   * @return array
   *   Array of parameters to add to drupalSettings.
   */
  public function getMarketoScriptParameters(MarketoFormEntityInterface $marketo_form) : array {
    $form_id = $marketo_form->getFormId();

    $munchkin_id = $this->marketoConfig->get('munchkin_id');
    $instance_host = $this->marketoConfig->get('instance_host');

    // Submission callbacks.
    $html_class = $this->htmlClass;
    $submission_callbacks = $this->getSubmissionCallbacks($marketo_form);

    if (empty($marketo_form->bundle)) {
      return [];
    }

    /** @var \Drupal\e3_marketo\Entity\MarketoFormEntityBundle $marketo_bundle */
    $marketo_bundle = $marketo_form->bundle->entity;

    // Main params to pass into JS.
    $result = [
      'munchkinId' => $munchkin_id,
      'instanceHost' => $instance_host,
      'formId' => $form_id,
      'loadErrorMessage' => $this->marketoConfig->get('load_error_message.value'),
      'alternativeInstanceHost' => $this->marketoConfig->get('alt_instance_host'),
      'entityWrapper' => '.marketo-form-entity-ajax-wrapper',
      'formWrapper' => '.marketo-form',
      'htmlClass' => $html_class,
      'removeSourceStyles' => $marketo_bundle->getRemoveSourceStyles(),
      $this->instance => [
        'submissionCallbacks' => $submission_callbacks,
      ],
    ];

    // If this form is referenced via component, check if any hidden fields have
    // been set.
    if (!empty($marketo_form->_referringItem)) {
      $parent_entity = $marketo_form->_referringItem->getEntity();

      if ($parent_entity->hasField('field_marketo_hidden_fields')) {
        $hidden_fields = $this->getMarketoHiddenFields($parent_entity);

        if ($hidden_fields) {
          $result[$this->instance]['hiddenFields'] = $hidden_fields;
        }
      }
    }

    $this->alterScriptParameters($result, $marketo_form);

    // Figure out if any redirects set up within Marketo should be skipped.
    $non_default_callbacks_added = !empty($submission_callbacks) && !isset($submission_callbacks['default_marketo_handler']);
    $default_with_thank_you = isset($submission_callbacks['default_marketo_handler']) && !empty($result['thankYouComponent']);
    if ($non_default_callbacks_added || $default_with_thank_you) {
      $result[$this->instance]['skipMarketoRedirects'] = TRUE;
    }

    $params[$html_class] = $result;
    return $params;
  }

  /**
   * Alter the list of parameters that will be sent to Marketo script.
   *
   * @param array $params
   *   Parameters list to alter.
   * @param \Drupal\e3_marketo\Entity\MarketoFormEntityInterface $marketo_form
   *   Marketo Form entity.
   */
  public function alterScriptParameters(array &$params, MarketoFormEntityInterface $marketo_form) {
    // Nothing to do here in this handler, but the function stub needs to exist.
  }

  /**
   * Retrieve a set of Html parameters to pass into Marketo template.
   *
   * @param \Drupal\e3_marketo\Entity\MarketoFormEntityInterface $marketo_form
   *   Marketo form entity.
   *
   * @return \Drupal\Core\Template\Attribute
   *   Html attributes to pass into template as 'form_attributes'.
   */
  public function getMarketoFormAttributes(MarketoFormEntityInterface $marketo_form) : Attribute {
    $html_class = $this->htmlClass;

    $attributes = new Attribute();
    $attributes->setAttribute('data-form-id', $marketo_form->getFormId());
    $attributes->setAttribute('data-form-name', $marketo_form->getName());
    $attributes->addClass(['marketo-form-load', $html_class]);
    $attributes->setAttribute('data-instance', (string) $this->instance);

    return $attributes;
  }

  /**
   * Check that all required Marketo settings have been set.
   *
   * @return bool
   *   TRUE if all required settings are available, FALSE otherwise.
   */
  public function verifyMarketoSettings() : bool {
    if (!$this->marketoConfig->get('instance_host') || !$this->marketoConfig->get('munchkin_id')) {
      $this->messenger->addError($this->t("Marketo Form could not be loaded, because some of the required Marketo Settings are missing. Please, visit the @link to fill them.", [
        '@link' => Link::createFromRoute($this->t("Settings Page"), 'marketo_form.settings')->toString(),
      ]));

      return FALSE;
    }
    else {
      return TRUE;
    }
  }

  /**
   * Retrieve all hidden fields set for the Marketo Form.
   *
   * @param \Drupal\Core\Entity\FieldableEntityInterface $parent_entity
   *   Parent entity of the Marketo Form.
   *
   * @return array
   *   An object with field names as properties. This is the way Marketo expects
   *   the hidden fields data to be set.
   */
  public function getMarketoHiddenFields(FieldableEntityInterface $parent_entity) : array {
    $result = [];

    // Check if any hidden fields have been set.
    if (!$parent_entity->get('field_marketo_hidden_fields')->isEmpty()) {
      foreach ($parent_entity->get('field_marketo_hidden_fields') as $hidden_field) {
        $parent = !empty($hidden_field->entity) ? $hidden_field->entity : NULL;

        if ($parent && $parent->hasField('field_hidden_field_name') && $parent->hasField('field_hidden_field_value')) {
          $field_name = $parent->get('field_hidden_field_name')->value;
          $field_value = $parent->get('field_hidden_field_value')->value;
          $result[$field_name] = $field_value;
        }
      }
    }

    return $result;
  }

  /**
   * Get the submission callbacks selected for this form.
   *
   * @param \Drupal\e3_marketo\Entity\MarketoFormEntityInterface $marketo_form
   *   Marketo form entity.
   */
  public function getSubmissionCallbacks(MarketoFormEntityInterface $marketo_form) : array {
    // Check for patent entity.
    if (!empty($marketo_form->_referringItem)) {
      $parent_entity = $marketo_form->_referringItem->getEntity();

      if ($parent_entity && $parent_entity->hasField('field_submission_behavior')) {
        $submission_behavior = $parent_entity->get('field_submission_behavior')->getString();
      }
    }

    // If parent entity didn't provide a behavior, look for one on the form.
    if (empty($submission_behavior)) {
      $submission_behavior = $marketo_form->get('submission_behavior')->getString();
    }

    // Set submission callbacks.
    if ($submission_behavior) {
      try {
        /** @var \Drupal\e3_marketo\Plugin\SubmissionBehaviorInterface $behavior */
        $behavior = $this->submissionBehaviorManager->createInstance($submission_behavior);
      }
      catch (PluginException $e) {
        return [];
      }

      return $behavior->getSubmissionCallbacks($marketo_form);
    }

    return [];
  }

}

Главная | Обратная связь

drupal hosting | друпал хостинг | it patrol .inc