package com.interaction.example.odata.multicompany; /* * #%L * interaction-example-odata-multicompany * %% * Copyright (C) 2012 - 2013 Temenos Holdings N.V. * %% * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. * #L% */ import static org.junit.Assert.*; import java.io.IOException; import java.io.StringReader; import java.util.List; import org.apache.abdera.Abdera; import org.apache.abdera.model.Document; import org.apache.abdera.parser.Parser; import org.apache.commons.httpclient.HttpClient; import org.apache.commons.httpclient.HttpStatus; import org.apache.commons.httpclient.methods.GetMethod; import org.core4j.Enumerable; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.odata4j.consumer.ODataConsumer; import org.odata4j.core.OEntity; import org.odata4j.core.OLink; import org.odata4j.jersey.consumer.ODataJerseyConsumer; /** * This test ensures that this projects OData entities have working * OData associations (links). * * @author aphethean */ public class ODataMulticompanyITCase { private final static String FLIGHT_ENTITYSET_NAME = "Flights"; private final static String FLIGHT_SCHEDULE_ENTITYSET_NAME = "FlightSchedules"; private final static String AIRPORT_ENTITYSET_NAME = "Airports"; private String baseUri = null; private HttpClient client; public ODataMulticompanyITCase() throws Exception { super(); } @Before public void setup() { baseUri = ConfigurationHelper.getTestEndpointUri(Configuration.TEST_ENDPOINT_URI); client = new HttpClient(); } @After public void tearDown() {} @Test public void testGetServiceDocumentUri() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); // get the service document for the company specific service document String serviceRootUri = consumer.getServiceRootUri(); assertNotNull(serviceRootUri); GetMethod method = new GetMethod(serviceRootUri); String response = null; try { method.setDoAuthentication(true); //Require authentication client.executeMethod(method); assertEquals(200, method.getStatusCode()); if (method.getStatusCode() == HttpStatus.SC_OK) { // read as string response = method.getResponseBodyAsString(); } } catch (IOException e) { fail(e.getMessage()); } finally { method.releaseConnection(); } // assert the Users entity set exists in service document assertTrue(response.contains("<collection href=\"Flights\">")); } @Test public void testGetServiceDocumentBaseUri() throws Exception { org.apache.abdera.model.Service service = null; GetMethod method = new GetMethod(baseUri); try { client.executeMethod(method); assertEquals(200, method.getStatusCode()); if (method.getStatusCode() == HttpStatus.SC_OK) { // read as string for debugging String response = method.getResponseBodyAsString(); System.out.println("Response = " + response); Abdera abdera = new Abdera(); Parser parser = abdera.getParser(); Document<org.apache.abdera.model.Service> doc = parser.parse(new StringReader(response)); service = doc.getRoot(); } } catch (IOException e) { fail(e.getMessage()); } finally { method.releaseConnection(); } assertNotNull(service); assertEquals("http://localhost:8080/example/interaction-odata-multicompany.svc/MockCompany001/", service.getBaseUri().toString()); } @Test public void testGetServiceDocumentBaseUriWithoutTrailingSlash() throws Exception { org.apache.abdera.model.Service service = null; String testBaseUri = baseUri; if (testBaseUri.endsWith("/")) testBaseUri = testBaseUri.substring(0, testBaseUri.length() - 1); GetMethod method = new GetMethod(testBaseUri); try { client.executeMethod(method); assertEquals(200, method.getStatusCode()); if (method.getStatusCode() == HttpStatus.SC_OK) { // read as string for debugging String response = method.getResponseBodyAsString(); System.out.println("Response = " + response); Abdera abdera = new Abdera(); Parser parser = abdera.getParser(); Document<org.apache.abdera.model.Service> doc = parser.parse(new StringReader(response)); service = doc.getRoot(); } } catch (IOException e) { fail(e.getMessage()); } finally { method.releaseConnection(); } assertNotNull(service); assertEquals("http://localhost:8080/example/interaction-odata-multicompany.svc/MockCompany001/", service.getBaseUri().toString()); } /** * GET item, check id of entity */ @Test public void getFlightCheckId() throws Exception { org.apache.abdera.model.Entry entry = null; GetMethod method = new GetMethod(baseUri + "Flights(2)"); try { client.executeMethod(method); assertEquals(200, method.getStatusCode()); if (method.getStatusCode() == HttpStatus.SC_OK) { // read as string for debugging String response = method.getResponseBodyAsString(); System.out.println("Response = " + response); Abdera abdera = new Abdera(); Parser parser = abdera.getParser(); Document<org.apache.abdera.model.Entry> doc = parser.parse(new StringReader(response)); entry = doc.getRoot(); } } catch (IOException e) { fail(e.getMessage()); } finally { method.releaseConnection(); } assertNotNull(entry); assertEquals("http://localhost:8080/example/interaction-odata-multicompany.svc/MockCompany001/Flights(2)", entry.getId().toString()); } /** * GET collection, check link to self and other entities for each item */ @Test public void getFlightsLinksToFlightSchedule() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); Enumerable<OEntity> flights = consumer.getEntities(FLIGHT_ENTITYSET_NAME).execute(); assertEquals(4, flights.toSet().size()); for (OEntity flight : flights.toSet()) { Long flightID = (Long) flight.getProperty("flightID").getValue(); Long flightScheduleNum = (Long) flight.getProperty("flightScheduleNum").getValue(); assertEquals(1, flight.getLinks().size()); // there should be one link to one flight schedule for this flight assertTrue(containsLink(flight.getLinks(), FLIGHT_ENTITYSET_NAME + "(" + flightID + ")/flightSchedule") || containsLink(flight.getLinks(), FLIGHT_SCHEDULE_ENTITYSET_NAME + "(" + flightScheduleNum + ")")); } } /** * GET item, check link to another entity */ @Test public void getFlightLinksToFlightSchedule() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); OEntity flight = consumer.getEntity(FLIGHT_ENTITYSET_NAME, 2).execute(); Long flightID = (Long) flight.getProperty("flightID").getValue(); assertEquals(2, flightID.intValue()); Long flightScheduleNum = (Long) flight.getProperty("flightScheduleNum").getValue(); // there should be one link to one flight schedule for this flight assertEquals(1, flight.getLinks().size()); assertTrue(containsLink(flight.getLinks(), FLIGHT_ENTITYSET_NAME + "(" + flightID + ")/flightSchedule") || containsLink(flight.getLinks(), FLIGHT_SCHEDULE_ENTITYSET_NAME + "(" + flightScheduleNum + ")")); } /** * GET collection, check link to self and other entities for each item */ @Test public void getFlightSchedulesLinksToFlightSchedule() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); Enumerable<OEntity> flightSchedules = consumer.getEntities(FLIGHT_SCHEDULE_ENTITYSET_NAME).execute(); // if the test is run multiple times it will be greater than 7 assertTrue(flightSchedules.toSet().size() >= 7); for (OEntity flightSchedule : flightSchedules.toSet()) { Long id = (Long) flightSchedule.getProperty("flightScheduleID").getValue(); // there should be one link to self (OData4j swallows this) // there should be one link to flights // there should be one link to one departureAirport for this flight schedule // there should be one link to one departureAirport for this flight schedule assertTrue(containsLink(flightSchedule.getLinks(), "FlightSchedules(" + id + ")/flights", "http://schemas.microsoft.com/ado/2007/08/dataservices/related/Flights")); assertTrue(containsLink(flightSchedule.getLinks(), FLIGHT_SCHEDULE_ENTITYSET_NAME + "(" + id + ")/departureAirport", "http://schemas.microsoft.com/ado/2007/08/dataservices/related/Airport")); assertTrue(containsLink(flightSchedule.getLinks(), FLIGHT_SCHEDULE_ENTITYSET_NAME + "(" + id + ")/arrivalAirport", "http://schemas.microsoft.com/ado/2007/08/dataservices/related/Airport")); assertEquals(3, flightSchedule.getLinks().size()); } } /** * GET item, check link to another entity */ @Test public void getFlightScheduleLinksToAirports() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); OEntity flightSchedule = consumer.getEntity(FLIGHT_SCHEDULE_ENTITYSET_NAME, 2).execute(); Long id = (Long) flightSchedule.getProperty("flightScheduleID").getValue(); assertEquals(2, id.intValue()); // there should be one link to self (OData4j swallows this) // there should be one link to flights // there should be one link to one departureAirport for this flight schedule // there should be one link to one arrivalAirport for this flight schedule assertTrue(containsLink(flightSchedule.getLinks(), FLIGHT_SCHEDULE_ENTITYSET_NAME + "(" + id + ")/departureAirport", "http://schemas.microsoft.com/ado/2007/08/dataservices/related/Airport")); assertTrue(containsLink(flightSchedule.getLinks(), FLIGHT_SCHEDULE_ENTITYSET_NAME + "(" + id + ")/arrivalAirport", "http://schemas.microsoft.com/ado/2007/08/dataservices/related/Airport")); assertEquals(3, flightSchedule.getLinks().size()); } /** * GET nav properties for an item */ @Test public void getFlightScheduleNavProperties() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); // now follow links to departure airport and arrival airport //do this only for strict odata OEntity departureAirport = consumer .getEntity(FLIGHT_SCHEDULE_ENTITYSET_NAME, 2055) .nav("departureAirport") .execute(); assertEquals("LTN", departureAirport.getProperty("code").getValue()); OEntity arrivalAirport = consumer .getEntity(FLIGHT_SCHEDULE_ENTITYSET_NAME, 2055) .nav("arrivalAirport") .execute(); assertEquals("GVA", arrivalAirport.getProperty("code").getValue()); } /** * GET collection, check link to self and other entities for each item */ @Test public void getAirportsLinksToAirport() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); Enumerable<OEntity> airports = consumer.getEntities(AIRPORT_ENTITYSET_NAME).execute(); assertEquals(6, airports.toSet().size()); for (OEntity airport : airports.toSet()) { String code = airport.getProperty("code").getValue().toString(); assertEquals(2, airport.getLinks().size()); // there should be one link to departures assertTrue(containsLink(airport.getLinks(), AIRPORT_ENTITYSET_NAME + "('" + code + "')/departures")); assertTrue(containsLink(airport.getLinks(), AIRPORT_ENTITYSET_NAME + "('" + code + "')/arrivals")); } } /** * GET item, check link to another entity */ @Test public void getAirportLinksToArrivalsDepartures() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); OEntity airport = consumer.getEntity(AIRPORT_ENTITYSET_NAME, "LTN").execute(); String code = airport.getProperty("code").getValue().toString(); assertEquals("LTN", code); assertEquals(2, airport.getLinks().size()); assertTrue(containsLink(airport.getLinks(), AIRPORT_ENTITYSET_NAME + "('" + code + "')/departures")); assertTrue(containsLink(airport.getLinks(), AIRPORT_ENTITYSET_NAME + "('" + code + "')/arrivals")); } /** * GET nav properties for an item */ @Test public void getAirportNavProperties() throws Exception { ODataConsumer consumer = ODataJerseyConsumer.newBuilder(baseUri).build(); // now follow links to departure airport and arrival airport OEntity departuresFlightSchedule = consumer .getEntity(AIRPORT_ENTITYSET_NAME, "LTN") .nav("departures") .execute(); assertEquals(2051L, departuresFlightSchedule.getProperty("flightScheduleID").getValue()); OEntity arrivalsFlightSchedule = consumer .getEntity(AIRPORT_ENTITYSET_NAME, "LTN") .nav("arrivals") .execute(); assertEquals(2052L, arrivalsFlightSchedule.getProperty("flightScheduleID").getValue()); } private boolean containsLink(List<OLink> links, String link) { return containsLink(links, link, null); } private boolean containsLink(List<OLink> links, String link, String relation) { assert(links != null); for (OLink l : links) { if (l.getHref().equals(link) && (relation == null || l.getRelation().equals(relation))) { return true; } } //Link not found => print debug info System.out.println("Links with rel [" + relation + "] and href [" + link + "] does not exist:"); for(OLink l : links) { System.out.println(" Link: rel [" + l.getRelation() + "], href [" + l.getHref() + "]"); } return false; } }