2 * This document is a part of the source code and related artifacts
3 * for CollectionSpace, an open source collections management system
4 * for museums and related institutions:
6 * http://www.collectionspace.org
7 * http://wiki.collectionspace.org
9 * Copyright © 2009 Regents of the University of California
11 * Licensed under the Educational Community License (ECL), Version 2.0.
12 * You may not use this file except in compliance with this License.
14 * You may obtain a copy of the ECL 2.0 License at
15 * https://source.collectionspace.org/collection-space/LICENSE.txt
17 * Unless required by applicable law or agreed to in writing, software
18 * distributed under the License is distributed on an "AS IS" BASIS,
19 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20 * See the License for the specific language governing permissions and
21 * limitations under the License.
23 package org.collectionspace.services.client.test;
25 import java.text.Collator;
26 import java.util.ArrayList;
27 import java.util.Comparator;
28 import java.util.List;
29 import java.util.Locale;
30 import javax.ws.rs.core.MediaType;
31 import javax.ws.rs.core.Response;
33 import org.collectionspace.services.MovementJAXBSchema;
34 import org.collectionspace.services.client.CollectionSpaceClient;
35 import org.collectionspace.services.client.MovementClient;
36 import org.collectionspace.services.movement.MovementsCommon;
37 import org.collectionspace.services.movement.MovementsCommonList;
38 import org.collectionspace.services.jaxb.AbstractCommonList;
40 import org.jboss.resteasy.client.ClientResponse;
41 import org.jboss.resteasy.plugins.providers.multipart.MultipartInput;
42 import org.jboss.resteasy.plugins.providers.multipart.MultipartOutput;
43 import org.jboss.resteasy.plugins.providers.multipart.OutputPart;
45 import org.testng.Assert;
46 import org.testng.annotations.AfterClass;
47 import org.testng.annotations.DataProvider;
48 import org.testng.annotations.Test;
50 import org.slf4j.Logger;
51 import org.slf4j.LoggerFactory;
54 * MovementSortByTest, tests sorting of summary lists by fields
55 * of various datatypes.
57 * $LastChangedRevision: 2562 $
58 * $LastChangedDate: 2010-06-22 23:26:51 -0700 (Tue, 22 Jun 2010) $
60 public class MovementSortByTest extends BaseServiceTest {
62 private final String CLASS_NAME = MovementSortByTest.class.getName();
63 private final Logger logger = LoggerFactory.getLogger(CLASS_NAME);
65 // Instance variables specific to this test.
66 private final String DELIMITER_SCHEMA_AND_FIELD = ":";
67 private final String KEYWORD_DESCENDING_SEARCH = "DESC";
68 private final String SERVICE_PATH_COMPONENT = "movements";
69 private final String TEST_SPECIFIC_KEYWORD = "msotebstpfscn";
70 private List<String> movementIdsCreated = new ArrayList<String>();
71 private final String SORT_FIELD_SEPARATOR = ", ";
74 * @see org.collectionspace.services.client.test.BaseServiceTest#getClientInstance()
77 protected CollectionSpaceClient getClientInstance() {
78 throw new UnsupportedOperationException(); //method not supported (or needed) in this test class
82 * @see org.collectionspace.services.client.test.BaseServiceTest#getAbstractCommonList(org.jboss.resteasy.client.ClientResponse)
85 protected AbstractCommonList getAbstractCommonList(
86 ClientResponse<AbstractCommonList> response) {
87 throw new UnsupportedOperationException(); //method not supported (or needed) in this test class
90 // ---------------------------------------------------------------
92 // ---------------------------------------------------------------
97 * Tests whether a list of records, sorted by a String field in
98 * ascending order, is returned in the expected order.
100 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
101 dependsOnMethods = {"createList"})
102 public void sortByStringFieldAscending(String testName) throws Exception {
104 if (logger.isDebugEnabled()) {
105 logger.debug(testBanner(testName, CLASS_NAME));
108 String sortFieldName = qualifySortFieldName(MovementJAXBSchema.MOVEMENT_NOTE);
109 if (logger.isDebugEnabled()) {
110 logger.debug("Sorting on field name=" + sortFieldName);
112 MovementsCommonList list = readSortedList(sortFieldName);
113 List<MovementsCommonList.MovementListItem> items =
114 list.getMovementListItem();
116 ArrayList<String> values = new ArrayList<String>();
117 Collator usEnglishCollator = Collator.getInstance(Locale.US);
119 for (MovementsCommonList.MovementListItem item : items) {
120 // Because movementNote is not currently a summary field
121 // (returned in summary list items), we will need to verify
122 // sort order by retrieving full records, using the
123 // IDs provided in the summary list items. amd then retriving
124 // the value of that field from each of those records.
125 MovementsCommon movement = read(item.getCsid());
126 values.add(i, movement.getMovementNote());
127 if (logger.isDebugEnabled()) {
128 logger.debug("list-item[" + i + "] movementNote=" + values.get(i));
130 // Verify that the value of the specified field in the current record
131 // is equal to or greater than its value in the previous record,
132 // using a locale-specific collator.
134 // (Note: when used with certain text, this test case could potentially
135 // reflect inconsistencies, if any, between Java's collator and the
136 // collator used for ordering by the database. To help avoid this,
137 // it might be useful to keep test strings fairly generic.)
138 if (i > 0 && values.get(i) != null && values.get(i - 1) != null) {
139 Assert.assertTrue(usEnglishCollator.compare(values.get(i), values.get(i - 1)) >= 0);
147 * Tests whether a list of records, obtained by a keyword search, and
148 * sorted by a String field in ascending order, is returned in the expected order.
150 * This verifies that summary list results from keyword searches, in
151 * addition to 'read list' requests, can be returned in sorted order.
153 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
154 dependsOnMethods = {"createList"})
155 public void sortKeywordSearchResultsByStringFieldAscending(String testName) throws Exception {
157 if (logger.isDebugEnabled()) {
158 logger.debug(testBanner(testName, CLASS_NAME));
161 String sortFieldName = qualifySortFieldName(MovementJAXBSchema.MOVEMENT_NOTE);
162 if (logger.isDebugEnabled()) {
163 logger.debug("Sorting on field name=" + sortFieldName);
165 MovementsCommonList list = keywordSearchSortedBy(TEST_SPECIFIC_KEYWORD, sortFieldName);
166 List<MovementsCommonList.MovementListItem> items =
167 list.getMovementListItem();
169 ArrayList<String> values = new ArrayList<String>();
170 Collator usEnglishCollator = Collator.getInstance(Locale.US);
172 for (MovementsCommonList.MovementListItem item : items) {
173 // Because movementNote is not currently a summary field
174 // (returned in summary list items), we will need to verify
175 // sort order by retrieving full records, using the
176 // IDs provided in the summary list items. amd then retriving
177 // the value of that field from each of those records.
178 MovementsCommon movement = read(item.getCsid());
179 values.add(i, movement.getMovementNote());
180 if (logger.isDebugEnabled()) {
181 logger.debug("list-item[" + i + "] movementNote=" + values.get(i));
183 // Verify that the value of the specified field in the current record
184 // is equal to or greater than its value in the previous record,
185 // using a locale-specific collator.
187 // (Note: when used with certain text, this test case could potentially
188 // reflect inconsistencies, if any, between Java's collator and the
189 // collator used for ordering by the database. To help avoid this,
190 // it might be useful to keep test strings fairly generic.)
191 if (i > 0 && values.get(i) != null && values.get(i - 1) != null) {
192 Assert.assertTrue(usEnglishCollator.compare(values.get(i), values.get(i - 1)) >= 0);
200 * Tests whether a list of records, sorted by a String field in
201 * descending order, is returned in the expected order.
203 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
204 dependsOnMethods = {"createList"})
205 public void sortByStringFieldDescending(String testName) throws Exception {
207 if (logger.isDebugEnabled()) {
208 logger.debug(testBanner(testName, CLASS_NAME));
211 String sortFieldName =
212 asDescendingSort(qualifySortFieldName(MovementJAXBSchema.MOVEMENT_NOTE));
213 if (logger.isDebugEnabled()) {
214 logger.debug("Sorting on field name=" + sortFieldName);
216 MovementsCommonList list = readSortedList(sortFieldName);
217 List<MovementsCommonList.MovementListItem> items =
218 list.getMovementListItem();
220 ArrayList<String> values = new ArrayList<String>();
221 Collator usEnglishCollator = Collator.getInstance(Locale.US);
223 for (MovementsCommonList.MovementListItem item : items) {
224 // Because movementNote is not currently a summary field
225 // (returned in summary list items), we will need to verify
226 // sort order by retrieving full records, using the
227 // IDs provided in the summary list items. amd then retriving
228 // the value of that field from each of those records.
229 MovementsCommon movement = read(item.getCsid());
230 values.add(i, movement.getMovementNote());
231 if (logger.isDebugEnabled()) {
232 logger.debug("list-item[" + i + "] movementNote=" + values.get(i));
234 // Verify that the value of the specified field in the current record
235 // is less than or equal to than its value in the previous record,
236 // using a locale-specific collator.
238 // (Note: when used with certain text, this test case could potentially
239 // reflect inconsistencies, if any, between Java's collator and the
240 // collator used for ordering by the database. To help avoid this,
241 // it might be useful to keep test strings fairly generic.)
242 if (i > 0 && values.get(i) != null && values.get(i - 1) != null) {
243 Assert.assertTrue(usEnglishCollator.compare(values.get(i), values.get(i - 1)) <= 0);
251 * Tests whether a list of records, sorted by a dateTime field in
252 * ascending order, is returned in the expected order.
254 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
255 dependsOnMethods = {"createList"})
256 public void sortByDateTimeFieldAscending(String testName) throws Exception {
258 if (logger.isDebugEnabled()) {
259 logger.debug(testBanner(testName, CLASS_NAME));
262 String sortFieldName = qualifySortFieldName(MovementJAXBSchema.LOCATION_DATE);
263 if (logger.isDebugEnabled()) {
264 logger.debug("Sorting on field name=" + sortFieldName);
266 MovementsCommonList list = readSortedList(sortFieldName);
267 List<MovementsCommonList.MovementListItem> items =
268 list.getMovementListItem();
270 ArrayList<String> values = new ArrayList<String>();
271 Comparator<String> comparator = String.CASE_INSENSITIVE_ORDER;
273 for (MovementsCommonList.MovementListItem item : items) {
274 values.add(i, item.getLocationDate());
275 if (logger.isDebugEnabled()) {
276 logger.debug("list-item[" + i + "] locationDate=" + values.get(i));
278 // Verify that the value of the specified field in the current record
279 // is equal to or greater than its value in the previous record.
280 if (i > 0 && values.get(i) != null && values.get(i - 1) != null) {
281 Assert.assertTrue(comparator.compare(values.get(i), values.get(i - 1)) >= 0);
288 * Tests whether a list of records, sorted by a dateTime field in
289 * descending order, is returned in the expected order.
291 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
292 dependsOnMethods = {"createList"})
293 public void sortByDateTimeFieldDescending(String testName) throws Exception {
295 if (logger.isDebugEnabled()) {
296 logger.debug(testBanner(testName, CLASS_NAME));
299 String sortFieldName =
300 asDescendingSort(qualifySortFieldName(MovementJAXBSchema.LOCATION_DATE));
301 if (logger.isDebugEnabled()) {
302 logger.debug("Sorting on field name=" + sortFieldName);
304 MovementsCommonList list = readSortedList(sortFieldName);
305 List<MovementsCommonList.MovementListItem> items =
306 list.getMovementListItem();
308 ArrayList<String> values = new ArrayList<String>();
309 Comparator<String> comparator = String.CASE_INSENSITIVE_ORDER;
311 for (MovementsCommonList.MovementListItem item : items) {
312 values.add(i, item.getLocationDate());
313 if (logger.isDebugEnabled()) {
314 logger.debug("list-item[" + i + "] locationDate=" + values.get(i));
316 // Verify that the value of the specified field in the current record
317 // is less than or equal to its value in the previous record.
318 if (i > 0 && values.get(i) != null && values.get(i - 1) != null) {
319 Assert.assertTrue(comparator.compare(values.get(i), values.get(i - 1)) <= 0);
326 * Tests whether a list of records, sorted by two different fields in
327 * ascending order, is returned in the expected order.
329 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
330 dependsOnMethods = {"createList"})
331 public void sortByTwoFieldsAscending(String testName) throws Exception {
333 if (logger.isDebugEnabled()) {
334 logger.debug(testBanner(testName, CLASS_NAME));
337 String firstSortFieldName = qualifySortFieldName(MovementJAXBSchema.MOVEMENT_NOTE);
338 String secondSortFieldName = qualifySortFieldName(MovementJAXBSchema.LOCATION_DATE);
339 if (logger.isDebugEnabled()) {
340 logger.debug("Sorting on field names=" + firstSortFieldName + " and " + secondSortFieldName);
342 String sortExpression = firstSortFieldName + SORT_FIELD_SEPARATOR + secondSortFieldName;
343 MovementsCommonList list = readSortedList(sortExpression);
344 List<MovementsCommonList.MovementListItem> items =
345 list.getMovementListItem();
347 ArrayList<String> firstFieldValues = new ArrayList<String>();
348 ArrayList<String> secondFieldValues = new ArrayList<String>();
349 Collator usEnglishCollator = Collator.getInstance(Locale.US);
350 Comparator<String> comparator = String.CASE_INSENSITIVE_ORDER;
352 for (MovementsCommonList.MovementListItem item : items) {
353 // Because movementNote is not currently a summary field
354 // (returned in summary list items), we will need to verify
355 // sort order by retrieving full records, using the
356 // IDs provided in the summary list items. amd then retriving
357 // the value of that field from each of those records.
358 MovementsCommon movement = read(item.getCsid());
359 firstFieldValues.add(i, movement.getMovementNote());
360 secondFieldValues.add(i, movement.getLocationDate());
361 if (logger.isDebugEnabled()) {
362 logger.debug("list-item[" + i + "] movementNote=" + firstFieldValues.get(i));
363 logger.debug("list-item[" + i + "] locationDate=" + secondFieldValues.get(i));
365 // Verify that the value of the specified field in the current record
366 // is less than or greater than its value in the previous record.
367 if (i > 0 && firstFieldValues.get(i) != null && firstFieldValues.get(i - 1) != null) {
368 Assert.assertTrue(usEnglishCollator.compare(firstFieldValues.get(i), firstFieldValues.get(i - 1)) >= 0);
369 // If the value of the first sort field in the current record is identical to
370 // its value in the previous record, verify that the value of the second sort
371 // field is equal to or greater than its value in the previous record,
372 // using a locale-specific collator.
373 if (usEnglishCollator.compare(firstFieldValues.get(i), firstFieldValues.get(i - 1)) == 0) {
374 if (i > 0 && secondFieldValues.get(i) != null && secondFieldValues.get(i - 1) != null) {
375 Assert.assertTrue(comparator.compare(secondFieldValues.get(i), secondFieldValues.get(i - 1)) >= 0);
384 * Tests whether a list of records, sorted by one different fields in
385 * descending order and a second field in ascending order, is returned in the expected order.
387 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class,
388 dependsOnMethods = {"createList"})
389 public void sortByOneFieldAscendingOneFieldsDescending(String testName) throws Exception {
391 if (logger.isDebugEnabled()) {
392 logger.debug(testBanner(testName, CLASS_NAME));
395 String firstSortFieldName =
396 asDescendingSort(qualifySortFieldName(MovementJAXBSchema.LOCATION_DATE));
397 String secondSortFieldName = qualifySortFieldName(MovementJAXBSchema.MOVEMENT_NOTE);
398 if (logger.isDebugEnabled()) {
399 logger.debug("Sorting on field names=" + firstSortFieldName + " and " + secondSortFieldName);
401 String sortExpression = firstSortFieldName + SORT_FIELD_SEPARATOR + secondSortFieldName;
402 MovementsCommonList list = readSortedList(sortExpression);
403 List<MovementsCommonList.MovementListItem> items =
404 list.getMovementListItem();
406 ArrayList<String> firstFieldValues = new ArrayList<String>();
407 ArrayList<String> secondFieldValues = new ArrayList<String>();
408 Collator usEnglishCollator = Collator.getInstance(Locale.US);
409 Comparator<String> comparator = String.CASE_INSENSITIVE_ORDER;
411 for (MovementsCommonList.MovementListItem item : items) {
412 // Because movementNote is not currently a summary field
413 // (returned in summary list items), we will need to verify
414 // sort order by retrieving full records, using the
415 // IDs provided in the summary list items. amd then retriving
416 // the value of that field from each of those records.
417 MovementsCommon movement = read(item.getCsid());
418 firstFieldValues.add(i, movement.getLocationDate());
419 secondFieldValues.add(i, movement.getMovementNote());
420 if (logger.isDebugEnabled()) {
421 logger.debug("list-item[" + i + "] locationDate=" + firstFieldValues.get(i));
422 logger.debug("list-item[" + i + "] movementNote=" + secondFieldValues.get(i));
424 // Verify that the value of the specified field in the current record
425 // is less than or greater than its value in the previous record.
426 if (i > 0 && firstFieldValues.get(i) != null && firstFieldValues.get(i - 1) != null) {
427 Assert.assertTrue(comparator.compare(firstFieldValues.get(i), firstFieldValues.get(i - 1)) <= 0);
428 // If the value of the first sort field in the current record is identical to
429 // its value in the previous record, verify that the value of the second sort
430 // field is equal to or greater than its value in the previous record,
431 // using a locale-specific collator.
432 if (comparator.compare(firstFieldValues.get(i), firstFieldValues.get(i - 1)) == 0) {
433 if (i > 0 && secondFieldValues.get(i) != null && secondFieldValues.get(i - 1) != null) {
434 Assert.assertTrue(usEnglishCollator.compare(secondFieldValues.get(i), secondFieldValues.get(i - 1)) >= 0);
444 * Tests whether a request to sort by an empty field name is handled
445 * as expected: the query parameter is simply ignored, and a list
446 * of records is returned, unsorted, with a success result.
448 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class)
449 public void sortWithEmptySortFieldName(String testName) throws Exception {
451 if (logger.isDebugEnabled()) {
452 logger.debug(testBanner(testName, CLASS_NAME));
454 testSetup(STATUS_OK, ServiceRequestType.READ);
456 // Submit the request to the service and store the response.
457 MovementClient client = new MovementClient();
458 final String EMPTY_SORT_FIELD_NAME = "";
459 ClientResponse<MovementsCommonList> res =
460 client.readListSortedBy(EMPTY_SORT_FIELD_NAME);
461 int statusCode = res.getStatus();
463 // Check the status code of the response: does it match
464 // the expected response(s)?
465 if (logger.isDebugEnabled()) {
466 logger.debug(testName + ": status = " + statusCode);
468 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
469 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
470 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);
477 * Tests whether a request to sort by an unqualified field name is
478 * handled as expected. The field name provided in this test is valid,
479 * but has not been qualified by being prefixed by a schema name and delimiter.
481 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class)
482 public void sortWithUnqualifiedFieldName(String testName) throws Exception {
484 if (logger.isDebugEnabled()) {
485 logger.debug(testBanner(testName, CLASS_NAME));
487 // FIXME: Ultimately, this should return a BAD_REQUEST status.
488 testSetup(STATUS_INTERNAL_SERVER_ERROR, ServiceRequestType.READ);
490 // Submit the request to the service and store the response.
491 MovementClient client = new MovementClient();
492 ClientResponse<MovementsCommonList> res =
493 client.readListSortedBy(MovementJAXBSchema.LOCATION_DATE);
494 int statusCode = res.getStatus();
496 // Check the status code of the response: does it match
497 // the expected response(s)?
498 if (logger.isDebugEnabled()) {
499 logger.debug(testName + ": status = " + statusCode);
501 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
502 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
503 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);
508 * Tests whether a request to sort by an invalid identifier for the
509 * sort order (ascending or descending) is handled as expected.
511 @Test(dataProvider = "testName", dataProviderClass = AbstractServiceTestImpl.class)
512 public void sortWithInvalidSortOrderIdentifier(String testName) throws Exception {
514 if (logger.isDebugEnabled()) {
515 logger.debug(testBanner(testName, CLASS_NAME));
517 // FIXME: Ultimately, this should return a BAD_REQUEST status.
518 testSetup(STATUS_INTERNAL_SERVER_ERROR, ServiceRequestType.READ);
520 // Submit the request to the service and store the response.
521 MovementClient client = new MovementClient();
522 final String INVALID_SORT_ORDER_IDENTIFIER = "NO_DIRECTION";
523 ClientResponse<MovementsCommonList> res =
524 client.readListSortedBy(MovementJAXBSchema.LOCATION_DATE
525 + " " + INVALID_SORT_ORDER_IDENTIFIER);
526 int statusCode = res.getStatus();
528 // Check the status code of the response: does it match
529 // the expected response(s)?
530 if (logger.isDebugEnabled()) {
531 logger.debug(testName + ": status = " + statusCode);
533 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
534 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
535 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);
540 * Tests whether a request to sort by a malformed field name is
541 * handled as expected.
544 @Test(dataProvider="testName", dataProviderClass=AbstractServiceTestImpl.class)
545 public void sortWithMalformedFieldName(String testName) throws Exception {
547 // FIXME: Implement this stub method.
549 // FIXME: Consider splitting this test into various tests, with
550 // different malformed field name formats that might confuse parsers
551 // and/or validation code.
553 // FIXME: Consider fixing DocumentFilter.setSortOrder() to return
554 // an error response to this test case, then revise this test case
555 // to expect that response.
560 // ---------------------------------------------------------------
561 // Cleanup of resources created during testing
562 // ---------------------------------------------------------------
564 * Deletes all resources created by tests, after all tests have been run.
566 * This cleanup method will always be run, even if one or more tests fail.
567 * For this reason, it attempts to remove all resources created
568 * at any point during testing, even if some of those resources
569 * may be expected to be deleted by certain tests.
571 @AfterClass(alwaysRun = true)
572 public void cleanUp() {
573 String noTest = System.getProperty("noTestCleanup");
574 if (Boolean.TRUE.toString().equalsIgnoreCase(noTest)) {
575 if (logger.isDebugEnabled()) {
576 logger.debug("Skipping Cleanup phase ...");
580 if (logger.isDebugEnabled()) {
581 logger.debug("Cleaning up temporary resources created for testing ...");
583 // Delete all Movement resource(s) created during this test.
584 MovementClient movementClient = new MovementClient();
585 for (String resourceId : movementIdsCreated) {
586 // Note: Any non-success responses are ignored and not reported.
587 movementClient.delete(resourceId);
591 // ---------------------------------------------------------------
592 // Utility methods used by tests above
593 // ---------------------------------------------------------------
596 public String getServicePathComponent() {
597 return SERVICE_PATH_COMPONENT;
600 private String getCommonSchemaName() {
601 // FIXME: While this convention - appending a suffix to the name of
602 // the service's first unique URL path component - works, it would
603 // be preferable to get the common schema name from configuration.
605 // Such configuration is provided for example, on the services side, in
606 // org.collectionspace.services.common.context.AbstractServiceContextImpl
607 return getServicePathComponent() + "_" + "common";
610 public String qualifySortFieldName(String fieldName) {
611 return getCommonSchemaName() + DELIMITER_SCHEMA_AND_FIELD + fieldName;
614 public String asDescendingSort(String qualifiedFieldName) {
615 return qualifiedFieldName + " " + KEYWORD_DESCENDING_SEARCH;
619 * A data provider that provides a set of unsorted values, which are
620 * to be used in populating (seeding) values in test records.
622 * Data elements provided for each test record consist of:
623 * * An integer, reflecting expected sort order.
624 * * US English text, to populate the value of a free text (String) field.
625 * * An ISO 8601 timestamp, to populate the value of a calendar date (dateTime) field.
627 @DataProvider(name = "unsortedValues")
628 public Object[][] unsortedValues() {
629 // Add a test record-specific string so we have the option of
630 // constraining tests to only test records, in list or search results.
631 final String TEST_RECORD_SPECIFIC_STRING = CLASS_NAME + " " + TEST_SPECIFIC_KEYWORD;
632 return new Object[][]{
633 {1, "Aardvark and plumeria. " + TEST_RECORD_SPECIFIC_STRING, "2009-01-29T00:00:05Z"},
634 {10, "Zounds! " + TEST_RECORD_SPECIFIC_STRING, "2010-08-31T00:00:00Z"},
635 {3, "Aardvark and plumeria. " + TEST_RECORD_SPECIFIC_STRING, "2010-08-30T00:00:00Z"},
636 {7, "Bat fling off wall. " + TEST_RECORD_SPECIFIC_STRING, "2010-08-30T00:00:00Z"},
637 {4, "Aardvarks and plumeria. " + TEST_RECORD_SPECIFIC_STRING, "2009-01-29T08:00:00Z"},
638 {5, "Aardvarks and plumeria. " + TEST_RECORD_SPECIFIC_STRING, "2009-05-29T00:00:00Z"},
639 {2, "Aardvark and plumeria. " + TEST_RECORD_SPECIFIC_STRING, "2009-05-29T00:00:00Z"},
640 {9, "Zounds! " + TEST_RECORD_SPECIFIC_STRING, "2009-05-29T00:00:00Z"}, // Identical to next record
641 {8, "Zounds! " + TEST_RECORD_SPECIFIC_STRING, "2009-05-29T00:00:00Z"},
642 {6, "Bat flies off ball. " + TEST_RECORD_SPECIFIC_STRING, "2009-05-29T00:00:00Z"}
647 * Create multiple test records, initially in unsorted order,
648 * using values for various fields obtained from the data provider.
650 @Test(dataProvider = "unsortedValues")
651 public void createList(int expectedSortOrder, String movementNote,
652 String locationDate) throws Exception {
654 String testName = "createList";
655 if (logger.isDebugEnabled()) {
656 logger.debug(testBanner(testName, CLASS_NAME));
658 testSetup(STATUS_CREATED, ServiceRequestType.CREATE);
660 // Iterates through the sets of values returned by the data provider,
661 // and creates a corresponding test record for each set of values.
662 create(movementNote, locationDate);
665 private void create(String movementNote, String locationDate) throws Exception {
667 String testName = "create";
668 testSetup(STATUS_CREATED, ServiceRequestType.CREATE);
670 // Submit the request to the service and store the response.
671 MovementClient client = new MovementClient();
672 MultipartOutput multipart = createMovementInstance(createIdentifier(),
673 movementNote, locationDate);
674 ClientResponse<Response> res = client.create(multipart);
675 int statusCode = res.getStatus();
677 // Check the status code of the response: does it match
678 // the expected response(s)?
681 // Does it fall within the set of valid status codes?
682 // Does it exactly match the expected status code?
683 if (logger.isDebugEnabled()) {
684 logger.debug(testName + ": status = " + statusCode);
686 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
687 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
688 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);
690 // Store the IDs from every resource created by tests,
691 // so they can be deleted after tests have been run.
692 movementIdsCreated.add(extractId(res));
695 private MovementsCommon read(String csid) throws Exception {
697 String testName = "read";
698 testSetup(STATUS_OK, ServiceRequestType.READ);
700 // Submit the request to the service and store the response.
701 MovementClient client = new MovementClient();
702 ClientResponse<MultipartInput> res = client.read(csid);
703 int statusCode = res.getStatus();
705 // Check the status code of the response: does it match
706 // the expected response(s)?
707 if (logger.isDebugEnabled()) {
708 logger.debug(testName + ": status = " + statusCode);
710 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
711 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
712 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);
714 // Extract and return the common part of the record.
715 MultipartInput input = (MultipartInput) res.getEntity();
716 MovementsCommon movement = (MovementsCommon) extractPart(input,
717 client.getCommonPartName(), MovementsCommon.class);
722 private MultipartOutput createMovementInstance(
723 String movementReferenceNumber,
725 String locationDate) {
726 MovementsCommon movement = new MovementsCommon();
727 movement.setMovementReferenceNumber(movementReferenceNumber);
728 movement.setMovementNote(movementNote);
729 movement.setLocationDate(locationDate);
730 MultipartOutput multipart = new MultipartOutput();
731 OutputPart commonPart =
732 multipart.addPart(movement, MediaType.APPLICATION_XML_TYPE);
733 commonPart.getHeaders().add("label", new MovementClient().getCommonPartName());
735 if (logger.isDebugEnabled()) {
736 logger.debug("to be created, movement common");
737 logger.debug(objectAsXmlString(movement, MovementsCommon.class));
743 private MovementsCommonList readSortedList(String sortFieldName) throws Exception {
745 String testName = "readSortedList";
746 testSetup(STATUS_OK, ServiceRequestType.READ);
748 // Submit the request to the service and store the response.
749 MovementClient client = new MovementClient();
751 ClientResponse<MovementsCommonList> res =
752 client.readListSortedBy(sortFieldName);
753 MovementsCommonList list = res.getEntity();
754 int statusCode = res.getStatus();
756 // Check the status code of the response: does it match
757 // the expected response(s)?
758 if (logger.isDebugEnabled()) {
759 logger.debug(testName + ": status = " + statusCode);
761 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
762 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
763 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);
769 private MovementsCommonList keywordSearchSortedBy(String keywords,
770 String sortFieldName) throws Exception {
772 String testName = "keywordSearchSortedBy";
773 testSetup(STATUS_OK, ServiceRequestType.READ);
775 // Submit the request to the service and store the response.
776 MovementClient client = new MovementClient();
778 ClientResponse<MovementsCommonList> res =
779 client.keywordSearchSortedBy(keywords, sortFieldName);
780 MovementsCommonList list = res.getEntity();
781 int statusCode = res.getStatus();
783 // Check the status code of the response: does it match
784 // the expected response(s)?
785 if (logger.isDebugEnabled()) {
786 logger.debug(testName + ": status = " + statusCode);
788 Assert.assertTrue(REQUEST_TYPE.isValidStatusCode(statusCode),
789 invalidStatusCodeMessage(REQUEST_TYPE, statusCode));
790 Assert.assertEquals(statusCode, EXPECTED_STATUS_CODE);