diff --git a/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Administrator.java b/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Administrator.java index e279bb1cdf2882a24a379324594e9692ece1cbc2..d3b1b3061005f26c4195d63558580b78e6146208 100644 --- a/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Administrator.java +++ b/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Administrator.java @@ -35,5 +35,6 @@ public class Administrator extends User implements Serializable { */ public Administrator(String login, String password) { super(login, password); + this.role = "ADMIN"; } } diff --git a/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Owner.java b/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Owner.java index d3645ec74cb4fc64716522f62788a3edf66ab23b..d6d116820686aeceda1cf35c3ef8b7ac1c5d567f 100644 --- a/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Owner.java +++ b/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/Owner.java @@ -53,6 +53,7 @@ public class Owner extends User implements Serializable { */ public Owner(String login, String password) { super(login, password); + this.role = "OWNER"; this.pets = new HashSet<>(); } diff --git a/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/User.java b/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/User.java index 289b34a044ccf1752f6d305c467c6222df60103d..b55c735024927ea3df017c950a0cfb8ffeae6202 100644 --- a/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/User.java +++ b/domain/src/main/java/es/uvigo/esei/xcs/domain/entities/User.java @@ -33,6 +33,9 @@ public abstract class User implements Serializable { @Column(length = 32, nullable = false) protected String password; + @Column(name="role", insertable = false, updatable = false) + protected String role; + User() {} /** @@ -78,6 +81,16 @@ public abstract class User implements Serializable { this.login = login; } + + /** + * Returns the role of the user. This value is automatically set by JPA, as + * it is the value used as discriminator in the inheritance. + * + * @return the role of the user. + */ + public String getRole() { + return role; + } /** * Returns the MD5 of the user's password. Capital letters are used diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/OwnerResource.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/OwnerResource.java index 8d15c3159c08b253879203086482bbf62efb6c08..7b08121a2ea5af0f99de2336771fc57669a76819 100644 --- a/rest/src/main/java/es/uvigo/esei/xcs/rest/OwnerResource.java +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/OwnerResource.java @@ -18,7 +18,8 @@ import javax.ws.rs.core.Response; import javax.ws.rs.core.UriInfo; import es.uvigo.esei.xcs.domain.entities.Owner; -import es.uvigo.esei.xcs.domain.entities.Pet; +import es.uvigo.esei.xcs.rest.entity.OwnerEditionData; +import es.uvigo.esei.xcs.rest.entity.OwnerCreationData; import es.uvigo.esei.xcs.service.OwnerService; /** @@ -74,19 +75,20 @@ public class OwnerResource { * Creates a new owner. This owner may include a list of pets, that will be * also created. * - * @param owner a new owner to be stored. + * @param ownerData a new owner to be stored. * @return a {@code CREATED} response with the URI of the new owner in the * {@code Location} header. * @throws IllegalArgumentException if owner is {@code null} or if an owner * with the same login already exists. */ @POST - public Response create(Owner owner) { - // Pets are serialized without owner. - assignOwnerToPets(owner); - + public Response create(OwnerCreationData ownerData) { + if (ownerData == null) { + throw new IllegalArgumentException("ownerData can't be null"); + } + try { - final Owner newOwner = this.service.create(owner); + final Owner newOwner = this.service.create(ownerData.toOwner()); final URI ownerUri = uriInfo.getAbsolutePathBuilder() .path(newOwner.getLogin()) .build(); @@ -101,15 +103,24 @@ public class OwnerResource { * Updates an owner. This owner may include a list of pets, that will be * also created or updated. If the owner does not exists it will be created. * - * @param owner an owner to be updated. + * @param ownerData an owner to be updated. * @return an empty {@code OK} response. * @throws IllegalArgumentException if owner is {@code null}. */ + @Path("{login}") @PUT - public Response update(Owner owner) { - // Pets are serialized without owner. - assignOwnerToPets(owner); - + public Response update(@PathParam("login") String login, OwnerEditionData ownerData) { + if (login == null) { + throw new IllegalArgumentException("login can't be null"); + } + if (ownerData == null) { + throw new IllegalArgumentException("ownerData can't be null"); + } + + final Owner owner = this.service.get(login); + + ownerData.assignData(owner); + this.service.update(owner); return Response.ok().build(); @@ -133,14 +144,4 @@ public class OwnerResource { return Response.ok().build(); } - - private static void assignOwnerToPets(Owner owner) { - if (owner == null) - throw new IllegalArgumentException("owner can't be null"); - - for (Pet pet : owner.getPets()) { - if (pet.getOwner() != owner) - pet.setOwner(owner); - } - } } diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/PetResource.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/PetResource.java index 9194ef226126ba391a8f18865b118da7c5671d50..a946b50236130da5972cfed6aeda720cb8f630d2 100644 --- a/rest/src/main/java/es/uvigo/esei/xcs/rest/PetResource.java +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/PetResource.java @@ -19,6 +19,7 @@ import javax.ws.rs.core.Response; import javax.ws.rs.core.UriInfo; import es.uvigo.esei.xcs.domain.entities.Pet; +import es.uvigo.esei.xcs.rest.entity.PetData; import es.uvigo.esei.xcs.service.PetService; /** @@ -73,7 +74,7 @@ public class PetResource { /** * Creates a new pet owned by the current user. * - * @param pet a new owner to be stored. + * @param petData a new owner to be stored. * @return a {@code CREATED} response with the URI of the new pet in the * {@code Location} header. * @throws IllegalArgumentException if pet is {@code null} or if a pet with @@ -83,14 +84,15 @@ public class PetResource { * thrown. */ @POST - public Response create(Pet pet) throws SecurityException { - if (pet == null) + public Response create(PetData petData) throws SecurityException { + if (petData == null) throw new IllegalArgumentException("pet can't be null"); try { - final Pet newPet = this.service.create(pet); + final Pet pet = this.service.create(petData.toPet()); + final URI petUri = uriInfo.getAbsolutePathBuilder() - .path(Integer.toString(newPet.getId())) + .path(Integer.toString(pet.getId())) .build(); return Response.created(petUri).build(); @@ -105,18 +107,23 @@ public class PetResource { * Updates the information of a pet. If the pet is not stored, it will be * created. * - * @param pet a pet to be updated. + * @param id the identifier of the pet to be modified. + * @param petData a pet to be updated. * @return an empty {@code OK} response. * @throws IllegalArgumentException if pet is {@code null} of it has no * owner. * @throws SecurityException if the pet's owner is not the current user. */ + @Path("{id}") @PUT - public Response update(Pet pet) throws SecurityException { - if (pet == null) + public Response update(@PathParam("id") int id, PetData petData) throws SecurityException { + if (petData == null) throw new IllegalArgumentException("pet can't be null"); try { + final Pet pet = this.service.get(id); + petData.assignData(pet); + this.service.update(pet); return Response.ok().build(); diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/UserResource.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/UserResource.java new file mode 100644 index 0000000000000000000000000000000000000000..35d0046ba8145b74d192eacca1e11a2a81723859 --- /dev/null +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/UserResource.java @@ -0,0 +1,31 @@ +package es.uvigo.esei.xcs.rest; + +import javax.ejb.EJB; +import javax.ejb.EJBAccessException; +import javax.ws.rs.GET; +import javax.ws.rs.Path; +import javax.ws.rs.Produces; +import javax.ws.rs.core.MediaType; +import javax.ws.rs.core.Response; + +import es.uvigo.esei.xcs.domain.entities.User; +import es.uvigo.esei.xcs.rest.entity.UserCredentials; +import es.uvigo.esei.xcs.service.UserService; + +@Path("user") +@Produces(MediaType.APPLICATION_JSON) +public class UserResource { + @EJB + private UserService service; + + @GET + public Response getCredentials() { + try { + final User currentUser = this.service.getCurrentUser(); + + return Response.ok(new UserCredentials(currentUser)).build(); + } catch (EJBAccessException eae) { + throw new SecurityException(eae); + } + } +} diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/OwnerCreationData.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/OwnerCreationData.java new file mode 100644 index 0000000000000000000000000000000000000000..2d35f46656fd3ca465380670c0ca9cee856fa9d3 --- /dev/null +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/OwnerCreationData.java @@ -0,0 +1,31 @@ +package es.uvigo.esei.xcs.rest.entity; + +import java.io.Serializable; + +import es.uvigo.esei.xcs.domain.entities.Owner; + +public class OwnerCreationData implements Serializable { + private static final long serialVersionUID = 1L; + + private String login; + private String password; + + OwnerCreationData() {} + + public OwnerCreationData(String login, String password) { + this.login = login; + this.password = password; + } + + public String getLogin() { + return login; + } + + public String getPassword() { + return password; + } + + public Owner toOwner() { + return new Owner(this.login, this.password); + } +} diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/OwnerEditionData.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/OwnerEditionData.java new file mode 100644 index 0000000000000000000000000000000000000000..867e2dc80f2820e01a376d1f747f1be3b4616629 --- /dev/null +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/OwnerEditionData.java @@ -0,0 +1,25 @@ +package es.uvigo.esei.xcs.rest.entity; + +import java.io.Serializable; + +import es.uvigo.esei.xcs.domain.entities.Owner; + +public class OwnerEditionData implements Serializable { + private static final long serialVersionUID = 1L; + private String password; + + OwnerEditionData() {} + + public OwnerEditionData(String password) { + this.password = password; + } + + public String getPassword() { + return password; + } + + public void assignData(Owner owner) { + owner.changePassword(this.password); + } + +} diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/PetData.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/PetData.java new file mode 100644 index 0000000000000000000000000000000000000000..f168e80311cb04876da7c6cb347640199ba17a98 --- /dev/null +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/PetData.java @@ -0,0 +1,48 @@ +package es.uvigo.esei.xcs.rest.entity; + +import java.io.Serializable; +import java.util.Date; + +import es.uvigo.esei.xcs.domain.entities.AnimalType; +import es.uvigo.esei.xcs.domain.entities.Pet; + +public class PetData implements Serializable { + private static final long serialVersionUID = 1L; + + private String name; + private AnimalType animal; + private Date birth; + + PetData() {} + + public PetData(String name, AnimalType animal, Date birth) { + this.name = name; + this.animal = animal; + this.birth = birth; + } + + public String getName() { + return name; + } + + public AnimalType getAnimal() { + return animal; + } + + public Date getBirth() { + return birth; + } + + public Pet assignData(Pet pet) { + pet.setName(this.name); + pet.setAnimal(this.animal); + pet.setBirth(this.birth); + + return pet; + } + + public Pet toPet() { + return new Pet(this.name, this.animal, this.birth); + } + +} diff --git a/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/UserCredentials.java b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/UserCredentials.java new file mode 100644 index 0000000000000000000000000000000000000000..3a89ab147f19742622f3a18d46d8509366eb49ae --- /dev/null +++ b/rest/src/main/java/es/uvigo/esei/xcs/rest/entity/UserCredentials.java @@ -0,0 +1,26 @@ +package es.uvigo.esei.xcs.rest.entity; + +import java.io.Serializable; + +import es.uvigo.esei.xcs.domain.entities.User; + +public class UserCredentials implements Serializable { + private static final long serialVersionUID = 1L; + + private String login; + private String role; + + public UserCredentials(User user) { + this.login = user.getLogin(); + this.role = user.getRole(); + } + + public String getLogin() { + return login; + } + + public String getRole() { + return role; + } + +} diff --git a/rest/src/main/webapp/WEB-INF/web.xml b/rest/src/main/webapp/WEB-INF/web.xml index f8bf7f36d650eb9a181f2539fc7db84712c9ecaf..e36c67f7bd7b9fa222066ceed5cca9abdadfd1d0 100644 --- a/rest/src/main/webapp/WEB-INF/web.xml +++ b/rest/src/main/webapp/WEB-INF/web.xml @@ -10,6 +10,18 @@ + + + user + /api/user/* + OPTIONS + + + ADMIN + OWNER + + + admin diff --git a/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceRestTest.java b/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceRestTest.java index dbc2deefc375c4bf61adab6bf1072da1ebfa5429..1c77e70de8826e68599ab68724de95165be37ed7 100644 --- a/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceRestTest.java +++ b/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceRestTest.java @@ -7,8 +7,8 @@ import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.NON_EXISTENT_LOGIN import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.OWNER_WITHOUT_PETS_LOGIN; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.OWNER_WITH_PETS_LOGIN; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentOwner; -import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerWithFreshPets; -import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerWithPersistentPets; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerLogin; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerPassword; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerWithoutPets; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newPasswordForExistentOwner; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.owners; @@ -23,7 +23,6 @@ import static org.junit.Assert.assertThat; import java.util.List; import javax.ws.rs.client.ClientBuilder; -import javax.ws.rs.client.WebTarget; import javax.ws.rs.core.MediaType; import javax.ws.rs.core.Response; @@ -48,261 +47,272 @@ import org.junit.runner.RunWith; import es.uvigo.esei.xcs.domain.entities.Owner; import es.uvigo.esei.xcs.rest.GenericTypes.ListOwnerType; +import es.uvigo.esei.xcs.rest.entity.OwnerCreationData; +import es.uvigo.esei.xcs.rest.entity.OwnerEditionData; import es.uvigo.esei.xcs.service.OwnerService; @RunWith(Arquillian.class) public class OwnerResourceRestTest { - private final static String BASE_PATH = "api/owner/"; - private static final String BASIC_AUTHORIZATION = "Basic am9zZTpqb3NlcGFzcw="; - - @Deployment - public static Archive createDeployment() { - return ShrinkWrap.create(WebArchive.class, "test.war") - .addClass(OwnerResource.class) - .addClasses(CORSFilter.class, IllegalArgumentExceptionMapper.class, SecurityExceptionMapper.class) - .addPackage(OwnerService.class.getPackage()) - .addPackage(Owner.class.getPackage()) - .addAsResource("test-persistence.xml", "META-INF/persistence.xml") - .addAsWebInfResource("jboss-web.xml") - .addAsWebInfResource("web.xml") - .addAsResource("arquillian.extension.persistence.properties") - .addAsResource("arquillian.extension.persistence.dbunit.properties") - .addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml"); - } - - @Test @InSequence(1) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeGet() {} - - @Test @InSequence(2) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testGet( - @ArquillianResteasyResource(BASE_PATH + EXISTENT_LOGIN) ResteasyWebTarget webTarget - ) throws Exception { - final Response response = webTarget.request().get(); - - assertThat(response, hasOkStatus()); - - final Owner owner = response.readEntity(Owner.class); - final Owner expected = existentOwner(); - - assertThat(owner, is(equalToOwner(expected))); - } - - @Test @InSequence(3) - @ShouldMatchDataSet("owners.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterGet() {} - - - - @Test @InSequence(4) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeGetNonExistent() {} - - @Test @InSequence(5) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testGetNonExistent( - @ArquillianResteasyResource(BASE_PATH + NON_EXISTENT_LOGIN) ResteasyWebTarget webTarget - ) throws Exception { - final Response response = webTarget.request().get(); - - assertThat(response, hasBadRequestStatus()); - } - - @Test @InSequence(6) - @ShouldMatchDataSet("owners.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterGetNonExistent() {} - - - - @Test @InSequence(10) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeList() {} - - @Test @InSequence(11) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testList( - @ArquillianResteasyResource(BASE_PATH) ResteasyWebTarget webTarget - ) throws Exception { - final Response response = webTarget.request().get(); - - assertThat(response, hasOkStatus()); - - final List list = ListOwnerType.readEntity(response); - assertThat(list, containsOwnersInAnyOrder(owners())); - } - - @Test @InSequence(12) - @ShouldMatchDataSet("owners.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterList() {} - - - - @Test @InSequence(20) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeCreate() {} - - @Test @InSequence(21) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testCreate( - @ArquillianResteasyResource(BASE_PATH) ResteasyWebTarget webTarget - ) throws Exception { - testCreateOwner(webTarget, newOwnerWithoutPets()); - } - - @Test @InSequence(22) - @ShouldMatchDataSet({"owners.xml", "owners-create-without-pets.xml"}) - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterCreate() {} - - - - @Test @InSequence(23) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeCreateWithPets() {} - - @Test @InSequence(24) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testCreateWithPets( - @ArquillianResteasyResource(BASE_PATH) ResteasyWebTarget webTarget - ) throws Exception { - testCreateOwner(webTarget, newOwnerWithFreshPets(), newOwnerWithPersistentPets()); - } - - @Test @InSequence(25) - @ShouldMatchDataSet({"owners.xml", "owners-create-with-pets.xml"}) - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterCreateWithPets() {} - - - private void testCreateOwner(WebTarget webTarget, Owner newOwner) { - testCreateOwner(webTarget, newOwner, newOwner); - } - - private void testCreateOwner(WebTarget webTarget, Owner newOwner, Owner persistentOwner) { - final Response response = webTarget.request().post(json(newOwner)); - - assertThat(response, hasCreatedStatus()); - - final String location = response.getHeaderString("Location"); - - final Response responseGet = authorizedJsonRequestGet(location); - final Owner owner = responseGet.readEntity(Owner.class); - assertThat(owner, is(equalToOwner(persistentOwner))); - } - - - @Test @InSequence(30) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeUpdatePassword() {} - - @Test @InSequence(31) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testUpdatePassword( - @ArquillianResteasyResource(BASE_PATH) ResteasyWebTarget webTarget - ) throws Exception { - final Owner owner = existentOwner(); - owner.changePassword(newPasswordForExistentOwner()); - - final Response response = webTarget.request().put(json(owner)); - - assertThat(response, hasOkStatus()); - } - - @Test @InSequence(32) - @ShouldMatchDataSet("owners-update-password.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterUpdatePassword() {} - - - - @Test @InSequence(40) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeDeleteWithoutPets() {} - - @Test @InSequence(41) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testDeleteWithoutPets( - @ArquillianResteasyResource(BASE_PATH + OWNER_WITHOUT_PETS_LOGIN) ResteasyWebTarget webTarget - ) throws Exception { - final Response response = webTarget.request().delete(); - - assertThat(response, hasOkStatus()); - } - - @Test @InSequence(42) - @ShouldMatchDataSet("owners-remove-without-pets.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterDeleteWithoutPets() {} - - - - @Test @InSequence(43) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeDeleteWithPets() {} - - @Test @InSequence(44) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testDeleteWithPets( - @ArquillianResteasyResource(BASE_PATH + OWNER_WITH_PETS_LOGIN) ResteasyWebTarget webTarget - ) throws Exception { - final Response response = webTarget.request().delete(); - - assertThat(response, hasOkStatus()); - } - - @Test @InSequence(45) - @ShouldMatchDataSet("owners-remove-with-pets.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterDeleteWithPets() {} - - - - @Test @InSequence(46) - @UsingDataSet("owners.xml") - @Cleanup(phase = TestExecutionPhase.NONE) - public void beforeDeleteNoLogin() {} - - @Test @InSequence(47) - @RunAsClient - @Header(name = "Authorization", value = BASIC_AUTHORIZATION) - public void testDeleteNoLogin( - @ArquillianResteasyResource(BASE_PATH) ResteasyWebTarget webTarget - ) throws Exception { - final Response response = webTarget.request().delete(); - - assertThat(response, hasMethodNotAllowedStatus()); - } - - @Test @InSequence(48) - @ShouldMatchDataSet("owners.xml") - @CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) - public void afterDeleteNoLogin() {} - - - private static Response authorizedJsonRequestGet(String uri) { - return ClientBuilder.newClient().target(uri) - .request(MediaType.APPLICATION_JSON_TYPE) - .header("Authorization", BASIC_AUTHORIZATION) - .get(); - } + private final static String BASE_PATH = "api/owner/"; + private static final String BASIC_AUTHORIZATION = "Basic am9zZTpqb3NlcGFzcw="; + + @Deployment + public static Archive createDeployment() { + return ShrinkWrap.create(WebArchive.class, "test.war") + .addClass(OwnerResource.class) + .addClasses(OwnerCreationData.class, OwnerEditionData.class) + .addClasses(CORSFilter.class, IllegalArgumentExceptionMapper.class, SecurityExceptionMapper.class) + .addPackage(OwnerService.class.getPackage()) + .addPackage(Owner.class.getPackage()) + .addAsResource("test-persistence.xml", "META-INF/persistence.xml") + .addAsWebInfResource("jboss-web.xml") + .addAsWebInfResource("web.xml") + .addAsResource("arquillian.extension.persistence.properties") + .addAsResource("arquillian.extension.persistence.dbunit.properties") + .addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml"); + } + + @Test + @InSequence(1) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeGet() {} + + @Test + @InSequence(2) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testGet( + @ArquillianResteasyResource(BASE_PATH + EXISTENT_LOGIN) + ResteasyWebTarget webTarget + ) throws Exception { + final Response response = webTarget.request().get(); + + assertThat(response, hasOkStatus()); + + final Owner owner = response.readEntity(Owner.class); + final Owner expected = existentOwner(); + + assertThat(owner, is(equalToOwner(expected))); + } + + @Test + @InSequence(3) + @ShouldMatchDataSet("owners.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterGet() {} + + @Test + @InSequence(4) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeGetNonExistent() {} + + @Test + @InSequence(5) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testGetNonExistent( + @ArquillianResteasyResource(BASE_PATH + NON_EXISTENT_LOGIN) + ResteasyWebTarget webTarget + ) throws Exception { + final Response response = webTarget.request().get(); + + assertThat(response, hasBadRequestStatus()); + } + + @Test + @InSequence(6) + @ShouldMatchDataSet("owners.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterGetNonExistent() {} + + @Test + @InSequence(10) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeList() {} + + @Test + @InSequence(11) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testList( + @ArquillianResteasyResource(BASE_PATH) + ResteasyWebTarget webTarget + ) throws Exception { + final Response response = webTarget.request().get(); + + assertThat(response, hasOkStatus()); + + final List list = ListOwnerType.readEntity(response); + assertThat(list, containsOwnersInAnyOrder(owners())); + } + + @Test + @InSequence(12) + @ShouldMatchDataSet("owners.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterList() {} + + @Test + @InSequence(20) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeCreate() {} + + @Test + @InSequence(21) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testCreate( + @ArquillianResteasyResource(BASE_PATH) + ResteasyWebTarget webTarget + ) throws Exception { + final Owner newOwner = newOwnerWithoutPets(); + final OwnerCreationData ownerData = new OwnerCreationData(newOwnerLogin(), newOwnerPassword()); + + final Response response = webTarget.request().post(json(ownerData)); + + assertThat(response, hasCreatedStatus()); + + final String location = response.getHeaderString("Location"); + + final Response responseGet = authorizedJsonRequestGet(location); + final Owner owner = responseGet.readEntity(Owner.class); + assertThat(owner, is(equalToOwner(newOwner))); + } + + @Test + @InSequence(22) + @ShouldMatchDataSet({ + "owners.xml", "owners-create-without-pets.xml" + }) + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterCreate() {} + + @Test + @InSequence(30) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeUpdatePassword() {} + + @Test + @InSequence(31) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testUpdatePassword( + @ArquillianResteasyResource(BASE_PATH + EXISTENT_LOGIN) + ResteasyWebTarget webTarget + ) throws Exception { + final OwnerEditionData ownerData = new OwnerEditionData(newPasswordForExistentOwner()); + + final Response response = webTarget.request().put(json(ownerData)); + + assertThat(response, hasOkStatus()); + } + + @Test + @InSequence(32) + @ShouldMatchDataSet("owners-update-password.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterUpdatePassword() {} + + @Test + @InSequence(40) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeDeleteWithoutPets() {} + + @Test + @InSequence(41) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testDeleteWithoutPets( + @ArquillianResteasyResource(BASE_PATH + OWNER_WITHOUT_PETS_LOGIN) + ResteasyWebTarget webTarget + ) throws Exception { + final Response response = webTarget.request().delete(); + + assertThat(response, hasOkStatus()); + } + + @Test + @InSequence(42) + @ShouldMatchDataSet("owners-remove-without-pets.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterDeleteWithoutPets() {} + + @Test + @InSequence(43) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeDeleteWithPets() {} + + @Test + @InSequence(44) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testDeleteWithPets( + @ArquillianResteasyResource(BASE_PATH + OWNER_WITH_PETS_LOGIN) + ResteasyWebTarget webTarget + ) throws Exception { + final Response response = webTarget.request().delete(); + + assertThat(response, hasOkStatus()); + } + + @Test + @InSequence(45) + @ShouldMatchDataSet("owners-remove-with-pets.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterDeleteWithPets() {} + + @Test + @InSequence(46) + @UsingDataSet("owners.xml") + @Cleanup(phase = TestExecutionPhase.NONE) + public void beforeDeleteNoLogin() {} + + @Test + @InSequence(47) + @RunAsClient + @Header(name = "Authorization", value = BASIC_AUTHORIZATION) + public void testDeleteNoLogin( + @ArquillianResteasyResource(BASE_PATH) + ResteasyWebTarget webTarget + ) throws Exception { + final Response response = webTarget.request().delete(); + + assertThat(response, hasMethodNotAllowedStatus()); + } + + @Test + @InSequence(48) + @ShouldMatchDataSet("owners.xml") + @CleanupUsingScript({ + "cleanup.sql", "cleanup-autoincrement.sql" + }) + public void afterDeleteNoLogin() {} + + private static Response authorizedJsonRequestGet(String uri) { + return ClientBuilder.newClient().target(uri) + .request(MediaType.APPLICATION_JSON_TYPE) + .header("Authorization", BASIC_AUTHORIZATION) + .get(); + } } diff --git a/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceUnitTest.java b/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceUnitTest.java index abfce26520f47e94cbda37406215d1d8f1605bd8..446d177da044829e1faa4611b1a17a225fcf9af6 100644 --- a/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceUnitTest.java +++ b/rest/src/test/java/es/uvigo/esei/xcs/rest/OwnerResourceUnitTest.java @@ -3,17 +3,19 @@ package es.uvigo.esei.xcs.rest; import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.containsOwnersInAnyOrder; import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.equalToOwner; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.anyLogin; -import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.anyOwner; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentLogin; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentOwner; -import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerWithFreshPets; -import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerWithPersistentPets; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentPassword; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerLogin; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerPassword; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newPasswordForExistentOwner; import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.owners; import static es.uvigo.esei.xcs.http.util.HasHttpStatus.hasCreatedStatus; import static es.uvigo.esei.xcs.http.util.HasHttpStatus.hasOkStatus; import static java.util.Arrays.asList; import static java.util.Collections.emptyList; +import static org.easymock.EasyMock.anyObject; import static org.easymock.EasyMock.expect; -import static org.easymock.EasyMock.expectLastCall; import static org.hamcrest.CoreMatchers.equalTo; import static org.hamcrest.CoreMatchers.instanceOf; import static org.hamcrest.CoreMatchers.is; @@ -38,177 +40,185 @@ import org.junit.runner.RunWith; import es.uvigo.esei.xcs.domain.entities.Owner; import es.uvigo.esei.xcs.domain.entities.OwnersDataset; +import es.uvigo.esei.xcs.rest.entity.OwnerCreationData; +import es.uvigo.esei.xcs.rest.entity.OwnerEditionData; import es.uvigo.esei.xcs.service.OwnerService; @RunWith(EasyMockRunner.class) public class OwnerResourceUnitTest extends EasyMockSupport { - @TestSubject - private OwnerResource resource = new OwnerResource(); - - @Mock - private OwnerService facade; - - @Mock - private UriInfo uriInfo; - - @Mock - private UriBuilder uriBuilder; - - @After - public void tearDown() throws Exception { - verifyAll(); - } - - @Test - public void testGet() { - final Owner owner = OwnersDataset.anyOwner(); - - expect(facade.get(owner.getLogin())) - .andReturn(owner); - - replayAll(); - - final Response response = resource.get(owner.getLogin()); - - assertThat(response, hasOkStatus()); - assertThat(response.getEntity(), is(instanceOf(Owner.class))); - assertThat((Owner) response.getEntity(), is(equalToOwner(owner))); - } - - @Test(expected = IllegalArgumentException.class) - public void testGetNull() { - replayAll(); - - resource.get(null); - } - - @Test(expected = IllegalArgumentException.class) - public void testGetMissing() { - final String login = anyLogin(); - - expect(facade.get(login)) - .andReturn(null); - - replayAll(); - - resource.get(login); - } - - @Test - @SuppressWarnings("unchecked") - public void testList() { - final Owner[] owners = owners(); - - expect(facade.list()) - .andReturn(asList(owners)); - - replayAll(); - - final Response response = resource.list(); - - assertThat(response, hasOkStatus()); - assertThat(response.getEntity(), is(instanceOf(List.class))); - assertThat((List) response.getEntity(), containsOwnersInAnyOrder(owners)); - } - - @Test - @SuppressWarnings("unchecked") - public void testListEmpty() { - expect(facade.list()) - .andReturn(emptyList()); - - replayAll(); - - final Response response = resource.list(); - - assertThat(response, hasOkStatus()); - assertThat(response.getEntity(), is(instanceOf(List.class))); - assertThat((List) response.getEntity(), is(empty())); - } - - @Test - public void testCreate() throws Exception { - final Owner newOwner = newOwnerWithFreshPets(); - final Owner createdOwner = newOwnerWithPersistentPets(); - - final URI mockUri = new URI("http://host/api/owner/" + newOwner.getLogin()); - - expect(facade.create(newOwner)) - .andReturn(createdOwner); - - expect(uriInfo.getAbsolutePathBuilder()) - .andReturn(uriBuilder); - expect(uriBuilder.path(newOwner.getLogin())) - .andReturn(uriBuilder); - expect(uriBuilder.build()) - .andReturn(mockUri); - - replayAll(); - - final Response response = resource.create(newOwner); - - assertThat(response, hasCreatedStatus()); - assertThat(response.getHeaderString("Location"), is(equalTo(mockUri.toString()))); - } - - @Test(expected = IllegalArgumentException.class) - public void testCreateNull() { - replayAll(); - - resource.create(null); - } - - @Test(expected = IllegalArgumentException.class) - public void testCreateExistentOwner() { - final Owner existentOwner = existentOwner(); - - expect(facade.create(existentOwner)) - .andThrow(new EntityExistsException()); - - replayAll(); - - resource.create(existentOwner); - } - - @Test - public void testUpdate() { - final Owner owner = anyOwner(); - - facade.update(owner); - - expectLastCall().andReturn(owner); - - replayAll(); - - final Response response = resource.update(owner); - - assertThat(response, hasOkStatus()); - } - - @Test(expected = IllegalArgumentException.class) - public void testUpdateNull() { - replayAll(); - - resource.update(null); - } - - @Test - public void testDelete() { - final String login = anyLogin(); - - facade.remove(login); - - replayAll(); - - final Response response = resource.delete(login); - - assertThat(response, hasOkStatus()); - } - - @Test(expected = IllegalArgumentException.class) - public void testDeleteNull() { - replayAll(); - - resource.delete(null); - } + @TestSubject + private OwnerResource resource = new OwnerResource(); + + @Mock + private OwnerService facade; + + @Mock + private UriInfo uriInfo; + + @Mock + private UriBuilder uriBuilder; + + @After + public void tearDown() throws Exception { + verifyAll(); + } + + @Test + public void testGet() { + final Owner owner = OwnersDataset.anyOwner(); + + expect(facade.get(owner.getLogin())) + .andReturn(owner); + + replayAll(); + + final Response response = resource.get(owner.getLogin()); + + assertThat(response, hasOkStatus()); + assertThat(response.getEntity(), is(instanceOf(Owner.class))); + assertThat((Owner) response.getEntity(), is(equalToOwner(owner))); + } + + @Test(expected = IllegalArgumentException.class) + public void testGetNull() { + replayAll(); + + resource.get(null); + } + + @Test(expected = IllegalArgumentException.class) + public void testGetMissing() { + final String login = anyLogin(); + + expect(facade.get(login)) + .andReturn(null); + + replayAll(); + + resource.get(login); + } + + @Test + @SuppressWarnings("unchecked") + public void testList() { + final Owner[] owners = owners(); + + expect(facade.list()) + .andReturn(asList(owners)); + + replayAll(); + + final Response response = resource.list(); + + assertThat(response, hasOkStatus()); + assertThat(response.getEntity(), is(instanceOf(List.class))); + assertThat((List) response.getEntity(), containsOwnersInAnyOrder(owners)); + } + + @Test + @SuppressWarnings("unchecked") + public void testListEmpty() { + expect(facade.list()) + .andReturn(emptyList()); + + replayAll(); + + final Response response = resource.list(); + + assertThat(response, hasOkStatus()); + assertThat(response.getEntity(), is(instanceOf(List.class))); + assertThat((List) response.getEntity(), is(empty())); + } + + @Test + public void testCreate() throws Exception { + final OwnerCreationData newOwner = new OwnerCreationData(newOwnerLogin(), newOwnerPassword()); + final Owner createdOwner = OwnersDataset.newOwnerWithoutPets(); + + final URI mockUri = new URI("http://host/api/owner/" + newOwner.getLogin()); + + expect(facade.create(anyObject(Owner.class))) + .andReturn(createdOwner); + + expect(uriInfo.getAbsolutePathBuilder()) + .andReturn(uriBuilder); + expect(uriBuilder.path(newOwner.getLogin())) + .andReturn(uriBuilder); + expect(uriBuilder.build()) + .andReturn(mockUri); + + replayAll(); + + final Response response = resource.create(newOwner); + + assertThat(response, hasCreatedStatus()); + assertThat(response.getHeaderString("Location"), is(equalTo(mockUri.toString()))); + } + + @Test(expected = IllegalArgumentException.class) + public void testCreateNull() { + replayAll(); + + resource.create(null); + } + + @Test(expected = IllegalArgumentException.class) + public void testCreateExistentOwner() { + final OwnerCreationData existentOwner = new OwnerCreationData(existentLogin(), existentPassword()); + + expect(facade.create(anyObject(Owner.class))) + .andThrow(new EntityExistsException()); + + replayAll(); + + resource.create(existentOwner); + } + + @Test + public void testUpdate() { + final Owner owner = existentOwner(); + final Owner ownerWithChangedPassword = existentOwner(); + ownerWithChangedPassword.changePassword(newPasswordForExistentOwner()); + + final OwnerEditionData ownerData = new OwnerEditionData(newPasswordForExistentOwner()); + + expect(facade.get(owner.getLogin())) + .andReturn(owner); + + expect(facade.update(anyObject(Owner.class))) + .andReturn(owner); + + replayAll(); + + final Response response = resource.update(owner.getLogin(), ownerData); + + assertThat(response, hasOkStatus()); + } + + @Test(expected = IllegalArgumentException.class) + public void testUpdateNull() { + replayAll(); + + resource.update(null, null); + } + + @Test + public void testDelete() { + final String login = anyLogin(); + + facade.remove(login); + + replayAll(); + + final Response response = resource.delete(login); + + assertThat(response, hasOkStatus()); + } + + @Test(expected = IllegalArgumentException.class) + public void testDeleteNull() { + replayAll(); + + resource.delete(null); + } } diff --git a/service/src/main/java/es/uvigo/esei/xcs/service/UserService.java b/service/src/main/java/es/uvigo/esei/xcs/service/UserService.java new file mode 100644 index 0000000000000000000000000000000000000000..d65592a425329bd5b60ab08a9126f498b9a3e188 --- /dev/null +++ b/service/src/main/java/es/uvigo/esei/xcs/service/UserService.java @@ -0,0 +1,30 @@ +package es.uvigo.esei.xcs.service; + +import java.security.Principal; + +import javax.annotation.security.RolesAllowed; +import javax.ejb.Stateless; +import javax.inject.Inject; +import javax.persistence.EntityManager; +import javax.persistence.PersistenceContext; + +import es.uvigo.esei.xcs.domain.entities.User; + +@Stateless +@RolesAllowed({"OWNER", "ADMIN"}) +public class UserService { + @PersistenceContext + private EntityManager em; + + @Inject + private Principal principal; + + /** + * Returns the current user entity. + * + * @return the entity with the information of the current user. + */ + public User getCurrentUser() { + return this.em.find(User.class, this.principal.getName()); + } +} diff --git a/service/src/test/java/es/uvigo/esei/xcs/service/PetServiceIntegrationTest.java b/service/src/test/java/es/uvigo/esei/xcs/service/PetServiceIntegrationTest.java index d1ba538550a184d3822983f94eaf03e7a0b054b0..45707e87799e2a6ddbceafc8f311a662abf49720 100644 --- a/service/src/test/java/es/uvigo/esei/xcs/service/PetServiceIntegrationTest.java +++ b/service/src/test/java/es/uvigo/esei/xcs/service/PetServiceIntegrationTest.java @@ -63,8 +63,8 @@ public class PetServiceIntegrationTest { .addPackage(Pet.class.getPackage()) .addAsResource("test-persistence.xml", "META-INF/persistence.xml") .addAsWebInfResource("jboss-web.xml") - .addAsResource("arquillian.extension.persistence.properties") - .addAsResource("arquillian.extension.persistence.dbunit.properties") + .addAsResource("arquillian.extension.persistence.properties") + .addAsResource("arquillian.extension.persistence.dbunit.properties") .addAsWebInfResource("beans.xml", "beans.xml"); } diff --git a/service/src/test/java/es/uvigo/esei/xcs/service/ServiceIntegrationTestSuite.java b/service/src/test/java/es/uvigo/esei/xcs/service/ServiceIntegrationTestSuite.java index fe0cb61d0beec0a08234e2c4e136d34456b505ce..d1ef4dd64806841363a1b88ee42ed63c49a8bf67 100644 --- a/service/src/test/java/es/uvigo/esei/xcs/service/ServiceIntegrationTestSuite.java +++ b/service/src/test/java/es/uvigo/esei/xcs/service/ServiceIntegrationTestSuite.java @@ -9,7 +9,9 @@ import org.junit.runners.Suite.SuiteClasses; OwnerServiceIntegrationTest.class, OwnerServiceIllegalAccessIntegrationTest.class, PetServiceIntegrationTest.class, - PetServiceIllegalAccessIntegrationTest.class + PetServiceIllegalAccessIntegrationTest.class, + UserServiceIntegrationTest.class, + UserServiceIllegalAccessIntegrationTest.class }) public class ServiceIntegrationTestSuite { } diff --git a/service/src/test/java/es/uvigo/esei/xcs/service/UserServiceIllegalAccessIntegrationTest.java b/service/src/test/java/es/uvigo/esei/xcs/service/UserServiceIllegalAccessIntegrationTest.java new file mode 100644 index 0000000000000000000000000000000000000000..83bec3d0b67fc5a7cd1728e1371714b75bfbfb44 --- /dev/null +++ b/service/src/test/java/es/uvigo/esei/xcs/service/UserServiceIllegalAccessIntegrationTest.java @@ -0,0 +1,85 @@ +package es.uvigo.esei.xcs.service; + +import static es.uvigo.esei.xcs.domain.entities.IsEqualToUser.equalToUser; +import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentOwner; +import static es.uvigo.esei.xcs.domain.entities.UsersDataset.existentAdmin; +import static org.hamcrest.CoreMatchers.is; +import static org.junit.Assert.assertThat; + +import javax.ejb.EJB; +import javax.inject.Inject; + +import org.jboss.arquillian.container.test.api.Deployment; +import org.jboss.arquillian.junit.Arquillian; +import org.jboss.arquillian.persistence.CleanupUsingScript; +import org.jboss.arquillian.persistence.ShouldMatchDataSet; +import org.jboss.arquillian.persistence.UsingDataSet; +import org.jboss.shrinkwrap.api.Archive; +import org.jboss.shrinkwrap.api.ShrinkWrap; +import org.jboss.shrinkwrap.api.spec.WebArchive; +import org.junit.Test; +import org.junit.runner.RunWith; + +import es.uvigo.esei.xcs.domain.entities.Owner; +import es.uvigo.esei.xcs.domain.entities.OwnersDataset; +import es.uvigo.esei.xcs.domain.entities.Pet; +import es.uvigo.esei.xcs.domain.entities.User; +import es.uvigo.esei.xcs.domain.entities.UsersDataset; +import es.uvigo.esei.xcs.service.util.security.RoleCaller; +import es.uvigo.esei.xcs.service.util.security.TestPrincipal; + +@RunWith(Arquillian.class) +@UsingDataSet("owners.xml") +@CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) +public class UserServiceIllegalAccessIntegrationTest { + + @Inject + private UserService facade; + + @EJB(beanName = "owner-caller") + private RoleCaller asOwner; + + @EJB(beanName = "admin-caller") + private RoleCaller asAdmin; + + @Inject + private TestPrincipal principal; + + @Deployment + public static Archive createDeployment() { + return ShrinkWrap.create(WebArchive.class, "test.war") + .addClasses(UserService.class) + .addPackage(RoleCaller.class.getPackage()) + .addPackage(Pet.class.getPackage()) + .addAsResource("test-persistence.xml", "META-INF/persistence.xml") + .addAsWebInfResource("jboss-web.xml") + .addAsResource("arquillian.extension.persistence.properties") + .addAsResource("arquillian.extension.persistence.dbunit.properties") + .addAsWebInfResource("beans.xml", "beans.xml"); + } + + @Test + @ShouldMatchDataSet("owners.xml") + public void testGetOwnerCredentials() { + final Owner existentOwner = existentOwner(); + + principal.setName(existentOwner.getLogin()); + + final User actualUser = asOwner.call(() -> facade.getCurrentUser()); + + assertThat(actualUser, is(equalToUser(existentOwner))); + } + + @Test + @ShouldMatchDataSet("owners.xml") + public void testGetAdminCredentials() { + final User existentAdmin = existentAdmin(); + + principal.setName(existentAdmin.getLogin()); + + final User actualUser = asAdmin.call(() -> facade.getCurrentUser()); + + assertThat(actualUser, is(equalToUser(existentAdmin))); + } + +} diff --git a/service/src/test/java/es/uvigo/esei/xcs/service/UserServiceIntegrationTest.java b/service/src/test/java/es/uvigo/esei/xcs/service/UserServiceIntegrationTest.java new file mode 100644 index 0000000000000000000000000000000000000000..3db9c9c660b4cdc352677b5b5b1f62513d26444b --- /dev/null +++ b/service/src/test/java/es/uvigo/esei/xcs/service/UserServiceIntegrationTest.java @@ -0,0 +1,46 @@ +package es.uvigo.esei.xcs.service; + +import javax.ejb.EJBAccessException; +import javax.inject.Inject; + +import org.jboss.arquillian.container.test.api.Deployment; +import org.jboss.arquillian.junit.Arquillian; +import org.jboss.arquillian.persistence.CleanupUsingScript; +import org.jboss.arquillian.persistence.ShouldMatchDataSet; +import org.jboss.arquillian.persistence.UsingDataSet; +import org.jboss.shrinkwrap.api.Archive; +import org.jboss.shrinkwrap.api.ShrinkWrap; +import org.jboss.shrinkwrap.api.spec.WebArchive; +import org.junit.Test; +import org.junit.runner.RunWith; + +import es.uvigo.esei.xcs.domain.entities.Pet; +import es.uvigo.esei.xcs.service.util.security.RoleCaller; + +@RunWith(Arquillian.class) +@UsingDataSet("owners.xml") +@CleanupUsingScript({ "cleanup.sql", "cleanup-autoincrement.sql" }) +public class UserServiceIntegrationTest { + + @Inject + private UserService facade; + + @Deployment + public static Archive createDeployment() { + return ShrinkWrap.create(WebArchive.class, "test.war") + .addClasses(UserService.class) + .addPackage(RoleCaller.class.getPackage()) + .addPackage(Pet.class.getPackage()) + .addAsResource("test-persistence.xml", "META-INF/persistence.xml") + .addAsWebInfResource("jboss-web.xml") + .addAsResource("arquillian.extension.persistence.properties") + .addAsResource("arquillian.extension.persistence.dbunit.properties") + .addAsWebInfResource("beans.xml", "beans.xml"); + } + + @Test(expected = EJBAccessException.class) + @ShouldMatchDataSet("owners.xml") + public void testGetCredentialsNoUser() { + facade.getCurrentUser(); + } +} diff --git a/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/IsEqualToUser.java b/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/IsEqualToUser.java new file mode 100644 index 0000000000000000000000000000000000000000..7359d22ef1361c46479aa3bdadd89105fac90dda --- /dev/null +++ b/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/IsEqualToUser.java @@ -0,0 +1,38 @@ +package es.uvigo.esei.xcs.domain.entities; + +import org.hamcrest.Factory; +import org.hamcrest.Matcher; + +public class IsEqualToUser extends IsEqualToEntity { + public IsEqualToUser(User user) { + super(user); + } + + @Override + protected boolean matchesSafely(User actual) { + this.clearDescribeTo(); + + if (actual == null) { + this.addTemplatedDescription("actual", expected.toString()); + return false; + } else { + return checkAttribute("login", User::getLogin, actual) + && checkAttribute("role", User::getRole, actual); + } + } + + @Factory + public static IsEqualToUser equalToUser(User user) { + return new IsEqualToUser(user); + } + + @Factory + public static Matcher> containsUsersInAnyOrder(User ... users) { + return containsEntityInAnyOrder(IsEqualToUser::equalToUser, users); + } + + @Factory + public static Matcher> containsUsersInAnyOrder(Iterable users) { + return containsEntityInAnyOrder(IsEqualToUser::equalToUser, users); + } +} diff --git a/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/OwnersDataset.java b/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/OwnersDataset.java index 337b250f17695727ae206671625cc046fcf76aed..560074e9a4bcba3506bc34a40b4d5f17cd336a9b 100644 --- a/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/OwnersDataset.java +++ b/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/OwnersDataset.java @@ -34,9 +34,9 @@ public class OwnersDataset { public static Owner[] owners() { return new Owner[] { - new Owner(EXISTENT_LOGIN, "pepepass", + new Owner(EXISTENT_LOGIN, EXISTENT_LOGIN + "pass", new Pet(1, "Pepecat", AnimalType.CAT, new Date(946684861000L))), - new Owner(OWNER_WITH_PETS_LOGIN, "juanpass", + new Owner(OWNER_WITH_PETS_LOGIN, OWNER_WITH_PETS_LOGIN + "pass", new Pet(2, "Max", AnimalType.CAT, new Date(946684861000L)), new Pet(3, "Juandog", AnimalType.DOG, new Date(946684861000L)) ), @@ -45,7 +45,7 @@ public class OwnersDataset { new Pet(5, "Max", AnimalType.DOG, new Date(946684861000L)), new Pet(6, "Anabird", AnimalType.BIRD, new Date(946684861000L)) ), - new Owner(OWNER_WITHOUT_PETS_LOGIN, "lorenapass") + new Owner(OWNER_WITHOUT_PETS_LOGIN, OWNER_WITHOUT_PETS_LOGIN + "pass") }; } @@ -117,6 +117,22 @@ public class OwnersDataset { return new Owner(newOwnerLogin(), newOwnerPassword()); } + public static Owner newOwnerWithFreshPets() { + return new Owner(newOwnerLogin(), newOwnerPassword(), + new Pet("Jacintocat", AnimalType.CAT, new Date(946684861000L)), + new Pet("Jacintodo", AnimalType.DOG, new Date(946684861000L)), + new Pet("Jacintobird", AnimalType.BIRD, new Date(946684861000L)) + ); + } + + public static Owner newOwnerWithPersistentPets() { + return new Owner(newOwnerLogin(), newOwnerPassword(), + new Pet(7, "Jacintocat", AnimalType.CAT, new Date(946684861000L)), + new Pet(8, "Jacintodo", AnimalType.DOG, new Date(946684861000L)), + new Pet(9, "Jacintobird", AnimalType.BIRD, new Date(946684861000L)) + ); + } + public static String newOwnerLogin() { return "jacinto"; } @@ -125,22 +141,6 @@ public class OwnersDataset { return "jacintopass"; } - public static Owner newOwnerWithFreshPets() { - return new Owner(newOwnerLogin(), newOwnerPassword(), - new Pet("Jacintocat", AnimalType.CAT, new Date(946684861000L)), - new Pet("Jacintodo", AnimalType.DOG, new Date(946684861000L)), - new Pet("Jacintobird", AnimalType.BIRD, new Date(946684861000L)) - ); - } - - public static Owner newOwnerWithPersistentPets() { - return new Owner(newOwnerLogin(), newOwnerPassword(), - new Pet(7, "Jacintocat", AnimalType.CAT, new Date(946684861000L)), - new Pet(8, "Jacintodo", AnimalType.DOG, new Date(946684861000L)), - new Pet(9, "Jacintobird", AnimalType.BIRD, new Date(946684861000L)) - ); - } - public static String anyLogin() { return existentLogin(); } @@ -148,6 +148,10 @@ public class OwnersDataset { public static String existentLogin() { return EXISTENT_LOGIN; } + + public static String existentPassword() { + return EXISTENT_LOGIN + "pass"; + } public static String nonExistentLogin() { return NON_EXISTENT_LOGIN; @@ -156,6 +160,10 @@ public class OwnersDataset { public static Owner anyOwner() { return ownerWithLogin(anyLogin()); } + + public static String anyOwnerPassword() { + return anyOwner().getLogin() + "pass"; + } public static Owner existentOwner() { return ownerWithLogin(existentLogin()); diff --git a/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/UsersDataset.java b/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/UsersDataset.java new file mode 100644 index 0000000000000000000000000000000000000000..e1c3ac7fac390644252da31030cf8c0595ab71e1 --- /dev/null +++ b/tests/src/main/java/es/uvigo/esei/xcs/domain/entities/UsersDataset.java @@ -0,0 +1,19 @@ +package es.uvigo.esei.xcs.domain.entities; + +public class UsersDataset { + public static final String EXISTENT_LOGIN = "jose"; + + public static User[] users() { + final Owner[] owners = OwnersDataset.owners(); + final User[] users = new User[owners.length + 1]; + + users[0] = new Administrator(EXISTENT_LOGIN, EXISTENT_LOGIN + "pass"); + System.arraycopy(owners, 0, users, 1, owners.length); + + return users; + } + + public static User existentAdmin() { + return users()[0]; + } +}