simple_sitemap.module 8.45 KB
Newer Older
gbyte.co's avatar
gbyte.co committed
1
<?php
gbyte.co's avatar
gbyte.co committed
2

3 4 5 6
/**
 * @file
 * Main module file containing hooks.
 */
gbyte.co's avatar
gbyte.co committed
7

8
use Drupal\Core\Form\FormStateInterface;
gbyte.co's avatar
gbyte.co committed
9 10
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Routing\RouteMatchInterface;
11
use Drupal\system\MenuInterface;
12
use Drupal\language\ConfigurableLanguageInterface;
13

14
/**
15
 *Implements hook_help().
gbyte.co's avatar
gbyte.co committed
16 17 18 19
 *
 * @param $route_name
 * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
 * @return \Drupal\Component\Render\MarkupInterface|null
20
 */
gbyte.co's avatar
gbyte.co committed
21
function simple_sitemap_help($route_name, RouteMatchInterface $route_match) {
22
  return $route_name === 'help.page.simple_sitemap' ?
23
    check_markup(file_get_contents(dirname(__FILE__) . "/README.md")) : NULL;
24 25
}

26
/**
27
 * Implements hook_form_alter().
28 29
 *
 * Adds sitemap settings to entity types that are supported via plugins.
gbyte.co's avatar
gbyte.co committed
30 31 32 33
 *
 * @param $form
 * @param \Drupal\Core\Form\FormStateInterface $form_state
 * @param $form_id
34
 */
gbyte.co's avatar
gbyte.co committed
35
function simple_sitemap_form_alter(&$form, FormStateInterface $form_state, $form_id) {
36

37
  /** @var Drupal\simple_sitemap\Form\FormHelper $f */
gbyte.co's avatar
gbyte.co committed
38 39
  $f = \Drupal::service('simple_sitemap.form_helper');
  if (!$f->processForm($form_state)) {
40
    return;
gbyte.co's avatar
gbyte.co committed
41
  }
gbyte.co's avatar
gbyte.co committed
42 43 44 45

  $form['simple_sitemap'] = [
    '#type' => 'details',
    '#group' => isset($form['additional_settings']) ? 'additional_settings' : 'advanced',
46
    '#title' => t('Simple XML Sitemap'),
gbyte.co's avatar
gbyte.co committed
47
    '#description' => $f->getEntityCategory() === 'instance' ? t('Settings for this entity can be overridden here.') : '',
48
    '#weight' => 10,
gbyte.co's avatar
gbyte.co committed
49
  ];
50

gbyte.co's avatar
gbyte.co committed
51 52 53
  // Only attach fieldset summary js to 'additional settings' vertical tabs.
  if (isset($form['additional_settings'])) {
    $form['#attached']['library'][] = 'simple_sitemap/fieldsetSummaries';
54
  }
55

56
  $f->displayEntitySettings($form['simple_sitemap'])
gbyte.co's avatar
gbyte.co committed
57 58
  // todo: do not show setting when creating new bundle.
    ->displayRegenerateNow($form['simple_sitemap']);
59

60
  // Add submission handler.
61
  if (isset($form['actions']['submit']['#submit'])) {
62
    foreach (array_keys($form['actions']) as $action) {
gbyte.co's avatar
gbyte.co committed
63
      if ($action !== 'preview'
64 65
        && isset($form['actions'][$action]['#type'])
        && $form['actions'][$action]['#type'] === 'submit') {
66 67 68
        $form['actions'][$action]['#submit'][] = 'simple_sitemap_entity_form_submit';
      }
    }
69
  }
gbyte.co's avatar
gbyte.co committed
70 71
  // Fix for account page rendering other submit handlers not usable.
  else {
gbyte.co's avatar
gbyte.co committed
72
    $form['#submit'][] = 'simple_sitemap_entity_form_submit';
73
  }
gbyte.co's avatar
gbyte.co committed
74 75
}

76
/**
77
 * Form submission handler called in hook_form_alter.
gbyte.co's avatar
gbyte.co committed
78 79 80
 *
 * @param $form
 * @param \Drupal\Core\Form\FormStateInterface $form_state
81
 */
gbyte.co's avatar
gbyte.co committed
82
function simple_sitemap_entity_form_submit($form, FormStateInterface &$form_state) {
83

84
  /** @var Drupal\simple_sitemap\Form\FormHelper $f */
gbyte.co's avatar
gbyte.co committed
85 86 87 88
  $f = \Drupal::service('simple_sitemap.form_helper');
  if (!$f->processForm($form_state)) {
    return;
  }
89

90 91 92 93
  $values = $form_state->getValues();

  // Fix for values appearing in a sub array on a commerce product entity.
  $values = isset($values['simple_sitemap']) ? $values['simple_sitemap'] : $values;
94

95
  // Only make changes in DB if sitemap settings actually changed.
96
  if ($f->valuesChanged($form, $values)) {
97

98
    /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
99
    $generator = \Drupal::service('simple_sitemap.generator');
100

101 102 103 104 105 106 107 108 109 110 111 112 113 114 115
    foreach ($generator->getSitemapManager()->getSitemapVariants(NULL, FALSE) as $variant => $definition) {

      if (isset($values['index_' . $variant . '_' . $f->getEntityTypeId() . '_settings'])) { // Variants may have changed since form load.
        $settings = [
          'index' => (bool) $values['index_' . $variant . '_' . $f->getEntityTypeId() . '_settings'],
          'priority' => $values['priority_' . $variant . '_' . $f->getEntityTypeId() . '_settings'],
          'changefreq' => $values['changefreq_' . $variant . '_' . $f->getEntityTypeId() . '_settings'],
          'include_images' => (bool) $values['include_images_' . $variant . '_' . $f->getEntityTypeId() . '_settings'],
        ];

        $generator->setVariants($variant);

        switch ($f->getEntityCategory()) {

          case 'bundle':
116
            $generator->setBundleSettings($f->getEntityTypeId(), $f->getBundleName(), $settings);
117 118 119 120 121 122
            if (empty($settings['index'])) {
              $generator->removeEntityInstanceSettings($f->getEntityTypeId(), $f->getInstanceId());
            }
            break;

          case 'instance':
123 124 125
            if (!$f->entityIsNew()) {
              $generator->setEntityInstanceSettings($f->getEntityTypeId(), $f->getInstanceId(), $settings);
            }
126 127
            break;
        }
128 129 130
      }
    }

131 132
    // Regenerate sitemaps according to user setting.
    if ($values['simple_sitemap_regenerate_now']) {
133 134 135
      $generator->setVariants(TRUE)
        ->rebuildQueue()
        ->generateSitemap();
136
    }
137 138 139 140
  }
}

/**
141
 * Implements hook_cron().
142
 */
gbyte.co's avatar
gbyte.co committed
143
function simple_sitemap_cron() {
144

145
  /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
146
  $generator = \Drupal::service('simple_sitemap.generator');
147

148
  if ($generator->getSetting('cron_generate')) {
149
    $interval = (int) $generator->getSetting('cron_generate_interval', 0) * 60 * 60;
150 151 152 153 154 155 156 157 158 159 160 161
    $request_time = \Drupal::service('datetime.time')->getRequestTime();
    $generation_in_progress = $generator->getQueueWorker()->generationInProgress();
    $state = \Drupal::state();

    if ($interval === 0
      || $generation_in_progress
      || (($state->get('simple_sitemap.last_cron_generate', 0) + $interval) <= $request_time)) {

      if (!$generation_in_progress) {
        $state->set('simple_sitemap.last_cron_generate', $request_time);
      }

gbyte.co's avatar
gbyte.co committed
162
      $generator->generateSitemap('cron');
163
    }
164
  }
gbyte.co's avatar
gbyte.co committed
165
}
166

167 168 169 170 171 172 173
/**
 * Implements hook_ENTITY_TYPE_delete().
 *
 * When a language is removed from the system remove it also from settings.
 */
function simple_sitemap_configurable_language_delete(ConfigurableLanguageInterface $language) {

174
  /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
175
  $generator = \Drupal::service('simple_sitemap.generator');
gbyte.co's avatar
gbyte.co committed
176

177 178 179 180 181 182 183
  $excluded_languages = $generator->getSetting('excluded_languages');
  if (isset($excluded_languages[$language->id()])) {
    unset($excluded_languages[$language->id()]);
    $generator->saveSetting('excluded_languages', $excluded_languages);
  }
}

184 185 186 187
/**
 * Implements hook_entity_delete().
 *
 * Removes settings of the removed entity.
188 189
 *
 * @param \Drupal\Core\Entity\EntityInterface $entity
190
 */
gbyte.co's avatar
gbyte.co committed
191
function simple_sitemap_entity_delete(EntityInterface $entity) {
192

193 194 195 196 197 198 199 200 201 202
  /** @var \Drupal\simple_sitemap\EntityHelper $entity_helper */
  $entity_helper = \Drupal::service('simple_sitemap.entity_helper');
  if ($entity_helper->supports($entity->getEntityType())) {

    /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
    $generator = \Drupal::service('simple_sitemap.generator');
    $generator->setVariants(TRUE)->removeEntityInstanceSettings(
      $entity->getEntityTypeId(), $entity->id()
    );
  }
203
}
204 205 206 207 208

/**
 * Implements hook_entity_bundle_delete().
 *
 * Removes settings of the removed bundle.
gbyte.co's avatar
gbyte.co committed
209 210 211
 *
 * @param string $entity_type_id
 * @param string $bundle
212 213
 */
function simple_sitemap_entity_bundle_delete($entity_type_id, $bundle) {
214 215 216 217

  /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
  $generator = \Drupal::service('simple_sitemap.generator');
  $generator->setVariants(TRUE)->removeBundleSettings($entity_type_id, $bundle);
218 219 220 221 222 223 224 225 226 227
}

/**
 * Implements hook_menu_delete().
 *
 * Removes settings for the removed menu.
 *
 * @param \Drupal\system\MenuInterface $menu
 */
function simple_sitemap_menu_delete(MenuInterface $menu) {
228

229
  /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
230
  $generator = \Drupal::service('simple_sitemap.generator');
231
  $generator->setVariants(TRUE)->removeBundleSettings('menu_link_content', $menu->id());
232
}
233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254

/**
 * Implements hook_page_attachments_alter().
 */
function simple_sitemap_page_attachments_alter(array &$attachments) {
  /** @var \Drupal\simple_sitemap\Simplesitemap $generator */
  $generator = \Drupal::service('simple_sitemap.generator');
  if ($generator->getSetting('disable_language_hreflang')) {
    // @fixme https://www.drupal.org/project/drupal/issues/1255092
    // Content Translation module normally adds identical hreflang tags, so
    // executing its hook_page_attachments() implementation would be harmless,
    // but if an entity page is configured as the front page, it attaches
    // extraneous hreflang tags using the entity URL.
    foreach ($attachments['#attached']['html_head_link'] as $key => $list) {
      foreach ($list as $k => $element) {
        if (!empty($element['hreflang']) && !empty($element['rel'])) {
          unset($attachments['#attached']['html_head_link'][$key]);
        }
      }
    }
  }
}