Test automation checkpoint (#1)

* Test REQ-WA103-QO1 working, added assert handling for cases with HTTP Client exceptions
* Added additional test support methods for testing specific OData versions, also reset for local state.
* Assert stepdef cleanup.
* Added support for asserting response codes, like 400s, for a specific OData version
* Added support for arithmetic integer comparisons.
* Updated resoscript variables and added further test support.
* Added Integer Comparison Tests (through REQ-WA103-QO11)
* rebuilt for Java 1.8 and cleaned up some of the logging and int compare tests
* Updated Dockerfile, generic.resoscript, and removed assertions from the runRESOScript action. Gradle should be used for assertion testing. See README.
This commit is contained in:
Joshua Darnell 2020-02-26 18:49:41 -08:00 committed by GitHub
parent cffb8bf9e2
commit 97722ba86c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 504 additions and 269 deletions

View File

@ -4,7 +4,7 @@ WORKDIR /home/gradle/project
ADD . ./ ADD . ./
RUN gradle copyJarToOut RUN gradle jar
RUN ls RUN ls
@ -13,7 +13,7 @@ FROM alpine:latest
RUN apk add --update bash ca-certificates openjdk8-jre-base nss && \ RUN apk add --update bash ca-certificates openjdk8-jre-base nss && \
rm -rf /var/cache/apk/* rm -rf /var/cache/apk/*
COPY --from=builder /home/gradle/project/out/web-api-commander.jar ./ COPY --from=builder /home/gradle/project/build/libs/web-api-commander.jar ./
ENTRYPOINT ["java","-jar","/web-api-commander.jar"] ENTRYPOINT ["java","-jar","/web-api-commander.jar"]
CMD ["--help"] CMD ["--help"]

View File

@ -296,7 +296,6 @@ The XML DTD for this schema is as follows:
<!ELEMENT Requests (Request)*> <!ELEMENT Requests (Request)*>
<!ELEMENT Request (#PCDATA)*> <!ELEMENT Request (#PCDATA)*>
<!ATTLIST Request <!ATTLIST Request
AssertResponseCode CDATA #IMPLIED
Capability CDATA #REQUIRED Capability CDATA #REQUIRED
MetallicLevel CDATA #REQUIRED MetallicLevel CDATA #REQUIRED
OutputFile CDATA #REQUIRED OutputFile CDATA #REQUIRED
@ -492,4 +491,4 @@ Please contact [josh@reso.org](mailto:josh@reso.org) with any questions, bug rep
* Support for authentication options in addition to Bearer tokens (Client Credentials in beta, please email for more info). * Support for authentication options in addition to Bearer tokens (Client Credentials in beta, please email for more info).
* Parallel fetch for replication * Parallel fetch for replication
* Job Scheduling * Job Scheduling
* Excel export * Excel export

Binary file not shown.

View File

@ -25,9 +25,8 @@
Name CDATA #REQUIRED Name CDATA #REQUIRED
Value CDATA #REQUIRED> Value CDATA #REQUIRED>
<!ELEMENT Requests (Request)*> <!ELEMENT Requests (Request)*>
<!ELEMENT Request (Assertions)*> <!ELEMENT Request (#PCDATA)*>
<!ATTLIST Request <!ATTLIST Request
AssertResponseCode CDATA #IMPLIED
Capability CDATA #REQUIRED Capability CDATA #REQUIRED
MetallicLevel CDATA #REQUIRED MetallicLevel CDATA #REQUIRED
OutputFile CDATA #REQUIRED OutputFile CDATA #REQUIRED
@ -35,12 +34,6 @@
TestDescription CDATA #REQUIRED TestDescription CDATA #REQUIRED
Url CDATA #REQUIRED Url CDATA #REQUIRED
WebAPIReference CDATA #REQUIRED> WebAPIReference CDATA #REQUIRED>
<!ELEMENT Assertions (AssertPresent|AssertBinaryOpComparison)*>
<!ELEMENT AssertPresent (#PCDATA)>
<!ELEMENT AssertBinaryOpComparison (LVal|Op|RVal)*>
<!ELEMENT LVal (#PCDATA)>
<!ELEMENT Op (#PCDATA)>
<!ELEMENT RVal (#PCDATA)>
]> ]>
<OutputScript> <OutputScript>
@ -89,7 +82,7 @@
<!-- REQUIRED: OData $select list - adapt this for your system and then adjust the remaining queries accordingly --> <!-- REQUIRED: OData $select list - adapt this for your system and then adjust the remaining queries accordingly -->
<Parameter Name="SelectList" Value="ListingKey,BedroomsTotal,StreetName,PropertyType,ModificationTimestamp" /> <Parameter Name="SelectList" Value="ListingKey,BedroomsTotal,StreetName,PropertyType,ModificationTimestamp" />
<!-- REQUIRED: Substitute key name from your EndpointMetadata here, either ListingKey or ListingKeyNumeric, <!-- REQUIRED: Substitute key name from your EndpointMetadata here, either ListingKey or ListingKeyInteger,
which requires rewriting some of the queries that follow... --> which requires rewriting some of the queries that follow... -->
<Parameter Name="UniqueID" Value="ListingKey" /> <Parameter Name="UniqueID" Value="ListingKey" />
@ -100,14 +93,14 @@
<Parameter Name="TopCount" Value="5" /> <Parameter Name="TopCount" Value="5" />
<Parameter Name="SortCount" Value="20" /> <Parameter Name="SortCount" Value="20" />
<!-- Numeric Field for eq, ne, gt, ge, lt, le testing --> <!-- Integer Field for eq, ne, gt, ge, lt, le testing -->
<!-- Type="Edm.Int16" or Type="Edm.Int32" or Type="Edm.Int64" for non-lookup fields --> <!-- Type="Edm.Int16" or Type="Edm.Int32" or Type="Edm.Int64" for non-lookup fields -->
<Parameter Name="FilterNumericField" Value="BedroomsTotal" /> <Parameter Name="FilterIntegerField" Value="BedroomsTotal" />
<Parameter Name="FilterNumericValueLow" Value="9" /> <Parameter Name="FilterIntegerValueLow" Value="9" />
<Parameter Name="FilterNumericValueHigh" Value="15" /> <Parameter Name="FilterIntegerValueHigh" Value="15" />
<Parameter Name="FilterNumericNotFound" Value="-1" /> <Parameter Name="FilterIntegerNotFound" Value="-1" />
<!-- Numeric Field for "not" testing --> <!-- Integer Field for "not" testing -->
<Parameter Name="FilterNotField" Value="BedroomsTotal" /> <Parameter Name="FilterNotField" Value="BedroomsTotal" />
<Parameter Name="FilterNotValue" Value="-1" /> <Parameter Name="FilterNotValue" Value="-1" />
@ -126,11 +119,11 @@
<Parameter Name="ExpandField" Value="ListAgent" /> <Parameter Name="ExpandField" Value="ListAgent" />
<!-- For Geo-spatial Testing --> <!-- For Geo-spatial Testing -->
<Parameter Name="GeospatialLatitudeField" Value="Latitude" /> <Parameter Name="GeoSpatialLatitudeField" Value="Latitude" />
<Parameter Name="GeospatialLongitudeField" Value="Longitude" /> <Parameter Name="GeoSpatialLongitudeField" Value="Longitude" />
<Parameter Name="GeospatialField" Value="Coordinates" /> <Parameter Name="GeoSpatialField" Value="Coordinates" />
<Parameter Name="GeospatialValue" Value="REQUIRED: YOUR COORDINATES GO HERE in 'Longitude Latitude' format" /> <!-- "Longitude Latitude" --> <Parameter Name="GeoSpatialValue" Value="REQUIRED: YOUR COORDINATES GO HERE in 'Longitude Latitude' format" /> <!-- "Longitude Latitude" -->
<Parameter Name="GeospatialDistanceValue" Value="100" /> <Parameter Name="GeoSpatialDistanceValue" Value="100" />
<!--String Fields for testing --> <!--String Fields for testing -->
<!-- Type="Edm.String" --> <!-- Type="Edm.String" -->
@ -184,220 +177,192 @@
<!-- NOTE: for this test, we always assume that /$metadata is relative to the Web API Service Root, referred to as WebAPIURI here --> <!-- NOTE: for this test, we always assume that /$metadata is relative to the Web API Service Root, referred to as WebAPIURI here -->
<Request <Request
TestDescription="Metadata Endpoint" TestDescription="Metadata Endpoint"
RequirementId="REQ-WA103-END3" RequirementId="REQ-WA103-END3.metadata"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="" WebAPIReference=""
OutputFile="REQ-WA103-END3_Metadata.xml" OutputFile="REQ-WA103-END3.metadata.xml"
Url="*ClientSettings_WebAPIURI*/$metadata?$format=application/xml" Url="*ClientSettings_WebAPIURI*/$metadata?$format=application/xml"
/> />
<Request <Request
TestDescription="Data System" TestDescription="Data System"
RequirementId="REQ-WA103-END2" RequirementId="REQ-WA103-END2.datasystem"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core Support"
WebAPIReference="" WebAPIReference=""
OutputFile="REQ-WA103-END2_DataSystem.json" OutputFile="REQ-WA103-END2.datasystem.json"
Url="*Parameter_EndpointDataSystem*" Url="*Parameter_EndpointDataSystem*"
/> />
<Request <Request
TestDescription="Field names are case sensitive when used in the $select, $filter, and $orderby parameters. Case sensitivity is tested against the values defined in the resource metadata. Case sensitivity MUST be supported." TestDescription="Search Parameters: Select UniqueID"
RequirementId="REQ-WA103-Q1" RequirementId="REQ-WA103-QR1.select.uniqueId"
MetallicLevel="Core"
Capability="Core Support"
WebAPIReference=""
OutputFile="REQ-WA103-Q1.json"
Url=""
AssertResponseCode="400"
/>
<!-- TODO: verify AssertResponseCode -->
<Request
TestDescription="Servers MAY reject queries that are too complex to accept/handle. Servers MUST generate an appropriate error response and gracefully deny the request."
RequirementId="REQ-WA103-Q2"
MetallicLevel="Core"
Capability="Query functions"
WebAPIReference=""
OutputFile="REQ-WA103-Q2.json"
Url="*Parameter_QueryTooComplexUri*"
AssertResponseCode="20211"
/>
<Request
TestDescription="Search Parameters: Search by UniqueID"
RequirementId="REQ-WA103-QR1"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Query functions" Capability="Query functions"
WebAPIReference="2.4.1" WebAPIReference="2.4.1"
OutputFile="REQ-WA103-QR1.json" OutputFile="REQ-WA103-QR1.select.uniqueId.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*(*Parameter_UniqueIDValue*)?$select=*Parameter_UniqueID*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*(*Parameter_UniqueIDValue*)?$select=*Parameter_UniqueID*"
AssertResponseCode="200"
/> />
<Request <Request
TestDescription="Query Support: $select" TestDescription="Query Support: $select"
RequirementId="REQ-WA103-QR3" RequirementId="REQ-WA103-QR3.select"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Query functions" Capability="Query functions"
WebAPIReference="2.4.2" WebAPIReference="2.4.2"
OutputFile="REQ-WA103-QR3.json" OutputFile="REQ-WA103-QR3.select.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $top" TestDescription="Query Support: $top"
RequirementId="REQ-WA103-QR4" RequirementId="REQ-WA103-QR4.top"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Client paging ($top, $skip)" Capability="Client paging ($top, $skip)"
WebAPIReference="2.4.2" WebAPIReference="2.4.2"
OutputFile="REQ-WA103-QR4.json" OutputFile="REQ-WA103-QR4.top.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $skip" TestDescription="Query Support: $skip"
RequirementId="REQ-WA103-QR5" RequirementId="REQ-WA103-QR5.skip"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Client pageability ($top, $skip)" Capability="Client pageability ($top, $skip)"
WebAPIReference="2.4.2" WebAPIReference="2.4.2"
OutputFile="REQ-WA103-QR5.json" OutputFile="REQ-WA103-QR5.skip.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter" TestDescription="Query Support: $select case-sensitivity. Expect 400 response on OData 4.0"
RequirementId="REQ-WA103-QO1" RequirementId="REQ-WA103-QO1.select.case"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Core"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO1-1_Select_Case.json" OutputFile="REQ-WA103-QO1.select.case.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$SeLeCt=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* eq *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$SeLeCt=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* eq *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
AssertResponseCode="400"
/> />
<Request <Request
TestDescription="Query Support: $filter (2)" TestDescription="Query Support: $filter case-sensitivity. Expect 400 response on OData 4.0"
RequirementId="REQ-WA103-QO1" RequirementId="REQ-WA103-QO1.filter.case"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Core"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO1-2_Filter_Case.json" OutputFile="REQ-WA103-QO1.filter.case.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$FiLtEr=*Parameter_FilterNumericField* eq *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$FiLtEr=*Parameter_FilterIntegerField* eq *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
AssertResponseCode="400"
/> />
<Request <Request
TestDescription="Query Support: $filter (3)" TestDescription="Query Support: $orderby asc case-sensitivity. Expect 400 response on OData 4.0"
RequirementId="REQ-WA103-QO1" RequirementId="REQ-WA103-QO1.orderby.asc.case"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Core"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO1-3a_OrderByAsc_Case.json" OutputFile="REQ-WA103-QO1.orderby.asc.case.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterNumericField*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*&amp;$OrDeRbY=*Parameter_FilterNumericField* asc" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterIntegerField*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*&amp;$OrDeRbY=*Parameter_FilterIntegerField* asc"
AssertResponseCode="400"
/> />
<Request <Request
TestDescription="Query Support: $filter (4)" TestDescription="Query Support: $orderby desc case-sensitivity. Expect 400 response on OData 4.0"
RequirementId="REQ-WA103-QO1" RequirementId="REQ-WA103-QO1.orderby.desc.case"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Core"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO1-3b_OrderByDesc_Case.json" OutputFile="REQ-WA103-QO1.orderby.desc.case.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterNumericField*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*&amp;$oRdErBy=*Parameter_FilterNumericField* desc" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterIntegerField*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*&amp;$oRdErBy=*Parameter_FilterIntegerField* desc"
AssertResponseCode="400"
/> />
<Request <Request
TestDescription="Query Support: $filter - Comparison: eq (equal)" TestDescription="Query Support: $filter - Integer Comparison: eq (equal)"
RequirementId="REQ-WA103-QO2" RequirementId="REQ-WA103-QO2.filter.int.compare.eq"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO2_filter_eq.json" OutputFile="REQ-WA103-QO2.filter.int.compare.eq.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* eq *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* eq *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Comparison: ne (not equal)" TestDescription="Query Support: $filter - Integer Comparison: ne (not equal)"
RequirementId="REQ-WA103-QO3" RequirementId="REQ-WA103-QO3.filter.int.compare.ne"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO3_filter_ne.json" OutputFile="REQ-WA103-QO3.filter.int.compare.ne.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* ne *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* ne *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Comparison: gt (greater than)" TestDescription="Query Support: $filter - Integer Comparison: gt (greater than)"
RequirementId="REQ-WA103-QO4" RequirementId="REQ-WA103-QO4.filter.int.compare.gt"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO4_filter_gt.json" OutputFile="REQ-WA103-QO4.filter.int.compare.gt.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Comparison: ge (greater or equal)" TestDescription="Query Support: $filter - Integer Comparison: ge (greater or equal)"
RequirementId="REQ-WA103-QO5" RequirementId="REQ-WA103-QO5.filter.int.compare.ge"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO5_filter_ge.json" OutputFile="REQ-WA103-QO5.filter.int.compare.ge.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* ge *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* ge *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Comparison: lt (less than)" TestDescription="Query Support: $filter - Integer Comparison: lt (less than)"
RequirementId="REQ-WA103-QO6" RequirementId="REQ-WA103-QO6.filter.int.compare.lt"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO6_filter_lt.json" OutputFile="REQ-WA103-QO6.filter.int.compare.lt.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* lt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* lt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Comparison: le (less or equal)" TestDescription="Query Support: $filter - Integer Comparison: le (less or equal)"
RequirementId="REQ-WA103-QO7" RequirementId="REQ-WA103-QO7.filter.int.compare.le"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO7_filter_le.json" OutputFile="REQ-WA103-QO7.filter.int.compare.le.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* le *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* le *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Logical: and" TestDescription="Query Support: $filter - Integer Comparison: and"
RequirementId="REQ-WA103-QO9" RequirementId="REQ-WA103-QO9.filter.int.compare.and"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO9_filter_and.json" OutputFile="REQ-WA103-QO9.filter.int.compare.and.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow* and *Parameter_FilterNumericField* lt *Parameter_FilterNumericValueHigh**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow* and *Parameter_FilterIntegerField* lt *Parameter_FilterIntegerValueHigh**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Logical: or" TestDescription="Query Support: $filter - Integer Comparison: or"
RequirementId="REQ-WA103-QO10" RequirementId="REQ-WA103-QO10.filter.int.compare.or"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO10_filter_or.json" OutputFile="REQ-WA103-QO10.filter.int.compare.or.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueHigh* or *Parameter_FilterNumericField* lt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueHigh* or *Parameter_FilterIntegerField* lt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
TestDescription="Query Support: $filter - Logical: not" TestDescription="Query Support: $filter - Integer: not operator"
RequirementId="REQ-WA103-QO11" RequirementId="REQ-WA103-QO11.filter.int.compare.not.operator"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO11_filter_not.json" OutputFile="REQ-WA103-QO11.filter.int.compare.not.operator.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=not (*Parameter_FilterNotField* le *Parameter_FilterNotValue*)*Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=not(*Parameter_FilterNotField* le *Parameter_FilterNotValue*)*Parameter_RequiredParameters*"
/> />
<Request <Request
@ -444,7 +409,7 @@
TestDescription="Support Annotations" TestDescription="Support Annotations"
RequirementId="REQ-WA103-QM6" RequirementId="REQ-WA103-QM6"
MetallicLevel="Bronze" MetallicLevel="Bronze"
Capability="Core Support" Capability="Core"
WebAPIReference="2.4.8" WebAPIReference="2.4.8"
OutputFile="REQ-WA103-QM6.json" OutputFile="REQ-WA103-QM6.json"
Url="" Url=""
@ -497,7 +462,7 @@
Capability="Sortability ($orderby)" Capability="Sortability ($orderby)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO28_OrderByAscFiltered.json" OutputFile="REQ-WA103-QO28_OrderByAscFiltered.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterNumericField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* asc&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterIntegerField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* asc&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
@ -507,7 +472,7 @@
Capability="Sortability ($orderby)" Capability="Sortability ($orderby)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO28_OrderByAscNoFilter.json" OutputFile="REQ-WA103-QO28_OrderByAscNoFilter.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterNumericField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* asc" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterIntegerField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* asc"
/> />
<Request <Request
@ -517,7 +482,7 @@
Capability="Sortability ($orderby)" Capability="Sortability ($orderby)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO28_OrderByDescFiltered.json" OutputFile="REQ-WA103-QO28_OrderByDescFiltered.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterNumericField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* desc&amp;$filter=*Parameter_FilterNumericField* gt *Parameter_FilterNumericValueLow**Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterIntegerField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* desc&amp;$filter=*Parameter_FilterIntegerField* gt *Parameter_FilterIntegerValueLow**Parameter_RequiredParameters*"
/> />
<Request <Request
@ -527,7 +492,7 @@
Capability="Sortability ($orderby)" Capability="Sortability ($orderby)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO28_OrderByDescNoFilter.json" OutputFile="REQ-WA103-QO28_OrderByDescNoFilter.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterNumericField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* desc" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_SortCount*&amp;$select=*Parameter_FilterIntegerField*,*Parameter_TimestampField*&amp;$orderby=*Parameter_TimestampField* desc"
/> />
<Request <Request
@ -701,23 +666,23 @@
/> />
<Request <Request
TestDescription="Support Geospatial Search Implementation" TestDescription="Support GeoSpatial Search Implementation"
RequirementId="REQ-WA103-QM5" RequirementId="REQ-WA103-QM5"
MetallicLevel="Platinum" MetallicLevel="Platinum"
Capability="Query functions" Capability="Query functions"
WebAPIReference="2.4.7" WebAPIReference="2.4.7"
OutputFile="REQ-WA103-QM5_GeospatialLongLat_PointGeo.json" OutputFile="REQ-WA103-QM5_GeoSpatialLongLat_PointGeo.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=geo.distance(*Parameter_GeospatialField*, geography'POINT(*Parameter_GeospatialValue*)') le *Parameter_GeospatialDistanceValue*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=geo.distance(*Parameter_GeoSpatialField*, geography'POINT(*Parameter_GeoSpatialValue*)') le *Parameter_GeoSpatialDistanceValue*"
/> />
<Request <Request
TestDescription="Support Geospatial Search Implementation" TestDescription="Support GeoSpatial Search Implementation"
RequirementId="REQ-WA103-QM5" RequirementId="REQ-WA103-QM5"
MetallicLevel="Platinum" MetallicLevel="Platinum"
Capability="Query functions" Capability="Query functions"
WebAPIReference="2.4.7" WebAPIReference="2.4.7"
OutputFile="REQ-WA103-QM5_GeospatialLongLat_LatGT1_PointGeo.json" OutputFile="REQ-WA103-QM5_GeoSpatialLongLat_LatGT1_PointGeo.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=geo.distance(*Parameter_GeospatialField*, geography'POINT(*Parameter_GeospatialValue*)') le *Parameter_GeospatialDistanceValue* and *Parameter_GeospatialLatitudeField* gt 1" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=geo.distance(*Parameter_GeoSpatialField*, geography'POINT(*Parameter_GeoSpatialValue*)') le *Parameter_GeoSpatialDistanceValue* and *Parameter_GeoSpatialLatitudeField* gt 1"
/> />
<Request <Request
@ -727,7 +692,7 @@
Capability="Filterability ($filter)" Capability="Filterability ($filter)"
WebAPIReference="2.4.4" WebAPIReference="2.4.4"
OutputFile="REQ-WA103-QO12_Grouping.json" OutputFile="REQ-WA103-QO12_Grouping.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=(*Parameter_FilterNumericField* eq *Parameter_FilterNumericValueLow*) and (*Parameter_FilterNumericField* le *Parameter_FilterNumericValueHigh* and *Parameter_FilterNumericField* ge *Parameter_FilterNumericValueLow*)*Parameter_RequiredParameters*" Url="*ClientSettings_WebAPIURI*/*Parameter_EndpointResource*?$top=*Parameter_TopCount*&amp;$select=*Parameter_SelectList*&amp;$filter=(*Parameter_FilterIntegerField* eq *Parameter_FilterIntegerValueLow*) and (*Parameter_FilterIntegerField* le *Parameter_FilterIntegerValueHigh* and *Parameter_FilterIntegerField* ge *Parameter_FilterIntegerValueLow*)*Parameter_RequiredParameters*"
/> />
<Request <Request
@ -784,7 +749,7 @@
TestDescription="Service Endpoint" TestDescription="Service Endpoint"
RequirementId="REQ-WA103-END1" RequirementId="REQ-WA103-END1"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="" WebAPIReference=""
OutputFile="REQ-WA103-END1_Service.json" OutputFile="REQ-WA103-END1_Service.json"
Url="*ClientSettings_WebAPIURI*/" Url="*ClientSettings_WebAPIURI*/"
@ -793,58 +758,53 @@
<!-- RESPONSE CODE SUPPORT --> <!-- RESPONSE CODE SUPPORT -->
<Request <Request
TestDescription="Assert 200 OK Request" TestDescription="200 OK Request"
RequirementId="REQ-WA103-RC3" RequirementId="REQ-WA103-RC3"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="2.5.2" WebAPIReference="2.5.2"
OutputFile="REQ-WA103-RC05_200OKRequest.json" OutputFile="REQ-WA103-RC05_200OKRequest.json"
Url="ClientSettings_WebAPIURI*/*Parameter_200_OK*" Url="ClientSettings_WebAPIURI*/*Parameter_200_OK*"
AssertResponseCode="200"
/> />
<Request <Request
TestDescription="Assert 400 Bad Request" TestDescription="400 Bad Request"
RequirementId="REQ-WA103-RC5" RequirementId="REQ-WA103-RC5"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="2.5.2" WebAPIReference="2.5.2"
OutputFile="REQ-WA103-RC05_400BadRequest.json" OutputFile="REQ-WA103-RC05_400BadRequest.json"
Url="ClientSettings_WebAPIURI*/*Parameter_400BadRequest*" Url="ClientSettings_WebAPIURI*/*Parameter_400BadRequest*"
AssertResponseCode="400"
/> />
<Request <Request
TestDescription="Assert 403 Forbidden Request" TestDescription="403 Forbidden Request"
RequirementId="REQ-WA103-RC06" RequirementId="REQ-WA103-RC06"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="2.5.2" WebAPIReference="2.5.2"
OutputFile="REQ-WA103-RC06_403Forbidden_Generic.json" OutputFile="REQ-WA103-RC06_403Forbidden_Generic.json"
Url="ClientSettings_WebAPIURI*/*Parameter_403Forbidden*" Url="ClientSettings_WebAPIURI*/*Parameter_403Forbidden*"
AssertResponseCode="403"
/> />
<Request <Request
TestDescription="Assert 404 Not Found Request" TestDescription="404 Not Found Request"
RequirementId="REQ-WA103-RC07" RequirementId="REQ-WA103-RC07"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="2.5.2" WebAPIReference="2.5.2"
OutputFile="REQ-WA103-RC07_404NotFound.json" OutputFile="REQ-WA103-RC07_404NotFound.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_404NotFound*" Url="*ClientSettings_WebAPIURI*/*Parameter_404NotFound*"
AssertResponseCode="404"
/> />
<Request <Request
TestDescription="Assert 501 Not Implemented Request" TestDescription="501 Not Implemented Request"
RequirementId="REQ-WA103-RC11" RequirementId="REQ-WA103-RC11"
MetallicLevel="Core" MetallicLevel="Core"
Capability="Core Support" Capability="Core"
WebAPIReference="2.5.2" WebAPIReference="2.5.2"
OutputFile="REQ-WA103-RC11_501NotImplemented.json" OutputFile="REQ-WA103-RC11_501NotImplemented.json"
Url="*ClientSettings_WebAPIURI*/*Parameter_501NotImplemented*" Url="*ClientSettings_WebAPIURI*/*Parameter_501NotImplemented*"
AssertResponseCode="501"
/> />
</Requests> </Requests>

View File

@ -7,47 +7,145 @@ Feature: Web API Server 1.0.2 Certification
And Client Settings and Parameters were read from the file And Client Settings and Parameters were read from the file
And an OData client was successfully created from the given RESOScript And an OData client was successfully created from the given RESOScript
@REQ-WA103-END3 @core @x.y.z @core-support-endorsement @REQ-WA103-END3 @core @x.y.z @core-endorsement
Scenario: REQ-WA103-END3 - CORE - Request and Validate Server Metadata Scenario: Request and Validate Server Metadata
When a GET request is made to the resolved Url in "REQ-WA103-END3" When a GET request is made to the resolved Url in "REQ-WA103-END3.metadata"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid XML And the response is valid XML
And the metadata returned is valid And the metadata returned is valid
@REQ-WA103-END2 @core @x.y.z @core-support-endorsement @REQ-WA103-END2 @core @x.y.z @core-endorsement
Scenario: REQ-WA103-END2 - CORE - Data System Endpoint test Scenario: Data System Endpoint test
When a GET request is made to the resolved Url in "REQ-WA103-END2" When a GET request is made to the resolved Url in "REQ-WA103-END2.datasystem"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid JSON And the response is valid JSON
And the response has results
And the results match the expected DataSystem JSON schema And the results match the expected DataSystem JSON schema
@REQ-WA103-QR1 @core @2.4.1 @query-functions-endorsement @REQ-WA103-QR1 @core @2.4.1 @query-functions-endorsement
Scenario: REQ-WA103-QR1 - CORE - Search Parameters: Search by UniqueID Scenario: Search Parameters: Select UniqueID
When a GET request is made to the resolved Url in "REQ-WA103-QR1" When a GET request is made to the resolved Url in "REQ-WA103-QR1.select.uniqueId"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid JSON And the response is valid JSON
And the response has singleton results in the "Parameter_UniqueID" field
And the provided "Parameter_UniqueIDValue" is returned in the "Parameter_UniqueID" field And the provided "Parameter_UniqueIDValue" is returned in the "Parameter_UniqueID" field
@REQ-WA103-QR3 @core @2.4.2 @query-functions-endorsement @REQ-WA103-QR3 @core @2.4.2 @query-functions-endorsement
Scenario: REQ-WA103-QR3 - CORE - Query Support: $select Scenario: Query Support: $select
When a GET request is made to the resolved Url in "REQ-WA103-QR3" When a GET request is made to the resolved Url in "REQ-WA103-QR3.select"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid JSON And the response is valid JSON
And the response has results
And data are present in fields contained within "Parameter_SelectList" And data are present in fields contained within "Parameter_SelectList"
@REQ-WA103-QR4 @core @2.4.2 @client-paging-endorsement @REQ-WA103-QR4 @core @2.4.2 @client-paging-endorsement
Scenario: REQ-WA103-QR4 - CORE - Query Support: $top Scenario: Query Support: $top
When a GET request is made to the resolved Url in "REQ-WA103-QR4" When a GET request is made to the resolved Url in "REQ-WA103-QR4.top"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid JSON And the response is valid JSON
And the results contain at most "Parameter_TopCount" records And the response has results
And the number of results is less than or equal to "Parameter_TopCount"
@REQ-WA103-QR5 @core @2.4.2 @query-support @REQ-WA103-QR5 @core @2.4.2 @query-support-endorsement
Scenario: REQ-WA103-QR5 - CORE - Query Support: $skip Scenario: Query Support: $skip
When a GET request is made to the resolved Url in "REQ-WA103-QR5" When a GET request is made to the resolved Url in "REQ-WA103-QR5.skip"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid JSON And the response is valid JSON
And a GET request is made to the resolved Url in "REQ-WA103-QR5" with $skip="Parameter_TopCount" And the response has results
And a GET request is made to the resolved Url in "REQ-WA103-QR5.skip" with $skip="Parameter_TopCount"
Then the server responds with a status code of 200 Then the server responds with a status code of 200
And the response is valid JSON And the response is valid JSON
And the response has results
And data in the "Parameter_UniqueId" fields are different in the second request than in the first And data in the "Parameter_UniqueId" fields are different in the second request than in the first
@REQ-WA103-QO1 @REQ-WA103-QO1.select @core @2.4.4 @core-endorsement @OData-4.0
Scenario: Query Support: $select case-sensitivity for OData 4.0
When a GET request is made to the resolved Url in "REQ-WA103-QO1.select.case"
Then the server responds with a status code of 400 if the server headers report OData version "4.0"
@REQ-WA103-QO1 @REQ-WA103-QO1.filter @core @2.4.4 @core-endorsement @OData-4.0
Scenario: Query Support: $filter case-sensitivity for OData 4.0
When a GET request is made to the resolved Url in "REQ-WA103-QO1.filter.case"
Then the server responds with a status code of 400 if the server headers report OData version "4.0"
@REQ-WA103-QO1 @REQ-WA103-QO1.orderby.asc.case @core @2.4.4 @core-endorsement @OData-4.0
Scenario: Query Support: $orderby asc case-sensitivity for OData 4.0
When a GET request is made to the resolved Url in "REQ-WA103-QO1.orderby.asc.case"
Then the server responds with a status code of 400 if the server headers report OData version "4.0"
@REQ-WA103-QO1 @REQ-WA103-QO1.orderby.desc.case @core @2.4.4 @core-endorsement @OData-4.0
Scenario: Query Support: $orderby desc case-sensitivity for OData 4.0
When a GET request is made to the resolved Url in "REQ-WA103-QO1.orderby.desc.case"
Then the server responds with a status code of 400 if the server headers report OData version "4.0"
@REQ-WA103-QO2 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: eq
When a GET request is made to the resolved Url in "REQ-WA103-QO2.filter.int.compare.eq"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "eq" "Parameter_FilterIntegerValueLow"
@REQ-WA103-QO3 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: ne
When a GET request is made to the resolved Url in "REQ-WA103-QO3.filter.int.compare.ne"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "ne" "Parameter_FilterIntegerValueLow"
@REQ-WA103-QO4 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: gt
When a GET request is made to the resolved Url in "REQ-WA103-QO4.filter.int.compare.gt"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "gt" "Parameter_FilterIntegerValueLow"
@REQ-WA103-QO5 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: ge
When a GET request is made to the resolved Url in "REQ-WA103-QO5.filter.int.compare.ge"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "ge" "Parameter_FilterIntegerValueLow"
@REQ-WA103-QO6 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: lt
When a GET request is made to the resolved Url in "REQ-WA103-QO6.filter.int.compare.lt"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "lt" "Parameter_FilterIntegerValueLow"
@REQ-WA103-QO7 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: le
When a GET request is made to the resolved Url in "REQ-WA103-QO7.filter.int.compare.le"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "le" "Parameter_FilterIntegerValueLow"
@REQ-WA103-QO9 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: and
When a GET request is made to the resolved Url in "REQ-WA103-QO9.filter.int.compare.and"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "gt" "Parameter_FilterIntegerValueLow" "and" "lt" "Parameter_FilterIntegerValueHigh"
@REQ-WA103-QO10 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: or
When a GET request is made to the resolved Url in "REQ-WA103-QO10.filter.int.compare.or"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterIntegerField" "gt" "Parameter_FilterIntegerValueLow" "or" "lt" "Parameter_FilterIntegerValueHigh"
@REQ-WA103-QO11 @core @2.4.4 @filterability-endorsement
Scenario: Query Support: $filter - Integer Comparison: not() (operator)
When a GET request is made to the resolved Url in "REQ-WA103-QO11.filter.int.compare.not.operator"
Then the server responds with a status code of 200
And the response is valid JSON
And the response has results
And Integer data in "Parameter_FilterNotField" "ne" "Parameter_FilterNotValue"

View File

@ -1,13 +1,14 @@
package org.reso.certification.stepdefs; package org.reso.certification.stepdefs;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.ObjectMapper;
import io.cucumber.java8.En; import io.cucumber.java8.En;
import io.restassured.response.Response; import io.restassured.response.Response;
import io.restassured.response.ValidatableResponse; import io.restassured.response.ValidatableResponse;
import io.restassured.specification.RequestSpecification; import io.restassured.specification.RequestSpecification;
import org.apache.http.Header;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger; import org.apache.logging.log4j.Logger;
import org.apache.olingo.client.api.communication.ODataClientErrorException;
import org.apache.olingo.client.api.communication.request.retrieve.ODataRawRequest; import org.apache.olingo.client.api.communication.request.retrieve.ODataRawRequest;
import org.apache.olingo.client.api.communication.response.ODataRawResponse; import org.apache.olingo.client.api.communication.response.ODataRawResponse;
import org.apache.olingo.client.api.edm.xml.XMLMetadata; import org.apache.olingo.client.api.edm.xml.XMLMetadata;
@ -23,8 +24,10 @@ import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
import java.util.HashMap; import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.atomic.AtomicReference; import java.util.concurrent.atomic.AtomicReference;
import java.util.function.Function;
import static io.restassured.path.json.JsonPath.from; import static io.restassured.path.json.JsonPath.from;
import static org.junit.Assert.*; import static org.junit.Assert.*;
@ -40,23 +43,83 @@ public class WebAPIServer_1_0_2 implements En {
private String serviceRoot, bearerToken, clientId, clientSecret, authorizationUri, tokenUri, redirectUri, scope; private String serviceRoot, bearerToken, clientId, clientSecret, authorizationUri, tokenUri, redirectUri, scope;
private String pathToRESOScript; private String pathToRESOScript;
private static final String JSON_VALUE_PATH = "value";
//container to hold retrieved metadata for later comparisons
private static AtomicReference<XMLMetadata> xmlMetadata = new AtomicReference<>();
public WebAPIServer_1_0_2() { public WebAPIServer_1_0_2() {
//TODO: split into separate test files and parallelize to remove the need for Atomic "globals" //TODO: split into separate test files and parallelize to remove the need for Atomic "globals"
AtomicReference<Commander> commander = new AtomicReference<>(); AtomicReference<Commander> commander = new AtomicReference<>();
AtomicReference<ODataRawResponse> oDataRawResponse = new AtomicReference<>(); AtomicReference<ODataRawResponse> oDataRawResponse = new AtomicReference<>();
AtomicReference<Request> request = new AtomicReference<>(); AtomicReference<Request> request = new AtomicReference<>();
AtomicReference<Integer> responseCode = new AtomicReference<>();
AtomicReference<String> responseData = new AtomicReference<>(); AtomicReference<String> responseData = new AtomicReference<>();
AtomicReference<String> initialResponseData = new AtomicReference<>(); //used if two result sets need to be compared AtomicReference<String> initialResponseData = new AtomicReference<>(); //used if two result sets need to be compared
AtomicReference<ODataRawRequest> rawRequest = new AtomicReference<>(); AtomicReference<ODataRawRequest> rawRequest = new AtomicReference<>();
//container to hold retrieved metadata for later comparisons AtomicReference<ODataClientErrorException> oDataClientErrorException = new AtomicReference<>();
AtomicReference<XMLMetadata> xmlMetadata = new AtomicReference<>(); AtomicReference<Boolean> oDataClientErrorExceptionHandled = new AtomicReference<>();
AtomicReference<String> serverODataHeaderVersion = new AtomicReference<>();
AtomicReference<Boolean> testAppliesToServerODataHeaderVersion = new AtomicReference<>();
final String HEADER_ODATA_VERSION = "OData-Version";
/*
* Instance Utility Methods - must precede usage
*/
/*
* Resets the local instance state used during test time. TODO: refactor into collection of AtomicReference<T>
*/
Runnable resetState = () -> {
commander.set(null);
oDataRawResponse.set(null);
request.set(null);
responseCode.set(null);
responseData.set(null);
initialResponseData.set(null);
rawRequest.set(null);
oDataClientErrorException.set(null);
serverODataHeaderVersion.set(null);
oDataClientErrorExceptionHandled.set(false);
testAppliesToServerODataHeaderVersion.set(false);
};
/*
* Executes HTTP GET request and sets the expected local variables.
* Handles exceptions and sets response codes.
*/
Function<URI, Void> executeGetRequest = (URI requestUri) -> {
LOG.info("Request URI: " + requestUri);
try {
rawRequest.set(commander.get().getClient().getRetrieveRequestFactory().getRawRequest(requestUri));
oDataRawResponse.set(rawRequest.get().execute());
responseData.set(convertInputStreamToString(oDataRawResponse.get().getRawResponse()));
serverODataHeaderVersion.set(oDataRawResponse.get().getHeader(HEADER_ODATA_VERSION).toString());
LOG.info("Request succeeded..." + responseData.get().getBytes().length + " bytes received.");
} catch (ODataClientErrorException cex) {
LOG.debug("OData Client Error Exception caught. Check subsequent test output for asserted conditions...");
oDataClientErrorException.set(cex);
serverODataHeaderVersion.set(Utils.getHeaderData(HEADER_ODATA_VERSION, cex.getHeaderInfo()));
responseCode.set(cex.getStatusLine().getStatusCode());
oDataClientErrorExceptionHandled.set(true);
}
return null;
};
/* /*
* Background * Background
*/ */
Given("^a RESOScript file was provided$", () -> { Given("^a RESOScript file was provided$", () -> {
/* NOTE: this item is the first step in the Background */
//Reset ALL local state variables prior to each run.
resetState.run();
if (pathToRESOScript == null) { if (pathToRESOScript == null) {
pathToRESOScript = System.getProperty("pathToRESOScript"); pathToRESOScript = System.getProperty("pathToRESOScript");
} }
@ -156,7 +219,7 @@ public class WebAPIServer_1_0_2 implements En {
AtomicInteger numResults = new AtomicInteger(); AtomicInteger numResults = new AtomicInteger();
//iterate over the items and count the number of fields with data to determine whether there are data present //iterate over the items and count the number of fields with data to determine whether there are data present
from(responseData.get()).getList("value", HashMap.class).forEach(item -> { from(responseData.get()).getList(JSON_VALUE_PATH, HashMap.class).forEach(item -> {
if (item != null) { if (item != null) {
numResults.getAndIncrement(); numResults.getAndIncrement();
fieldList.forEach(field -> { fieldList.forEach(field -> {
@ -180,7 +243,7 @@ public class WebAPIServer_1_0_2 implements En {
* $top=*Parameter_TopCount* * $top=*Parameter_TopCount*
*/ */
And("^the results contain at most \"([^\"]*)\" records$", (String parameterTopCount) -> { And("^the results contain at most \"([^\"]*)\" records$", (String parameterTopCount) -> {
List<String> items = from(responseData.get()).getList("value"); List<String> items = from(responseData.get()).getList(JSON_VALUE_PATH);
AtomicInteger numResults = new AtomicInteger(items.size()); AtomicInteger numResults = new AtomicInteger(items.size());
int topCount = Integer.parseInt(Utils.resolveValue(parameterTopCount, settings)); int topCount = Integer.parseInt(Utils.resolveValue(parameterTopCount, settings));
@ -204,19 +267,18 @@ public class WebAPIServer_1_0_2 implements En {
//TODO: convert to OData filter factory //TODO: convert to OData filter factory
URI requestUri = Commander.prepareURI(Settings.resolveParameters(settings.getRequests().get(requirementId), settings).getUrl() + "&$skip=" + skipCount); URI requestUri = Commander.prepareURI(Settings.resolveParameters(settings.getRequests().get(requirementId), settings).getUrl() + "&$skip=" + skipCount);
LOG.info("Request URI: " + (requestUri != null ? requestUri.toString() : "")); LOG.info("Request URI: " + (requestUri != null ? requestUri.toString() : ""));
rawRequest.set(commander.get().getClient().getRetrieveRequestFactory().getRawRequest(requestUri));
oDataRawResponse.set(rawRequest.get().execute()); executeGetRequest.apply(requestUri);
responseData.set(convertInputStreamToString(oDataRawResponse.get().getRawResponse()));
}); });
And("^data in the \"([^\"]*)\" fields are different in the second request than in the first$", (String parameterUniqueId) -> { And("^data in the \"([^\"]*)\" fields are different in the second request than in the first$", (String parameterUniqueId) -> {
ObjectMapper mapper = new ObjectMapper(); ObjectMapper mapper = new ObjectMapper();
JsonNode n1 = mapper.readTree(initialResponseData.get()); List<Object> l1 = from(initialResponseData.get()).getList(JSON_VALUE_PATH);
JsonNode n2 = mapper.readTree(responseData.get()); List<Object> l2 = from(responseData.get()).getList(JSON_VALUE_PATH);
assertFalse(n1.equals(n2)); assertFalse(l1.containsAll(l2));
}); });
//================================================================================================================== //==================================================================================================================
// Common Methods // Common Methods
//================================================================================================================== //==================================================================================================================
@ -226,51 +288,19 @@ public class WebAPIServer_1_0_2 implements En {
*/ */
When("^a GET request is made to the resolved Url in \"([^\"]*)\"$", (String requirementId) -> { When("^a GET request is made to the resolved Url in \"([^\"]*)\"$", (String requirementId) -> {
URI requestUri = Commander.prepareURI(Settings.resolveParameters(settings.getRequests().get(requirementId), settings).getUrl()); URI requestUri = Commander.prepareURI(Settings.resolveParameters(settings.getRequests().get(requirementId), settings).getUrl());
LOG.info("Request URI: " + requestUri); executeGetRequest.apply(requestUri);
rawRequest.set(commander.get().getClient().getRetrieveRequestFactory().getRawRequest(requestUri));
oDataRawResponse.set(rawRequest.get().execute());
responseData.set(convertInputStreamToString(oDataRawResponse.get().getRawResponse()));
LOG.info("Request succeeded..." + responseData.get().getBytes().length + " bytes received.");
});
/*
* GET request by requirementId with an additional Uri fragment for the base Uri
*/
When("^a GET request is made to the resolved Url in \"([^\"]*)\" with \"([^\"]*)\"$", (String requirementId, String parameterTopCount) -> {
request.set(Settings.resolveParameters(settings.getRequests().get(requirementId), settings));
LOG.info("Request URL: " + request.get().getUrl());
rawRequest.set(commander.get().getClient().getRetrieveRequestFactory().getRawRequest(Commander.prepareURI(request.get().getUrl())));
oDataRawResponse.set(rawRequest.get().execute());
responseData.set(convertInputStreamToString(oDataRawResponse.get().getRawResponse()));
LOG.info("Request succeeded..." + responseData.get().getBytes().length + " bytes received.");
}); });
/* /*
* Assert response code * Assert response code
*/ */
Then("^the server responds with a status code of (\\d+)$", (Integer code) -> { Then("^the server responds with a status code of (\\d+)$", (Integer assertedResponseCode) -> {
int responseCode = oDataRawResponse.get().getStatusCode(); responseCode.set(oDataClientErrorException.get() != null
LOG.info("Response code is: " + responseCode); ? oDataClientErrorException.get().getStatusLine().getStatusCode()
assertEquals(code.intValue(), responseCode); : oDataRawResponse.get().getStatusCode());
});
/* LOG.info("Asserted Response Code: " + assertedResponseCode + ", " + "Server Response Code: " + responseCode);
* Assert greater than: lValFromItem > rValFromSetting assertEquals(responseCode.get().intValue(), assertedResponseCode.intValue());
*
* TODO: add general op expression parameter rather than creating individual comparators
*/
And("^data in \"([^\"]*)\" are greater than \"([^\"]*)\"$", (String lValFromItem, String rValFromSetting) -> {
from(responseData.get()).getList("value", HashMap.class).forEach(item -> {
Integer lVal = new Integer(item.get(Utils.resolveValue(lValFromItem, settings)).toString()),
rVal = new Integer(Utils.resolveValue(rValFromSetting, settings));
assertTrue( lVal > rVal );
});
}); });
/* /*
@ -291,12 +321,183 @@ public class WebAPIServer_1_0_2 implements En {
LOG.info("Response is valid JSON!"); LOG.info("Response is valid JSON!");
}); });
/*
* Assert OData version
*/
And("^the server reports OData version \"([^\"]*)\"$", (String assertODataVersion) -> {
LOG.info("Asserted version: " + assertODataVersion + ", Reported OData Version: " + serverODataHeaderVersion.get()); ;
assertEquals(serverODataHeaderVersion.get(), assertODataVersion);
});
/*
* Assert HTTP Response Code given asserted OData version
*
* TODO: make a general Header assertion function
*/
Then("^the server responds with a status code of (\\d+) if the server headers report OData version \"([^\"]*)\"$",
(Integer assertedHttpResponseCode, String assertedODataVersion) -> {
boolean versionsMatch = responseCode.get().intValue() == assertedHttpResponseCode.intValue(),
responseCodesMatch = serverODataHeaderVersion.get().equals(assertedODataVersion);
if (versionsMatch) {
assertTrue(responseCodesMatch);
}
});
/*
* Compares field data (LHS) to a given parameter value (RHS). The operator is passed as a string,
* and is used to select among the supported comparisons.
*/
And("^Integer data in \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\"$", (String parameterFieldName, String op, String parameterAssertedValue) -> {
LOG.info("Parameter_FieldName: " + parameterFieldName + ", op: " + op + ", Parameter_Value: " + parameterAssertedValue);
String fieldName = Utils.resolveValue(parameterFieldName, settings);
int assertedValue = Integer.parseInt(Utils.resolveValue(parameterAssertedValue, settings));
//subsequent value comparisons are and-ed together while iterating over the list of items, so init to true
AtomicBoolean result = new AtomicBoolean(true);
AtomicReference<Integer> fieldValue = new AtomicReference<>();
//iterate through response data and ensure that with data, the statement fieldName "op" assertValue is true
from(responseData.get()).getList(JSON_VALUE_PATH, HashMap.class).forEach(item -> {
fieldValue.set(Integer.parseInt(item.get(fieldName).toString()));
result.set(result.get() && Utils.compare(fieldValue.get(), op, assertedValue));
LOG.info("Compare: " + fieldValue.get() + " " + op + " " + assertedValue + " is " + result.get());
});
assertTrue(result.get());
});
/*
* True if response has results, meaning value.length > 0
*/
And("^the response has results$", () -> {
int count = from(responseData.get()).getList(JSON_VALUE_PATH, HashMap.class).size();
LOG.info("Results count is: " + count);
assertTrue(count > 0);
});
/*
* True if data are present in the response
*/
And("^the response has singleton results in the \"([^\"]*)\" field$", (String parameterFieldName) -> {
String value = Utils.resolveValue(parameterFieldName, settings);
boolean isPresent = from(responseData.get()).get() != null && value != null;
LOG.info("Response value is: " + value);
LOG.info("IsPresent: " + isPresent);
assertTrue(isPresent);
});
/*
* True if results count less than or equal to limit
*/
And("^the number of results is less than or equal to \"([^\"]*)\"$", (String limitField) -> {
int count = from(responseData.get()).getList(JSON_VALUE_PATH, HashMap.class).size(),
limit = Integer.parseInt(Utils.resolveValue(limitField, settings));
LOG.info("Results count is: " + count + ", Limit is: " + limit);
assertTrue(count <= limit);
});
/*
* True if data in the lhs expression and rhs expressions pass the AND or OR condition given in andOrOp
*/
And("^Integer data in \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\" \"([^\"]*)\"$", (String parameterFieldName, String opLhs, String parameterAssertedLhsValue, String andOrOp, String opRhs, String parameterAssertedRhsValue) -> {
String fieldName = Utils.resolveValue(parameterFieldName, settings);
Integer assertedLhsValue = Integer.parseInt(Utils.resolveValue(parameterAssertedLhsValue, settings)),
assertedRhsValue = Integer.parseInt(Utils.resolveValue(parameterAssertedRhsValue, settings));
String op = andOrOp.toLowerCase();
boolean isAndOp = op.contains(Operators.AND);
//these should default to true when And and false when Or for the purpose of boolean comparisons
AtomicBoolean lhsResult = new AtomicBoolean(isAndOp);
AtomicBoolean rhsResult = new AtomicBoolean(isAndOp);
AtomicBoolean itemResult = new AtomicBoolean(isAndOp);
AtomicReference<Integer> lhsValue = new AtomicReference<>(),
rhsValue = new AtomicReference<>();
//iterate through response data and ensure that with data, the statement fieldName "op" assertValue is true
from(responseData.get()).getList(JSON_VALUE_PATH, HashMap.class).forEach(item -> {
lhsValue.set(Integer.parseInt(item.get(fieldName).toString()));
rhsValue.set(Integer.parseInt(item.get(fieldName).toString()));
LOG.info("Checking LHS");
lhsResult.set(Utils.compare(lhsValue.get(), opLhs, assertedLhsValue));
LOG.info("Checking RHS");
rhsResult.set(Utils.compare(rhsValue.get(), opRhs, assertedRhsValue));
if (op.contentEquals(Operators.AND)) {
itemResult.set(lhsResult.get() && rhsResult.get());
LOG.info("assertTrue: " + lhsResult.get() + " AND " + rhsResult.get() + " ==> " + itemResult.get());
assertTrue(itemResult.get());
} else if (op.contentEquals(Operators.OR)) {
itemResult.set(lhsResult.get() || rhsResult.get());
LOG.info("assertTrue: " + lhsResult.get() + " OR " + rhsResult.get() + " ==> " + itemResult.get());
assertTrue(itemResult.get());
}
});
});
}
/**
* Contains the list of supported operators for use in query expressions.
*/
private static class Operators {
private static final String
AND = "and",
OR = "or",
NE = "ne",
EQ = "eq",
GREATER_THAN = "gt",
GREATER_THAN_OR_EQUAL = "ge",
LESS_THAN = "lt",
LESS_THAN_OR_EQUAL = "le";
} }
private static class Utils { private static class Utils {
/**
* Returns true if each item in the list is true
* @param lhs left hand value
* @param op a binary operator for use in comparsions
* @param rhs right hand value
* @return true if lhs op rhs produces true, false otherwise
*/
private static boolean compare(Integer lhs, String op, Integer rhs) {
boolean result = false;
switch (op) {
case Operators.EQ:
result = lhs.equals(rhs);
break;
case Operators.NE:
result = !lhs.equals(rhs);
break;
case Operators.GREATER_THAN:
result = lhs > rhs;
break;
case Operators.GREATER_THAN_OR_EQUAL:
result = lhs >= rhs;
break;
case Operators.LESS_THAN:
result = lhs < rhs;
break;
case Operators.LESS_THAN_OR_EQUAL:
result = lhs <= rhs;
break;
}
LOG.info("Compare: " + lhs + " " + op + " " + rhs + " ==> " + result);
return result;
}
/** /**
* Tests the given string to see if it's valid JSON * Tests the given string to see if it's valid JSON
* @param jsonString * @param jsonString the JSON string to test the validity of
* @return true if valid, false otherwise. Throws {@link IOException} * @return true if valid, false otherwise. Throws {@link IOException}
*/ */
private static boolean isValidJson(String jsonString) { private static boolean isValidJson(String jsonString) {
@ -334,16 +535,16 @@ public class WebAPIServer_1_0_2 implements En {
private static String getResponseData(ODataRawResponse oDataRawResponse) { private static String getResponseData(ODataRawResponse oDataRawResponse) {
return convertInputStreamToString(oDataRawResponse.getRawResponse()); return convertInputStreamToString(oDataRawResponse.getRawResponse());
} }
}
/** private static String getHeaderData(String key, Header[] headers) {
* These are now passed dynamically but we may want to verify the choices. Leave in for now. String data = null;
*/
private static class REQUESTS { for(Header header : headers) {
private static class WEB_API_1_0_2 { if (header.getName().toLowerCase().contains(key.toLowerCase())) {
private static final String REQ_WA_103_END_3 = "REQ-WA103-END3"; data = header.getValue();
private static final String REQ_WA_103_QR_3 = "REQ-WA103-QR3"; }
private static final String REQ_WA103_END2 = "REQ-WA103-END2"; }
return data;
} }
} }

View File

@ -170,12 +170,12 @@ public class App {
//TODO: create dynamic JUnit (or similar) test runner //TODO: create dynamic JUnit (or similar) test runner
LOG.info(SMALL_DIVIDER); LOG.info(SMALL_DIVIDER);
LOG.info("Assertion: #" + (i + 1)); LOG.info("Request: #" + (i + 1));
LOG.info(SMALL_DIVIDER); LOG.info(SMALL_DIVIDER);
LOG.info("Assertion Name: " + request.getName()); LOG.info("Request Name: " + request.getName());
//TODO: function-ize the property test //TODO: function-ize the property test
LOG.info("Assertion Description: " + (request.getTestDescription().length() > 0 ? request.getTestDescription() : "Not Specified")); LOG.info("Description: " + (request.getTestDescription().length() > 0 ? request.getTestDescription() : "Not Specified"));
LOG.info("Requirement Id: " + (request.getRequirementId().length() > 0 ? request.getRequirementId() : "Not Specified")); LOG.info("Requirement Id: " + (request.getRequirementId().length() > 0 ? request.getRequirementId() : "Not Specified"));
LOG.info("Metallic Level: " + (request.getMetallicLevel().length() > 0 ? request.getMetallicLevel() : "Not Specified")); LOG.info("Metallic Level: " + (request.getMetallicLevel().length() > 0 ? request.getMetallicLevel() : "Not Specified"));
LOG.info("Capability: " + (request.getCapability().length() > 0 ? request.getCapability() : "Not Specified")); LOG.info("Capability: " + (request.getCapability().length() > 0 ? request.getCapability() : "Not Specified"));
@ -200,6 +200,8 @@ public class App {
if (responseCode == HttpStatus.SC_OK) { if (responseCode == HttpStatus.SC_OK) {
STATS.updateRequest(request, Request.Status.SUCCEEDED); STATS.updateRequest(request, Request.Status.SUCCEEDED);
} else {
STATS.updateRequest(request, Request.Status.FAILED);
} }
if (request.getOutputFile().toLowerCase().contains(EDMX_EXTENSION.toLowerCase())) { if (request.getOutputFile().toLowerCase().contains(EDMX_EXTENSION.toLowerCase())) {
@ -210,16 +212,9 @@ public class App {
LOG.error("Error: Invalid metadata retrieved. Cannot continue!!"); LOG.error("Error: Invalid metadata retrieved. Cannot continue!!");
System.exit(NOT_OK); System.exit(NOT_OK);
} }
} else if (responseCode != null && request.getAssertResponseCode() != null) {
if (responseCode == Integer.parseInt(request.getAssertResponseCode())) {
LOG.info("Assert Response Code " + request.getAssertResponseCode() + " passed!");
} else {
LOG.error("Request " + request.getName() + " Failed!");
STATS.updateRequest(request, Request.Status.FAILED);
}
} }
} else { } else {
LOG.info("Request " + request.getRequirementId() + " has an empty URL. Skipping...");
STATS.updateRequest(request, Request.Status.SKIPPED); STATS.updateRequest(request, Request.Status.SKIPPED);
} }
} catch (Exception ex) { } catch (Exception ex) {
@ -228,10 +223,6 @@ public class App {
LOG.error("Stack trace:"); LOG.error("Stack trace:");
Arrays.stream(ex.getStackTrace()).forEach(stackTraceElement -> LOG.error(stackTraceElement.toString())); Arrays.stream(ex.getStackTrace()).forEach(stackTraceElement -> LOG.error(stackTraceElement.toString()));
} finally { } finally {
if (request != null && STATS.getRequests().size() > 0) {
LOG.info("Request " + STATS.getRequests().get(request).getStatus().toString().toLowerCase() + "!");
}
if (resolvedUrl != null && resolvedUrl.length() > 0) { if (resolvedUrl != null && resolvedUrl.length() > 0) {
LOG.info("Elapsed Time: " + String.format("%.2f", (STATS.getRequests().get(request).getElapsedTimeMillis() / 1000.0)) + "s"); LOG.info("Elapsed Time: " + String.format("%.2f", (STATS.getRequests().get(request).getElapsedTimeMillis() / 1000.0)) + "s");
} }
@ -443,7 +434,7 @@ public class App {
numIncomplete = stats.getRequestCount(Request.Status.STARTED); numIncomplete = stats.getRequestCount(Request.Status.STARTED);
reportBuilder.append("\n\n" + DIVIDER); reportBuilder.append("\n\n" + DIVIDER);
reportBuilder.append("\nAssertion Statistics"); reportBuilder.append("\nRequest Statistics");
reportBuilder.append("\n" + DIVIDER); reportBuilder.append("\n" + DIVIDER);
reportBuilder.append(generateTotalsReport(stats.totalRequestCount(), numSucceeded, numFailed, numSkipped, numIncomplete)); reportBuilder.append(generateTotalsReport(stats.totalRequestCount(), numSucceeded, numFailed, numSkipped, numIncomplete));
@ -462,7 +453,7 @@ public class App {
numSkipped = stats.filterByMetallicCertification(metallicKey, stats.filterByStatus(Request.Status.SKIPPED)).size(); numSkipped = stats.filterByMetallicCertification(metallicKey, stats.filterByStatus(Request.Status.SKIPPED)).size();
numIncomplete = stats.filterByMetallicCertification(metallicKey, stats.filterByStatus(Request.Status.STARTED)).size(); numIncomplete = stats.filterByMetallicCertification(metallicKey, stats.filterByStatus(Request.Status.STARTED)).size();
reportBuilder.append("\n\n").append(metallicKey).append(numSucceeded > 0 && numSucceeded == (requestCount - numSkipped) ? " - REQUESTS SUCCEEDED!" : ""); reportBuilder.append("\n\n").append(metallicKey).append(numSucceeded > 0 && numSucceeded == (requestCount - numSkipped) ? " - ALL REQUESTS SUCCEEDED!" : "");
reportBuilder.append(generateTotalsReport(requestCount, numSucceeded, numFailed, numSkipped, numIncomplete)); reportBuilder.append(generateTotalsReport(requestCount, numSucceeded, numFailed, numSkipped, numIncomplete));
} }
@ -477,7 +468,7 @@ public class App {
numSkipped = stats.filterByCapability(capabilityKey, stats.filterByStatus(Request.Status.SKIPPED)).size(); numSkipped = stats.filterByCapability(capabilityKey, stats.filterByStatus(Request.Status.SKIPPED)).size();
numIncomplete = stats.filterByCapability(capabilityKey, stats.filterByStatus(Request.Status.STARTED)).size(); numIncomplete = stats.filterByCapability(capabilityKey, stats.filterByStatus(Request.Status.STARTED)).size();
reportBuilder.append("\n\n").append(capabilityKey).append(numSucceeded > 0 && numSucceeded == (requestCount - numSkipped) ? " - REQUESTS SUCCEEDED!" : ""); reportBuilder.append("\n\n").append(capabilityKey).append(numSucceeded > 0 && numSucceeded == (requestCount - numSkipped) ? " - ALL REQUESTS SUCCEEDED!" : "");
reportBuilder.append(generateTotalsReport(requestCount, numSucceeded, numFailed, numSkipped, numIncomplete)); reportBuilder.append(generateTotalsReport(requestCount, numSucceeded, numFailed, numSkipped, numIncomplete));
} }
reportBuilder.append("\n" + DIVIDER + "\n"); reportBuilder.append("\n" + DIVIDER + "\n");

View File

@ -24,7 +24,6 @@ public class Request {
private String metallicLevel; private String metallicLevel;
private String capability; private String capability;
private String webApiReference; private String webApiReference;
private String assertResponseCode;
private Request request; private Request request;
private Status status; private Status status;
@ -41,7 +40,7 @@ public class Request {
* @param url * @param url
*/ */
public Request(String requirementId, String outputFile, String url, String testDescription, String metallicLevel, public Request(String requirementId, String outputFile, String url, String testDescription, String metallicLevel,
String capability, String webApiReference, String assertResponseCode) { String capability, String webApiReference) {
//TODO: add Builder //TODO: add Builder
setRequirementId(requirementId); setRequirementId(requirementId);
@ -51,7 +50,6 @@ public class Request {
setMetallicLevel(metallicLevel); setMetallicLevel(metallicLevel);
setCapability(capability); setCapability(capability);
setWebApiReference(webApiReference); setWebApiReference(webApiReference);
setAssertResponseCode(assertResponseCode);
} }
@ -123,8 +121,7 @@ public class Request {
String expression = "/OutputScript/" + REQUESTS_KEY + "/node()"; String expression = "/OutputScript/" + REQUESTS_KEY + "/node()";
NodeList nodes = (NodeList) xPath.compile(expression).evaluate(xmlDocument, XPathConstants.NODESET); NodeList nodes = (NodeList) xPath.compile(expression).evaluate(xmlDocument, XPathConstants.NODESET);
Node node; Node node;
String name, outputFile, url, testDescription, requirementId, metallicLevel, capability, webApiReference, String name, outputFile, url, testDescription, requirementId, metallicLevel, capability, webApiReference;
assertResponseCode;
Request request; Request request;
for (int i = 0; i < nodes.getLength(); i++) { for (int i = 0; i < nodes.getLength(); i++) {
@ -138,9 +135,8 @@ public class Request {
metallicLevel = safeGetNamedItem(FIELDS.METALLIC_LEVEL, node); metallicLevel = safeGetNamedItem(FIELDS.METALLIC_LEVEL, node);
capability = safeGetNamedItem(FIELDS.CAPABILITY, node); capability = safeGetNamedItem(FIELDS.CAPABILITY, node);
webApiReference = safeGetNamedItem(FIELDS.WEB_API_REFERENCE, node); webApiReference = safeGetNamedItem(FIELDS.WEB_API_REFERENCE, node);
assertResponseCode = safeGetNamedItem(FIELDS.ASSERT_RESPONSE_CODE, node);
request = new Request(requirementId, outputFile, url, testDescription, metallicLevel, capability, webApiReference, assertResponseCode); request = new Request(requirementId, outputFile, url, testDescription, metallicLevel, capability, webApiReference);
name = safeGetNamedItem(FIELDS.NAME, node); name = safeGetNamedItem(FIELDS.NAME, node);
request.setName(name == null ? outputFile : name); request.setName(name == null ? outputFile : name);
@ -249,14 +245,6 @@ public class Request {
this.webApiReference = webApiReference; this.webApiReference = webApiReference;
} }
public String getAssertResponseCode() {
return assertResponseCode;
}
public void setAssertResponseCode(String assertResponseCode) {
this.assertResponseCode = assertResponseCode;
}
private static final class FIELDS { private static final class FIELDS {
static final String NAME = "Name"; static final String NAME = "Name";
static final String OUTPUT_FILE = "OutputFile"; static final String OUTPUT_FILE = "OutputFile";
@ -266,6 +254,5 @@ public class Request {
static final String METALLIC_LEVEL = "MetallicLevel"; static final String METALLIC_LEVEL = "MetallicLevel";
static final String CAPABILITY = "Capability"; static final String CAPABILITY = "Capability";
static final String WEB_API_REFERENCE = "WebAPIReference"; static final String WEB_API_REFERENCE = "WebAPIReference";
static final String ASSERT_RESPONSE_CODE = "AssertResponseCode";
} }
} }

View File

@ -59,7 +59,7 @@ public class Settings {
public static Request resolveParameters(Request request, Settings settings) { public static Request resolveParameters(Request request, Settings settings) {
//calls to resolve nested parameters //calls to resolve nested parameters
return new Request(request.getRequirementId(), request.getOutputFile(), resolveParametersString(request.getUrl(), settings), request.getTestDescription(), return new Request(request.getRequirementId(), request.getOutputFile(), resolveParametersString(request.getUrl(), settings), request.getTestDescription(),
request.getMetallicLevel(), request.getCapability(), request.getWebApiReference(), request.getAssertResponseCode()); request.getMetallicLevel(), request.getCapability(), request.getWebApiReference());
} }
/** /**

View File

@ -6,8 +6,7 @@ package org.reso.commander;
import org.junit.Test; import org.junit.Test;
public class AppTest { public class AppTest {
@Test public void testAppHasAGreeting() { @Test public void testParameterDeserialization() {
App classUnderTest = new App(); //TODO
//assertNotNull("app should have a greeting", classUnderTest.getGreeting());
} }
} }