field_test.module 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219
  1. <?php
  2. /**
  3. * @file
  4. * Helper module for the Field API tests.
  5. *
  6. * The module defines
  7. * - an entity type (field_test.entity.inc)
  8. * - a field type and its formatters and widgets (field_test.field.inc)
  9. * - a field storage backend (field_test.storage.inc)
  10. *
  11. * The main field_test.module file implements generic hooks and provides some
  12. * test helper functions
  13. */
  14. use Drupal\Core\Entity\EntityTypeInterface;
  15. use Drupal\Core\Form\FormStateInterface;
  16. use Drupal\Core\Render\Element;
  17. use Drupal\field\FieldStorageConfigInterface;
  18. require_once __DIR__ . '/field_test.entity.inc';
  19. require_once __DIR__ . '/field_test.field.inc';
  20. /**
  21. * Store and retrieve keyed data for later verification by unit tests.
  22. *
  23. * This function is a simple in-memory key-value store with the
  24. * distinction that it stores all values for a given key instead of
  25. * just the most recently set value. field_test module hooks call
  26. * this function to record their arguments, keyed by hook name. The
  27. * unit tests later call this function to verify that the correct
  28. * hooks were called and were passed the correct arguments.
  29. *
  30. * This function ignores all calls until the first time it is called
  31. * with $key of NULL. Each time it is called with $key of NULL, it
  32. * erases all previously stored data from its internal cache, but also
  33. * returns the previously stored data to the caller. A typical usage
  34. * scenario is:
  35. *
  36. * @code
  37. * // calls to field_test_memorize() here are ignored
  38. *
  39. * // turn on memorization
  40. * field_test_memorize();
  41. *
  42. * // call some Field API functions that invoke field_test hooks
  43. * FieldStorageConfig::create($field_definition)->save();
  44. *
  45. * // retrieve and reset the memorized hook call data
  46. * $mem = field_test_memorize();
  47. *
  48. * // make sure hook_field_storage_config_create() is invoked correctly
  49. * assertEqual(count($mem['field_test_field_storage_config_create']), 1);
  50. * assertEqual($mem['field_test_field_storage_config_create'][0], array($field));
  51. * @endcode
  52. *
  53. * @param $key
  54. * The key under which to store to $value, or NULL as described above.
  55. * @param $value
  56. * A value to store for $key.
  57. * @return
  58. * An array mapping each $key to an array of each $value passed in
  59. * for that key.
  60. */
  61. function field_test_memorize($key = NULL, $value = NULL) {
  62. $memorize = &drupal_static(__FUNCTION__, NULL);
  63. if (!isset($key)) {
  64. $return = $memorize;
  65. $memorize = [];
  66. return $return;
  67. }
  68. if (is_array($memorize)) {
  69. $memorize[$key][] = $value;
  70. }
  71. }
  72. /**
  73. * Memorize calls to field_test_field_storage_config_create().
  74. */
  75. function field_test_field_storage_config_create(FieldStorageConfigInterface $field_storage) {
  76. $args = func_get_args();
  77. field_test_memorize(__FUNCTION__, $args);
  78. }
  79. /**
  80. * Implements hook_entity_display_build_alter().
  81. */
  82. function field_test_entity_display_build_alter(&$output, $context) {
  83. $display_options = $context['display']->getComponent('test_field');
  84. if (isset($display_options['settings']['alter'])) {
  85. $output['test_field'][] = ['#markup' => 'field_test_entity_display_build_alter'];
  86. }
  87. if (isset($output['test_field'])) {
  88. $output['test_field'][] = ['#markup' => 'entity language is ' . $context['entity']->language()->getId()];
  89. }
  90. }
  91. /**
  92. * Implements hook_field_widget_form_alter().
  93. */
  94. function field_test_field_widget_form_alter(&$element, FormStateInterface $form_state, $context) {
  95. // Set a message if this is for the form displayed to set default value for
  96. // the field.
  97. if ($context['default']) {
  98. drupal_set_message('From hook_field_widget_form_alter(): Default form is true.');
  99. }
  100. }
  101. /**
  102. * Implements hook_field_widget_multivalue_form_alter().
  103. */
  104. function field_test_field_widget_multivalue_form_alter(array &$elements, FormStateInterface $form_state, array $context) {
  105. _field_test_alter_widget("hook_field_widget_multivalue_form_alter", $elements, $form_state, $context);
  106. }
  107. /**
  108. * Implements hook_field_widget_multivalue_WIDGET_TYPE_form_alter().
  109. */
  110. function field_test_field_widget_multivalue_test_field_widget_multiple_form_alter(array &$elements, FormStateInterface $form_state, array $context) {
  111. _field_test_alter_widget("hook_field_widget_multivalue_WIDGET_TYPE_form_alter", $elements, $form_state, $context);
  112. }
  113. /**
  114. * Implements hook_field_widget_multivalue_WIDGET_TYPE_form_alter().
  115. */
  116. function field_test_field_widget_multivalue_test_field_widget_multiple_single_value_form_alter(array &$elements, FormStateInterface $form_state, array $context) {
  117. _field_test_alter_widget("hook_field_widget_multivalue_WIDGET_TYPE_form_alter", $elements, $form_state, $context);
  118. }
  119. /**
  120. * Sets up alterations for widget alter tests.
  121. *
  122. * @see \Drupal\field\Tests\FormTest::widgetAlterTest()
  123. */
  124. function _field_test_alter_widget($hook, array &$elements, FormStateInterface $form_state, array $context) {
  125. // Set a message if this is for the form displayed to set default value for
  126. // the field.
  127. if ($context['default']) {
  128. drupal_set_message("From $hook(): Default form is true.");
  129. }
  130. $alter_info = \Drupal::state()->get("field_test.widget_alter_test");
  131. $name = $context['items']->getFieldDefinition()->getName();
  132. if (!empty($alter_info) && $hook === $alter_info['hook'] && $name === $alter_info['field_name']) {
  133. $elements['#prefix'] = "From $hook(): prefix on $name parent element.";
  134. foreach (Element::children($elements) as $delta => $element) {
  135. $elements[$delta]['#suffix'] = "From $hook(): suffix on $name child element.";
  136. }
  137. }
  138. }
  139. /**
  140. * Implements hook_query_TAG_alter() for tag 'efq_table_prefixing_test'.
  141. *
  142. * @see \Drupal\system\Tests\Entity\EntityFieldQueryTest::testTablePrefixing()
  143. */
  144. function field_test_query_efq_table_prefixing_test_alter(&$query) {
  145. // Add an additional join onto the entity base table. This will cause an
  146. // exception if the EFQ does not properly prefix the base table.
  147. $query->join('entity_test', 'et2', '%alias.id = entity_test.id');
  148. }
  149. /**
  150. * Implements hook_query_TAG_alter() for tag 'efq_metadata_test'.
  151. *
  152. * @see \Drupal\system\Tests\Entity\EntityQueryTest::testMetaData()
  153. */
  154. function field_test_query_efq_metadata_test_alter(&$query) {
  155. global $efq_test_metadata;
  156. $efq_test_metadata = $query->getMetadata('foo');
  157. }
  158. /**
  159. * Implements hook_entity_extra_field_info_alter().
  160. */
  161. function field_test_entity_extra_field_info_alter(&$info) {
  162. // Remove all extra fields from the 'no_fields' content type;
  163. unset($info['node']['no_fields']);
  164. }
  165. /**
  166. * Implements hook_entity_bundle_field_info_alter().
  167. */
  168. function field_test_entity_bundle_field_info_alter(&$fields, EntityTypeInterface $entity_type, $bundle) {
  169. if (($field_name = \Drupal::state()->get('field_test_constraint', FALSE)) && $entity_type->id() == 'entity_test' && $bundle == 'entity_test' && !empty($fields[$field_name])) {
  170. // Set a property constraint using
  171. // \Drupal\Core\Field\FieldConfigInterface::setPropertyConstraints().
  172. $fields[$field_name]->setPropertyConstraints('value', [
  173. 'TestField' => [
  174. 'value' => -2,
  175. 'message' => t('%name does not accept the value @value.', ['%name' => $field_name, '@value' => -2]),
  176. ],
  177. ]);
  178. // Add a property constraint using
  179. // \Drupal\Core\Field\FieldConfigInterface::addPropertyConstraints().
  180. $fields[$field_name]->addPropertyConstraints('value', [
  181. 'Range' => [
  182. 'min' => 0,
  183. 'max' => 32,
  184. ],
  185. ]);
  186. }
  187. }
  188. /**
  189. * Implements hook_field_ui_preconfigured_options_alter().
  190. */
  191. function field_test_field_ui_preconfigured_options_alter(array &$options, $field_type) {
  192. if ($field_type === 'test_field_with_preconfigured_options') {
  193. $options['custom_options']['entity_view_display']['settings'] = [
  194. 'test_formatter_setting_multiple' => 'altered dummy test string',
  195. ];
  196. }
  197. }