diff --git a/search_api.test b/search_api.test index 1748627..bc80cb4 100644 --- a/search_api.test +++ b/search_api.test @@ -43,13 +43,14 @@ class SearchApiWebTest extends DrupalWebTestCase { $this->insertItems(); $this->checkOverview1(); $this->createIndex(); - $this->insertItems(5); + $this->insertItems(); $this->createServer(); $this->checkOverview2(); $this->enableIndex(); $this->searchNoResults(); $this->indexItems(); $this->searchSuccess(); + $this->checkIndexingOrder(); $this->editServer(); $this->clearIndex(); $this->searchNoResults(); @@ -61,40 +62,19 @@ class SearchApiWebTest extends DrupalWebTestCase { $this->drupalPost('admin/config/search/search_api/index/default_node_index/delete', array(), t('Confirm')); } - protected function insertItems($offset = 0) { + protected function insertItems($number = 5) { $count = db_query('SELECT COUNT(*) FROM {search_api_test}')->fetchField(); - $this->insertItem(array( - 'id' => $offset + 1, - 'title' => 'Title 1', - 'body' => 'Body text 1.', - 'type' => 'Item', - )); - $this->insertItem(array( - 'id' => $offset + 2, - 'title' => 'Title 2', - 'body' => 'Body text 2.', - 'type' => 'Item', - )); - $this->insertItem(array( - 'id' => $offset + 3, - 'title' => 'Title 3', - 'body' => 'Body text 3.', - 'type' => 'Item', - )); - $this->insertItem(array( - 'id' => $offset + 4, - 'title' => 'Title 4', - 'body' => 'Body text 4.', - 'type' => 'Page', - )); - $this->insertItem(array( - 'id' => $offset + 5, - 'title' => 'Title 5', - 'body' => 'Body text 5.', - 'type' => 'Page', - )); + for ($i = 1; $i <= $number; ++$i) { + $id = $count + $i; + $this->insertItem(array( + 'id' => $id, + 'title' => "Title $id", + 'body' => "Body text $id.", + 'type' => 'Item', + )); + } $count = db_query('SELECT COUNT(*) FROM {search_api_test}')->fetchField() - $count; - $this->assertEqual($count, 5, '5 items successfully inserted.'); + $this->assertEqual($count, $number, "$number items successfully inserted."); } protected function insertItem($values) { @@ -299,8 +279,8 @@ class SearchApiWebTest extends DrupalWebTestCase { // Here we test the indexing + the warning message when some items // can not be indexed. - // The server refuses (for test purpose) to index items with IDs that are - // multiples of 8 unless the "search_api_test_index_all" variable is set. + // The server refuses (for test purpose) to index the item that has the same + // ID as the "search_api_test_indexing_break" variable (default: 8). $values = array( 'limit' => 8, ); @@ -322,7 +302,7 @@ class SearchApiWebTest extends DrupalWebTestCase { $this->assertText(t("Couldn't index items. Check the logs for details."), 'Index error is displayed.'); // Here we test the indexing of all the remaining items. - variable_set('search_api_test_index_all', TRUE); + variable_set('search_api_test_indexing_break', 0); $values = array( 'limit' => -1, ); @@ -344,6 +324,87 @@ class SearchApiWebTest extends DrupalWebTestCase { $this->assertText('results = (3, 4, 5, 6)', 'Correct search results with ranged query.'); } + protected function checkIndexingOrder() { + // Set cron batch size to 1 so not all items will get indexed right away. + $values = array( + 'options[cron_limit]' => 1, + ); + $this->drupalPost("admin/config/search/search_api/index/{$this->index_id}/edit", $values, t('Save settings')); + $this->assertText(t('The search index was successfully edited.')); + + // Manually clear the server's item storage – that way, the items will still + // count as indexed for the Search API, but won't be returned in searches. + // We do this so we have finer-grained control over the order in which items + // are indexed. + search_api_server_load($this->server_id, TRUE)->deleteItems(); + $this->drupalGet('search_api_test/query/' . $this->index_id); + $this->assertText('result count = 0', 'Indexed items were successfully deleted from the server.'); + $this->assertText('results = ()', 'Indexed items were successfully deleted from the server.'); + + // Now insert some new items, and mark others as changed. + $this->drupalGet('search_api_test/touch/8'); + $this->insertItems(1);// item 11 + $this->drupalGet('search_api_test/touch/2'); + $this->insertItems(1);// item 12 + $this->drupalGet('search_api_test/touch/5'); + $this->insertItems(1);// item 13 + $this->drupalGet('search_api_test/touch/8'); + $this->insertItems(1); // item 14 + + // Check whether the status display is right. + $this->drupalGet("admin/config/search/search_api/index/{$this->index_id}/status"); + $variables = array( + '@indexed' => 7, + '@total' => 14, + '@percentage' => 50, + ); + $this->assertText(t('About @percentage% of all items have been indexed in their latest version (@indexed / @total).', $variables), 'Correct index status displayed after inserting and changing items.'); + + // Indexing order should now be: 11, 12, 13, 14, 8, 2, 4. Let's try it out! + // First manually index one item, and see if it's 11. + $values = array( + 'limit' => 1, + ); + $this->drupalPost(NULL, $values, t('Index now')); + $this->assertText(t('Successfully indexed @count item.', array('@count' => 1))); + $this->assertNoText(t("Some items couldn't be indexed. Check the logs for details."), "Index errors warning isn't displayed."); + $this->assertNoText(t("Couldn't index items. Check the logs for details."), "Index error isn't displayed."); + $variables = array( + '@indexed' => 8, + '@total' => 14, + '@percentage' => 57, + ); + $this->assertText(t('About @percentage% of all items have been indexed in their latest version (@indexed / @total).', $variables), 'Correct index status displayed after inserting and changing items.'); + + $this->drupalGet('search_api_test/query/' . $this->index_id); + $this->assertText('result count = 1', 'Indexing order test 1: correct result count.'); + $this->assertText('results = (11)', 'Indexing order test 1: correct results.'); + + // Now index with a cron run, but stop at item 8. + variable_set('search_api_test_indexing_break', 8); + $this->cronRun(); + // Now just the four new items should have been indexed. + $this->drupalGet('search_api_test/query/' . $this->index_id); + $this->assertText('result count = 4', 'Indexing order test 2: correct result count.'); + $this->assertText('results = (11, 12, 13, 14)', 'Indexing order test 2: correct results.'); + + // This time stop at item 4 (should be the last one). + variable_set('search_api_test_indexing_break', 5); + $this->cronRun(); + // Now all new and changed items should have been indexed, except 4. + $this->drupalGet('search_api_test/query/' . $this->index_id); + $this->assertText('result count = 6', 'Indexing order test 3: correct result count.'); + $this->assertText('results = (2, 8, 11, 12, 13, 14)', 'Indexing order test 3: correct results.'); + + // Index the remaining items. + variable_set('search_api_test_indexing_break', 0); + $this->cronRun(); + // Now all new and changed items should have been indexed. + $this->drupalGet('search_api_test/query/' . $this->index_id); + $this->assertText('result count = 7', 'Indexing order test 4: correct result count.'); + $this->assertText('results = (2, 5, 8, 11, 12, 13, 14)', 'Indexing order test 4: correct results.'); + } + protected function editServer() { $values = array( 'name' => 'test-name-foo', @@ -360,7 +421,7 @@ class SearchApiWebTest extends DrupalWebTestCase { protected function clearIndex() { $this->drupalPost("admin/config/search/search_api/index/{$this->index_id}/status", array(), t('Clear index')); $this->assertText(t('The index was successfully cleared.')); - $this->assertText(t('All items still need to be indexed (@total total).', array('@total' => 10)), 'Correct index status displayed.'); + $this->assertText(t('All items still need to be indexed (@total total).', array('@total' => 14)), 'Correct index status displayed.'); } protected function deleteServer() { diff --git a/tests/search_api_test.module b/tests/search_api_test.module index 8a4ff82..659a5fe 100644 --- a/tests/search_api_test.module +++ b/tests/search_api_test.module @@ -11,10 +11,16 @@ function search_api_test_menu() { 'page arguments' => array('search_api_test_insert_item'), 'access callback' => TRUE, ), - 'search_api_test/%search_api_test' => array( + 'search_api_test/view/%search_api_test' => array( 'title' => 'View item', 'page callback' => 'search_api_test_view', - 'page arguments' => array(1), + 'page arguments' => array(2), + 'access callback' => TRUE, + ), + 'search_api_test/touch/%search_api_test' => array( + 'title' => 'Mark item as changed', + 'page callback' => 'search_api_test_touch', + 'page arguments' => array(2), 'access callback' => TRUE, ), 'search_api_test/query/%search_api_index' => array( @@ -81,6 +87,13 @@ function search_api_test_view($entity) { } /** + * Menu callback for marking a "search_api_test" entity as changed. + */ +function search_api_test_touch($entity) { + module_invoke_all('entity_update', $entity, 'search_api_test'); +} + +/** * Menu callback for executing a search. */ function search_api_test_query(SearchApiIndex $index, $keys = 'foo bar', $offset = 0, $limit = 10, $fields = NULL, $sort = NULL, $filters = NULL) { @@ -250,25 +263,23 @@ class SearchApiTestService extends SearchApiAbstractService { } public function indexItems(SearchApiIndex $index, array $items) { - // Refuse to index items with IDs that are multiples of 8 unless the - // "search_api_test_index_all" variable is set. - if (variable_get('search_api_test_index_all', FALSE)) { - return $this->index($index, array_keys($items)); - } - $ret = array(); - foreach ($items as $id => $item) { - if ($id % 8) { - $ret[] = $id; + // Refuse to index the item with the same ID as the + // "search_api_test_indexing_break" variable, if it is set. + if ($mod = variable_get('search_api_test_indexing_break', 8)) { + foreach ($items as $id => $item) { + if ($id == $mod) { + unset($items[$id]); + } } - } - return $this->index($index, $ret); + } + return $this->index($index, array_keys($items)); } protected function index(SearchApiIndex $index, array $ids) { $this->options += array('indexes' => array()); $this->options['indexes'] += array($index->machine_name => array()); $this->options['indexes'][$index->machine_name] += drupal_map_assoc($ids); - sort($this->options['indexes'][$index->machine_name]); + asort($this->options['indexes'][$index->machine_name]); $this->server->save(); return $ids; }