diff options
Diffstat (limited to 'modules/simpletest/tests')
-rw-r--r-- | modules/simpletest/tests/field_test.info | 9 | ||||
-rw-r--r-- | modules/simpletest/tests/field_test.install | 77 | ||||
-rw-r--r-- | modules/simpletest/tests/field_test.module | 1278 |
3 files changed, 0 insertions, 1364 deletions
diff --git a/modules/simpletest/tests/field_test.info b/modules/simpletest/tests/field_test.info deleted file mode 100644 index 88c67264c..000000000 --- a/modules/simpletest/tests/field_test.info +++ /dev/null @@ -1,9 +0,0 @@ -;$Id$ -name = "Field API Test" -description = "Support module for the Field API tests." -core = 7.x -package = Testing -files[] = field_test.module -files[] = field_test.install -version = VERSION -hidden = TRUE diff --git a/modules/simpletest/tests/field_test.install b/modules/simpletest/tests/field_test.install deleted file mode 100644 index 2bb1701bf..000000000 --- a/modules/simpletest/tests/field_test.install +++ /dev/null @@ -1,77 +0,0 @@ -<?php -// $Id$ - -/** - * @file - * Install, update and uninstall functions for the field_test module. - */ - -/** - * Implement hook_install(). - */ -function field_test_install() { - // hook_entity_info_alter() needs to be executed as last. - db_update('system') - ->fields(array('weight' => 1)) - ->condition('name', 'field_test') - ->execute(); -} - -/** - * Implement hook_schema(). - */ -function field_test_schema() { - $schema['test_entity'] = array( - 'description' => 'The base table for test_entities.', - 'fields' => array( - 'ftid' => array( - 'description' => 'The primary identifier for a test_entity.', - 'type' => 'serial', - 'unsigned' => TRUE, - 'not null' => TRUE, - ), - 'ftvid' => array( - 'description' => 'The current {test_entity_revision}.ftvid version identifier.', - 'type' => 'int', - 'unsigned' => TRUE, - 'not null' => TRUE, - 'default' => 0, - ), - 'fttype' => array( - 'description' => 'The type of this test_entity.', - 'type' => 'varchar', - 'length' => 32, - 'not null' => TRUE, - 'default' => '', - ), - ), - 'unique keys' => array( - 'ftvid' => array('ftvid'), - ), - 'primary key' => array('ftid'), - ); - $schema['test_entity_revision'] = array( - 'description' => 'Stores information about each saved version of a {test_entity}.', - 'fields' => array( - 'ftid' => array( - 'description' => 'The {test_entity} this version belongs to.', - 'type' => 'int', - 'unsigned' => TRUE, - 'not null' => TRUE, - 'default' => 0, - ), - 'ftvid' => array( - 'description' => 'The primary identifier for this version.', - 'type' => 'serial', - 'unsigned' => TRUE, - 'not null' => TRUE, - ), - ), - 'indexes' => array( - 'nid' => array('ftid'), - ), - 'primary key' => array('ftvid'), - ); - - return $schema; -} diff --git a/modules/simpletest/tests/field_test.module b/modules/simpletest/tests/field_test.module deleted file mode 100644 index a3cd45125..000000000 --- a/modules/simpletest/tests/field_test.module +++ /dev/null @@ -1,1278 +0,0 @@ -<?php -// $Id$ - -define('FIELD_TEST_ELEMENT_ID', 1); -define('FIELD_TEST_BUNDLE', 'test_bundle'); - -/** - * Implement hook_permission(). - */ -function field_test_permission() { - $perms = array( - 'access field_test content' => array( - 'title' => t('Access field_test content'), - 'description' => t('View published field_test content.'), - ), - 'administer field_test content' => array( - 'title' => t('Administer field_test content'), - 'description' => t('Manage field_test content'), - ), - ); - return $perms; -} - -/** - * Implement hook_menu(). - */ -function field_test_menu() { - $items = array(); - $bundles = field_info_bundles('test_entity'); - - foreach ($bundles as $bundle_name => $bundle_info) { - $bundle_url_str = str_replace('_', '-', $bundle_name); - $items['test-entity/add/' . $bundle_url_str] = array( - 'title' => t('Add %bundle test_entity', array('%bundle' => $bundle_info['label'])), - 'page callback' => 'field_test_entity_add', - 'page arguments' => array(2), - 'access arguments' => array('administer field_test content'), - 'type' => MENU_NORMAL_ITEM, - ); - } - $items['test-entity/%field_test_entity_test/edit'] = array( - 'title' => 'Edit test entity', - 'page callback' => 'field_test_entity_edit', - 'page arguments' => array(1), - 'access arguments' => array('administer field_test content'), - 'type' => MENU_NORMAL_ITEM, - ); - - return $items; -} - -/** - * Implements hook_field_access(). - */ -function field_test_field_access($op, $field, $obj_type, $object, $account) { - if ($field['field_name'] == "field_no_{$op}_access") { - return FALSE; - } - return TRUE; -} - -/** - * - * 'Field attach' API. - * - */ - - -/** - * Define a test fieldable entity. - */ -function field_test_entity_info() { - $bundles = variable_get('field_test_bundles', array('test_bundle' => array('label' => 'Test Bundle'))); - return array( - 'test_entity' => array( - 'name' => t('Test Entity'), - 'object keys' => array( - 'id' => 'ftid', - 'revision' => 'ftvid', - 'bundle' => 'fttype', - ), - 'cacheable' => FALSE, - 'bundles' => $bundles, - 'fieldable' => TRUE, - ), - // This entity type doesn't get form handling for now... - 'test_cacheable_entity' => array( - 'name' => t('Test Entity, cacheable'), - 'object keys' => array( - 'id' => 'ftid', - 'revision' => 'ftvid', - 'bundle' => 'fttype', - ), - 'fieldable' => TRUE, - 'cacheable' => TRUE, - 'bundles' => $bundles, - ), - ); -} - -/** - * Implement hook_entity_info_alter(). - */ -function field_test_entity_info_alter(&$entity_info) { - // Enable/disable field_test as a translation handler. - foreach (field_test_entity_info_translatable() as $obj_type => $translatable) { - $entity_info[$obj_type]['translation']['field_test'] = $translatable; - } - // Disable locale as a translation handler. - foreach ($entity_info as $obj_type => $info) { - $entity_info[$obj_type]['translation']['locale'] = FALSE; - } -} - -/** - * Implement hook_field_widget_settings_form(). - */ -function field_test_field_widget_settings_form($field, $instance) { - $widget = $instance['widget']; - $settings = $widget['settings']; - - $form['test_widget_setting'] = array( - '#type' => 'textfield', - '#title' => t('Field test field widget setting'), - '#default_value' => $settings['test_widget_setting'], - '#required' => FALSE, - '#description' => t('A dummy form element to simulate field widget setting.'), - ); - - return $form; -} - -/** - * Implement hook_field_instance_settings_form(). - */ -function field_test_field_instance_settings_form($field, $instance) { - $settings = $instance['settings']; - - $form['test_instance_setting'] = array( - '#type' => 'textfield', - '#title' => t('Field test field instance setting'), - '#default_value' => $settings['test_instance_setting'], - '#required' => FALSE, - '#description' => t('A dummy form element to simulate field instance setting.'), - ); - - return $form; -} - -/** - * Implement hook_field_settings_form(). - */ -function field_test_field_settings_form($field, $instance, $has_data) { - $settings = $field['settings']; - - $form['test_field_setting'] = array( - '#type' => 'textfield', - '#title' => t('Field test field setting'), - '#default_value' => $settings['test_field_setting'], - '#required' => FALSE, - '#description' => t('A dummy form element to simulate field setting.'), - ); - - return $form; -} - - -/** - * Create a new bundle for test_entity objects. - * - * @param $bundle - * The machine-readable name of the bundle. - * @param $text - * The human-readable name of the bundle. If none is provided, the machine - * name will be used. - */ -function field_test_create_bundle($bundle, $text = NULL) { - $bundles = variable_get('field_test_bundles', array('test_bundle' => array('label' => 'Test Bundle'))); - $bundles += array($bundle => array('label' => $text ? $text : $bundle)); - variable_set('field_test_bundles', $bundles); - - $info = field_test_entity_info(); - foreach ($info as $type => $type_info) { - field_attach_create_bundle($type, $bundle); - } -} - -/** - * Rename a bundle for test_entity objects. - * - * @param $bundle_old - * The machine-readable name of the bundle to rename. - * @param $bundle_new - * The new machine-readable name of the bundle. - */ -function field_test_rename_bundle($bundle_old, $bundle_new) { - $bundles = variable_get('field_test_bundles', array('test_bundle' => array('label' => 'Test Bundle'))); - $bundles[$bundle_new] = $bundles[$bundle_old]; - unset($bundles[$bundle_old]); - variable_set('field_test_bundles', $bundles); - - $info = field_test_entity_info(); - foreach ($info as $type => $type_info) { - field_attach_rename_bundle($type, $bundle_old, $bundle_new); - } -} - -/** - * Delete a bundle for test_entity objects. - * - * @param $bundle - * The machine-readable name of the bundle to delete. - */ -function field_test_delete_bundle($bundle) { - $bundles = variable_get('field_test_bundles', array('test_bundle' => array('label' => 'Test Bundle'))); - unset($bundles[$bundle]); - variable_set('field_test_bundles', $bundles); - - $info = field_test_entity_info(); - foreach ($info as $type => $type_info) { - field_attach_delete_bundle($type, $bundle); - } -} - -/** - * Implement hook_field_build_modes(). - */ -function field_test_field_build_modes($obj_type) { - $modes = array(); - if ($obj_type == 'test_entity' || $obj_type == 'test_cacheable_entity') { - $modes = array( - 'full' => t('Full node'), - 'teaser' => t('Teaser'), - ); - } - return $modes; -} - -/** - * Helper function to create a basic 'test entity' structure. - * - * TODO : do we stil need this now that we can actualy load and save test_entities ? - */ -function field_test_create_stub_entity($id = 1, $vid = 1, $bundle = FIELD_TEST_BUNDLE) { - $entity = new stdClass(); - // Only set id and vid properties if they don't come as NULL (creation form). - if (isset($id)) { - $entity->ftid = $id; - } - if (isset($vid)) { - $entity->ftvid = $vid; - } - $entity->fttype = $bundle; - - return $entity; -} - -function field_test_entity_test_load($ftid, $ftvid = NULL) { - // Load basic strucure. - $query = db_select('test_entity', 'fte', array()) - ->fields('fte') - ->condition('ftid', $ftid); - if ($ftvid) { - $query->condition('ftvid', $ftvid); - } - $entities = $query->execute()->fetchAllAssoc('ftid'); - - // Attach fields. - if ($ftvid) { - field_attach_load_revision('test_entity', $entities); - } - else { - field_attach_load('test_entity', $entities); - } - - return $entities[$ftid]; -} - -function field_test_entity_save(&$entity) { - field_attach_presave('test_entity', $entity); - - if (!isset($entity->is_new)) { - $entity->is_new = empty($entity->ftid); - } - - if (!$entity->is_new && !empty($entity->revision)) { - $entity->old_ftvid = $entity->ftvid; - unset($entity->ftvid); - } - - $update_entity = TRUE; - if ($entity->is_new) { - drupal_write_record('test_entity', $entity); - drupal_write_record('test_entity_revision', $entity); - $op = 'insert'; - } - else { - drupal_write_record('test_entity', $entity, 'ftid'); - if (!empty($entity->revision)) { - drupal_write_record('test_entity_revision', $entity); - } - else { - drupal_write_record('test_entity_revision', $entity, 'ftvid'); - $update_entity = FALSE; - } - $op = 'update'; - } - if ($update_entity) { - db_update('test_entity') - ->fields(array('ftvid' => $entity->ftvid)) - ->condition('ftid', $entity->ftid) - ->execute(); - } - - // Save fields. - $function = "field_attach_$op"; - $function('test_entity', $entity); -} - -function field_test_entity_add($fttype) { - $fttype = str_replace('-', '_', $fttype); - $entity = (object)array('fttype' => $fttype); - drupal_set_title(t('Create test_entity @bundle', array('@bundle' => $fttype)), PASS_THROUGH); - return drupal_get_form('field_test_entity_form', $entity, TRUE); -} - -function field_test_entity_edit($entity) { - drupal_set_title(t('test_entity @ftid revision @ftvid', array('@ftid' => $entity->ftid, '@ftvid' => $entity->ftvid)), PASS_THROUGH); - return drupal_get_form('field_test_entity_form', $entity); -} - -/** - * Form to set the value of fields attached to our entity. - */ -function field_test_entity_form($form, &$form_state, $entity, $add = FALSE) { - if (isset($form_state['test_entity'])) { - $entity = $form_state['test_entity'] + (array)$entity; - } - $entity = (object)$entity; - - foreach (array('ftid', 'ftvid', 'fttype') as $key) { - $form[$key] = array( - '#type' => 'value', - '#value' => isset($entity->$key) ? $entity->$key : NULL, - ); - } - - // Add field widgets. - $form['#builder_function'] = 'field_test_entity_form_submit_builder'; - field_attach_form('test_entity', $entity, $form, $form_state); - - if (!$add) { - $form['revision'] = array( - '#access' => user_access('administer field_test content'), - '#type' => 'checkbox', - '#title' => t('Create new revision'), - '#default_value' => FALSE, - '#weight' => 100, - ); - } - $form['submit'] = array( - '#type' => 'submit', - '#value' => t('Save'), - '#weight' => 101, - ); - - return $form; -} - -/** - * Validate handler for field_test_set_field_values(). - */ -function field_test_entity_form_validate($form, &$form_state) { - $entity = field_test_create_stub_entity($form_state['values']['ftid'], $form_state['values']['ftvid'], $form_state['values']['fttype']); - field_attach_form_validate('test_entity', $entity, $form, $form_state); -} - -/** - * Submit handler for field_test_set_field_values(). - */ -function field_test_entity_form_submit($form, &$form_state) { - $entity = field_test_entity_form_submit_builder($form, $form_state); - $insert = empty($entity->ftid); - field_test_entity_save($entity); - - $message = $insert ? t('test_entity @id has been created.', array('@id' => $entity->ftid)) : t('test_entity @id has been updated.', array('@id' => $entity->ftid)); - drupal_set_message($message); - - if ($entity->ftid) { - unset($form_state['rebuild']); - $form_state['redirect'] = 'test-entity/' . $entity->ftid . '/edit'; - } - else { - // Error on save. - drupal_set_message(t('The entity could not be saved.'), 'error'); - } - -} - -/** - * Build a test_entity by processing submitted form values and prepare for a form rebuild. - */ -function field_test_entity_form_submit_builder($form, &$form_state) { - $entity = field_test_create_stub_entity($form_state['values']['ftid'], $form_state['values']['ftvid'], $form_state['values']['fttype']); - $entity->revision = !empty($form_state['values']['revision']); - field_attach_submit('test_entity', $entity, $form, $form_state); - - $form_state['test_entity'] = (array)$entity; - $form_state['rebuild'] = TRUE; - - return $entity; -} - -/** - * - * 'Field type' API. - * - */ - -/** - * Implement hook_field_info(). - */ -function field_test_field_info() { - return array( - 'test_field' => array( - 'label' => t('Test Field'), - 'description' => t('Dummy field type used for tests.'), - 'settings' => array( - 'test_field_setting' => 'dummy test string', - 'changeable' => 'a changeable field setting', - 'unchangeable' => 'an unchangeable field setting', - ), - 'instance_settings' => array( - 'test_instance_setting' => 'dummy test string', - 'test_hook_field_load' => FALSE, - ), - 'default_widget' => 'test_field_widget', - 'default_formatter' => 'field_test_default', - ), - ); -} - -/** - * Implement hook_field_update_forbid(). - */ -function field_test_field_update_forbid($field, $prior_field, $has_data) { - if ($field['type'] == 'test_field' && $field['settings']['unchangeable'] != $prior_field['settings']['unchangeable']) { - throw new FieldException("field_test 'unchangeable' setting cannot be changed'"); - } -} - -/** - * Implement hook_field_schema(). - */ -function field_test_field_schema($field) { - return array( - 'columns' => array( - 'value' => array( - 'type' => 'int', - 'size' => 'tiny', - 'not null' => FALSE, - ), - ), - 'indexes' => array( - 'value' => array('value'), - ), - ); -} - -/** - * Implement hook_field_load(). - */ -function field_test_field_load($obj_type, $objects, $field, $instances, $langcode, &$items, $age) { - foreach ($items as $id => $item) { - // To keep the test non-intrusive, only act for instances with the - // test_hook_field_load setting explicitly set to TRUE. - if ($instances[$id]['settings']['test_hook_field_load']) { - foreach ($item as $delta => $value) { - // Don't add anything on empty values. - if ($value) { - $items[$id][$delta]['additional_key'] = 'additional_value'; - } - } - } - } -} - -/** - * Implement hook_field_validate(). - * - * Possible error codes: - * - 'field_test_invalid': The value is invalid. - */ -function field_test_field_validate($obj_type, $object, $field, $instance, $langcode, $items, &$errors) { - foreach ($items as $delta => $item) { - if ($item['value'] == -1) { - $errors[$field['field_name']][$langcode][$delta][] = array( - 'error' => 'field_test_invalid', - 'message' => t('%name does not accept the value -1.', array('%name' => $instance['label'])), - ); - } - } -} - -/** - * Implement hook_field_sanitize(). - */ -function field_test_field_sanitize($obj_type, $object, $field, $instance, $langcode, &$items) { - foreach ($items as $delta => $item) { - $value = check_plain($item['value']); - $items[$delta]['safe'] = $value; - } -} - -/** - * Implement hook_field_is_empty(). - */ -function field_test_field_is_empty($item, $field) { - return empty($item['value']); -} - -/** - * Implement hook_field_widget_info(). - * - * Here we indicate that the field module will handle - * the default value and multiple values for these widgets. - * - * Callbacks can be omitted if default handing is used. - * They're included here just so this module can be used - * as an example for custom modules that might do things - * differently. - */ -function field_test_field_widget_info() { - return array( - 'test_field_widget' => array( - 'label' => t('Test field'), - 'field types' => array('test_field'), - 'settings' => array('test_widget_setting' => 'dummy test string'), - 'behaviors' => array( - 'multiple values' => FIELD_BEHAVIOR_DEFAULT, - 'default value' => FIELD_BEHAVIOR_DEFAULT, - ), - ), - 'test_field_widget_multiple' => array( - 'label' => t('Test field 1'), - 'field types' => array('test_field'), - 'settings' => array('test_widget_setting_multiple' => 'dummy test string'), - 'behaviors' => array( - 'multiple values' => FIELD_BEHAVIOR_CUSTOM, - 'default value' => FIELD_BEHAVIOR_DEFAULT, - ), - ), - ); -} - -/** - * Implement hook_field_widget(). - */ -function field_test_field_widget(&$form, &$form_state, $field, $instance, $langcode, $items, $delta, $element) { - $element = array( - 'value' => $element + array( - '#type' => 'textfield', - '#default_value' => isset($items[$delta]['value']) ? $items[$delta]['value'] : '', - ), - ); - return $element; -} - -/** - * Implement hook_field_widget_error(). - */ -function field_test_field_widget_error($element, $error) { - form_error($element['value'], $error['message']); -} - -/** - * Implement hook_field_formatter_info(). - */ -function field_test_field_formatter_info() { - return array( - 'field_test_default' => array( - 'label' => t('Default'), - 'description' => t('Default formatter'), - 'field types' => array('test_field'), - 'settings' => array( - 'test_formatter_setting' => 'dummy test string', - ), - 'behaviors' => array( - 'multiple values' => FIELD_BEHAVIOR_DEFAULT, - ), - ), - 'field_test_multiple' => array( - 'label' => t('Multiple'), - 'description' => t('Multiple formatter'), - 'field types' => array('test_field'), - 'settings' => array( - 'test_formatter_setting_multiple' => 'dummy test string', - ), - 'behaviors' => array( - 'multiple values' => FIELD_BEHAVIOR_CUSTOM, - ), - ), - 'field_test_needs_additional_data' => array( - 'label' => t('Tests hook_field_formatter_prepare_view()'), - 'field types' => array('test_field'), - 'settings' => array( - 'test_formatter_setting_additional' => 'dummy test string', - ), - ), - ); -} - -/** - * Implement hook_field_formatter_prepare_view(). - */ -function field_test_field_formatter_prepare_view($obj_type, $objects, $field, $instances, $langcode, &$items, $build_mode) { - foreach ($items as $id => $item) { - // To keep the test non-intrusive, only act on the - // 'field_test_needs_additional_data' formatter. - if ($instances[$id]['display'][$build_mode]['type'] == 'field_test_needs_additional_data') { - foreach ($item as $delta => $value) { - // Don't add anything on empty values. - if ($value) { - $items[$id][$delta]['additional_formatter_value'] = $value['value'] + 1; - } - } - } - } -} - -/** - * Theme function for 'field_test_default' formatter. - */ -function theme_field_formatter_field_test_default($variables) { - $element = $variables['element']; - - $value = $element['#item']['value']; - $settings = $element['#settings']; - - return $settings['test_formatter_setting'] . '|' . $value; -} - -/** - * Theme function for 'field_test_multiple' formatter. - */ -function theme_field_formatter_field_test_multiple($variables) { - $element = $variables['element']; - - $settings = $element['#settings']; - - $items = array(); - foreach (element_children($element) as $key) { - $items[$key] = $key .':'. $element[$key]['#item']['value']; - } - $output = implode('|', $items); - return $settings['test_formatter_setting_multiple'] . '|' . $output; -} - -/** - * Theme function for 'field_test_needs_additional_data' formatter. - */ -function theme_field_formatter_field_test_needs_additional_data($variables) { - $element = $variables['element']; - $value = $element['#item']['value']; - $additional = $element['#item']['additional_formatter_value']; - $settings = $element['#settings']; - - return $settings['test_formatter_setting_additional'] . '|' . $value . '|' . $additional; -} - -/** - * Sample function to test default value assignment. - */ -function field_test_default_value($obj_type, $object, $field, $instance) { - return array(array('value' => 99)); -} - -/** - * Generic op to test _field_invoke behavior. - */ -function field_test_field_test_op($obj_type, $object, $field, $instance, $langcode, &$items) { - return array($langcode => md5(serialize(array($obj_type, $object, $field['field_name'], $langcode, $items)))); -} - -/** - * Generic op to test _field_invoke_multiple behavior. - */ -function field_test_field_test_op_multiple($obj_type, $objects, $field, $instances, $langcode, &$items) { - $result = array(); - foreach ($objects as $id => $object) { - $result[$id] = array($langcode => md5(serialize(array($obj_type, $object, $field['field_name'], $langcode, $items[$id])))); - } - return $result; -} - -/** - * Implement hook_field_languages(). - */ -function field_test_field_languages($obj_type, $field, &$languages) { - if ($field['settings']['test_hook_in']) { - // Add an unavailable language. - $languages[] = 'xx'; - // Remove an available language. - unset($languages[0]); - } -} - -/** - * Helper function to enable entity translations. - */ -function field_test_entity_info_translatable($obj_type = NULL, $translatable = NULL) { - $stored_value = &drupal_static(__FUNCTION__, array()); - if (isset($obj_type)) { - $stored_value[$obj_type] = $translatable; - drupal_static_reset('entity_get_info'); - cache_clear_all('entity_info', 'cache'); - } - return $stored_value; -} - -/** - * - * 'Field storage' API. - * - */ - -/** - * Implement hook_field_storage_info(). - */ -function field_test_field_storage_info() { - return array( - 'field_test_storage' => array( - 'label' => t('Test storage'), - 'description' => t('Dummy test storage backend. Stores field values in the variable table.'), - ), - 'field_test_storage_failure' => array( - 'label' => t('Test storage failure'), - 'description' => t('Dummy test storage backend. Always fails to create fields.'), - ), - ); -} - -/** - * Implement hook_field_storage_details(). - */ -function field_test_field_storage_details($field, $instance) { - $details = array(); - - // Add field columns. - $columns = array(); - foreach ((array) $field['columns'] as $column_name => $attributes) { - $columns[$column_name] = $column_name; - } - return array( - 'drupal_variables' => array( - 'field_test_storage_data[FIELD_LOAD_CURRENT]' => $columns, - 'field_test_storage_data[FIELD_LOAD_REVISION]' => $columns, - ), - ); -} - -/** - * Implement hook_field_storage_details_alter(). - * - * @see FieldAttachStorageTestCase::testFieldStorageDetailsAlter() - */ -function field_test_field_storage_details_alter(&$details, $field, $instance) { - - // For testing, storage details are changed only because of the field name. - if ($field['field_name'] == 'field_test_change_my_details') { - $columns = array(); - foreach ((array) $field['columns'] as $column_name => $attributes) { - $columns[$column_name] = $column_name; - } - $details['drupal_variables'] = array( - FIELD_LOAD_CURRENT => array( - 'moon' => $columns, - ), - FIELD_LOAD_REVISION => array( - 'mars' => $columns, - ), - ); - } -} - -/** - * Helper function: store or retrieve data from the 'storage backend'. - */ -function _field_test_storage_data($data = NULL) { - if (is_null($data)) { - return variable_get('field_test_storage_data', array()); - } - else { - variable_set('field_test_storage_data', $data); - } -} - -/** - * Implement hook_field_storage_load(). - */ -function field_test_field_storage_load($obj_type, $objects, $age, $fields, $options) { - $data = _field_test_storage_data(); - - $load_current = $age == FIELD_LOAD_CURRENT; - - foreach ($fields as $field_id => $ids) { - $field = field_info_field_by_id($field_id); - $field_name = $field['field_name']; - $field_data = $data[$field['id']]; - $sub_table = $load_current ? 'current' : 'revisions'; - $delta_count = array(); - foreach ($field_data[$sub_table] as $row) { - if ($row->type == $obj_type && (!$row->deleted || $options['deleted'])) { - if (($load_current && in_array($row->entity_id, $ids)) || (!$load_current && in_array($row->revision_id, $ids))) { - if (in_array($row->language, field_multilingual_available_languages($obj_type, $field))) { - if (!isset($delta_count[$row->entity_id][$row->language])) { - $delta_count[$row->entity_id][$row->language] = 0; - } - if ($field['cardinality'] == FIELD_CARDINALITY_UNLIMITED || $delta_count[$row->entity_id][$row->language] < $field['cardinality']) { - $item = array(); - foreach ($field['columns'] as $column => $attributes) { - $item[$column] = $row->{$column}; - } - $objects[$row->entity_id]->{$field_name}[$row->language][] = $item; - $delta_count[$row->entity_id][$row->language]++; - } - } - } - } - } - } -} - -/** - * Implement hook_field_storage_write(). - */ -function field_test_field_storage_write($obj_type, $object, $op, $fields) { - $data = _field_test_storage_data(); - - list($id, $vid, $bundle) = entity_extract_ids($obj_type, $object); - - foreach ($fields as $field_id) { - $field = field_info_field_by_id($field_id); - $field_name = $field['field_name']; - $field_data = &$data[$field_id]; - - $all_languages = field_multilingual_available_languages($obj_type, $field); - $field_languages = array_intersect($all_languages, array_keys((array) $object->$field_name)); - - // Delete and insert, rather than update, in case a value was added. - if ($op == FIELD_STORAGE_UPDATE) { - // Delete languages present in the incoming $object->$field_name. - // Delete all languages if $object->$field_name is empty. - $languages = !empty($object->$field_name) ? $field_languages : $all_languages; - if ($languages) { - foreach ($field_data['current'] as $key => $row) { - if ($row->type == $obj_type && $row->entity_id == $id && in_array($row->language, $languages)) { - unset($field_data['current'][$key]); - } - } - if (isset($vid)) { - foreach ($field_data['revisions'] as $key => $row) { - if ($row->type == $obj_type && $row->revision_id == $vid) { - unset($field_data['revisions'][$key]); - } - } - } - } - } - - foreach ($field_languages as $langcode) { - $items = (array) $object->{$field_name}[$langcode]; - $delta_count = 0; - foreach ($items as $delta => $item) { - $row = (object) array( - 'field_id' => $field_id, - 'type' => $obj_type, - 'entity_id' => $id, - 'revision_id' => $vid, - 'bundle' => $bundle, - 'delta' => $delta, - 'deleted' => FALSE, - 'language' => $langcode, - ); - foreach ($field['columns'] as $column => $attributes) { - $row->{$column} = isset($item[$column]) ? $item[$column] : NULL; - } - - $field_data['current'][] = $row; - if (isset($vid)) { - $field_data['revisions'][] = $row; - } - - if ($field['cardinality'] != FIELD_CARDINALITY_UNLIMITED && ++$delta_count == $field['cardinality']) { - break; - } - } - } - } - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_storage_delete(). - */ -function field_test_field_storage_delete($obj_type, $object, $fields) { - list($id, $vid, $bundle) = entity_extract_ids($obj_type, $object); - - // Note: reusing field_test_storage_purge(), like field_sql_storage.module - // does, is highly inefficient in our case... - foreach (field_info_instances($bundle) as $instance) { - if (isset($fields[$instance['field_id']])) { - $field = field_info_field_by_id($instance['field_id']); - field_test_field_storage_purge($obj_type, $object, $field, $instance); - } - } -} - -/** - * Implement hook_field_storage_purge(). - */ -function field_test_field_storage_purge($obj_type, $object, $field, $instance) { - $data = _field_test_storage_data(); - - list($id, $vid, $bundle) = entity_extract_ids($obj_type, $object); - - $field_data = &$data[$field['id']]; - foreach (array('current', 'revisions') as $sub_table) { - foreach ($field_data[$sub_table] as $key => $row) { - if ($row->type == $obj_type && $row->entity_id == $id) { - unset($field_data[$sub_table][$key]); - } - } - } - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_storage_delete_revision(). - */ -function field_test_field_storage_delete_revision($obj_type, $object, $fields) { - $data = _field_test_storage_data(); - - list($id, $vid, $bundle) = entity_extract_ids($obj_type, $object); - foreach ($fields as $field_id) { - $field_data = &$data[$field_id]; - foreach (array('current', 'revisions') as $sub_table) { - foreach ($field_data[$sub_table] as $key => $row) { - if ($row->type == $obj_type && $row->entity_id == $id && $row->revision_id == $vid) { - unset($field_data[$sub_table][$key]); - } - } - } - } - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_storage_query(). - */ -function field_test_field_storage_query($field_id, $conditions, $count, &$cursor = NULL, $age) { - $data = _field_test_storage_data(); - - $load_current = $age == FIELD_LOAD_CURRENT; - - $field = field_info_field_by_id($field_id); - $field_columns = array_keys($field['columns']); - - $field_data = $data[$field['id']]; - $sub_table = $load_current ? 'current' : 'revisions'; - // We need to sort records by object type and object id. - usort($field_data[$sub_table], '_field_test_field_storage_query_sort_helper'); - - // Initialize results array. - $return = array(); - $obj_count = 0; - $rows_count = 0; - $rows_total = count($field_data[$sub_table]); - $skip = $cursor; - $skipped = 0; - - foreach ($field_data[$sub_table] as $row) { - if ($count != FIELD_QUERY_NO_LIMIT && $obj_count >= $count) { - break; - } - - if ($row->field_id == $field['id']) { - $match = TRUE; - $condition_deleted = FALSE; - // Add conditions. - foreach ($conditions as $condition) { - @list($column, $value, $operator) = $condition; - if (empty($operator)) { - $operator = is_array($value) ? 'IN' : '='; - } - switch ($operator) { - case '=': - $match = $match && $row->{$column} == $value; - break; - case '!=': - case '<': - case '<=': - case '>': - case '>=': - eval('$match = $match && '. $row->{$column} . ' ' . $operator . ' '. $value); - break; - case 'IN': - $match = $match && in_array($row->{$column}, $value); - break; - case 'NOT IN': - $match = $match && !in_array($row->{$column}, $value); - break; - case 'BETWEEN': - $match = $match && $row->{$column} >= $value[0] && $row->{$column} <= $value[1]; - break; - case 'STARTS_WITH': - case 'ENDS_WITH': - case 'CONTAINS': - // Not supported. - $match = FALSE; - break; - } - // Track condition on 'deleted'. - if ($column == 'deleted') { - $condition_deleted = TRUE; - } - } - - // Exclude deleted data unless we have a condition on it. - if (!$condition_deleted && $row->deleted) { - $match = FALSE; - } - - if ($match) { - if (is_null($skip) || $skipped >= $skip) { - $cursor++; - // If querying all revisions and the entity type has revisions, we need - // to key the results by revision_ids. - $entity_type = entity_get_info($row->type); - $id = ($load_current || empty($entity_type['object keys']['revision'])) ? $row->entity_id : $row->revision_id; - - if (!isset($return[$row->type][$id])) { - $return[$row->type][$id] = entity_create_stub_entity($row->type, array($row->entity_id, $row->revision_id, $row->bundle)); - $obj_count++; - } - } - else { - $skipped++; - } - } - } - $rows_count++; - - // The query is complete if we walked the whole array. - if ($count != FIELD_QUERY_NO_LIMIT && $rows_count >= $rows_total) { - $cursor = FIELD_QUERY_COMPLETE; - } - } - - return $return; -} - -/** - * Sort helper for field_test_field_storage_query(). - * - * Sort by object type and object id. - */ -function _field_test_field_storage_query_sort_helper($a, $b) { - if ($a->type == $b->type) { - if ($a->entity_id == $b->entity_id) { - return 0; - } - else { - return $a->entity_id < $b->entity_id ? -1 : 1; - } - } - else { - return $a->type < $b->type ? -1 : 1; - } -} - -/** - * Implement hook_field_storage_create_field(). - */ -function field_test_field_storage_create_field($field) { - if ($field['storage']['type'] == 'field_test_storage_failure') { - throw new Exception('field_test_storage_failure engine always fails to create fields'); - } - - $data = _field_test_storage_data(); - - $data[$field['id']] = array( - 'current' => array(), - 'revisions' => array(), - ); - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_storage_delete_field(). - */ -function field_test_field_storage_delete_field($field) { - $data = _field_test_storage_data(); - - $field_data = &$data[$field['id']]; - foreach (array('current', 'revisions') as $sub_table) { - foreach ($field_data[$sub_table] as &$row) { - $row->deleted = TRUE; - } - } - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_storage_delete_instance(). - */ -function field_test_field_storage_delete_instance($instance) { - $data = _field_test_storage_data(); - - $field = field_info_field($instance['field_name']); - $field_data = &$data[$field['id']]; - foreach (array('current', 'revisions') as $sub_table) { - foreach ($field_data[$sub_table] as &$row) { - if ($row->bundle == $instance['bundle']) { - $row->deleted = TRUE; - } - } - } - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_attach_create_bundle(). - */ -function field_test_field_attach_create_bundle($bundle) { - // We don't need to do anything here. -} - -/** - * Implement hook_field_attach_rename_bundle(). - */ -function field_test_field_attach_rename_bundle($bundle_old, $bundle_new) { - $data = _field_test_storage_data(); - - // We need to account for deleted or inactive fields and instances. - $instances = field_read_instances(array('bundle' => $bundle_new), array('include_deleted' => TRUE, 'include_inactive' => TRUE)); - foreach ($instances as $field_name => $instance) { - $field = field_info_field_by_id($instance['field_id']); - if ($field['storage']['type'] == 'field_test_storage') { - $field_data = &$data[$field['id']]; - foreach (array('current', 'revisions') as $sub_table) { - foreach ($field_data[$sub_table] as &$row) { - if ($row->bundle == $bundle_old) { - $row->bundle = $bundle_new; - } - } - } - } - } - - _field_test_storage_data($data); -} - -/** - * Implement hook_field_attach_delete_bundle(). - */ -function field_test_field_attach_delete_bundle($bundle, $instances) { - $data = _field_test_storage_data(); - - $instances = field_info_instances($bundle); - foreach ($instances as $field_name => $instance) { - $field = field_info_field($field_name); - if ($field['storage']['type'] == 'field_test_storage') { - $field_data = &$data[$field['id']]; - foreach (array('current', 'revisions') as $sub_table) { - foreach ($field_data[$sub_table] as &$row) { - if ($row->bundle == $bundle_old) { - $row->deleted = TRUE; - } - } - } - } - } - - _field_test_storage_data($data); -} - -/** - * Store and retrieve keyed data for later verification by unit tests. - * - * This function is a simple in-memory key-value store with the - * distinction that it stores all values for a given key instead of - * just the most recently set value. field_test module hooks call - * this function to record their arguments, keyed by hook name. The - * unit tests later call this function to verify that the correct - * hooks were called and were passed the correct arguments. - * - * This function ignores all calls until the first time it is called - * with $key of NULL. Each time it is called with $key of NULL, it - * erases all previously stored data from its internal cache, but also - * returns the previously stored data to the caller. A typical usage - * scenario is: - * - * @code - * // calls to field_test_memorize() here are ignored - * - * // turn on memorization - * field_test_memorize(); - * - * // call some Field API functions that invoke field_test hooks - * $field = field_create_field(...); - * - * // retrieve and reset the memorized hook call data - * $mem = field_test_memorize(); - * - * // make sure hook_field_create_field() is invoked correctly - * assertEqual(count($mem['field_test_field_create_field']), 1); - * assertEqual($mem['field_test_field_create_field'][0], array($field)); - * @endcode - * - * @param $key - * The key under which to store to $value, or NULL as described above. - * @param $value - * A value to store for $key. - * @return - * An array mapping each $key to an array of each $value passed in - * for that key. - */ -function field_test_memorize($key = NULL, $value = NULL) { - $memorize = &drupal_static(__FUNCTION__, NULL); - - if (is_null($key)) { - $return = $memorize; - $memorize = array(); - return $return; - } - if (is_array($memorize)) { - $memorize[$key][] = $value; - } -} - -/** - * Memorize calls to hook_field_create_field(). - */ -function field_test_field_create_field($field) { - $args = func_get_args(); - field_test_memorize(__FUNCTION__, $args); -} - -/** - * Memorize calls to hook_field_insert(). - */ -function field_test_field_insert($obj_type, $object, $field, $instance, $items) { - $args = func_get_args(); - field_test_memorize(__FUNCTION__, $args); -} - -/** - * Memorize calls to hook_field_update(). - */ -function field_test_field_update($obj_type, $object, $field, $instance, $items) { - $args = func_get_args(); - field_test_memorize(__FUNCTION__, $args); -} - -/** - * Memorize calls to hook_field_delete(). - */ -function field_test_field_delete($obj_type, $object, $field, $instance, $items) { - $args = func_get_args(); - field_test_memorize(__FUNCTION__, $args); -} |