diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorAsyncClient.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorAsyncClient.java index a7515639a3..7c9108ddc2 100644 --- a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorAsyncClient.java +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorAsyncClient.java @@ -20,6 +20,7 @@ package org.jclouds.vcloud.director.v1_5; import org.jclouds.rest.annotations.Delegate; import org.jclouds.vcloud.director.v1_5.domain.Catalog; +import org.jclouds.vcloud.director.v1_5.domain.Group; import org.jclouds.vcloud.director.v1_5.domain.Media; import org.jclouds.vcloud.director.v1_5.domain.Org; import org.jclouds.vcloud.director.v1_5.domain.Session; @@ -28,6 +29,7 @@ import org.jclouds.vcloud.director.v1_5.domain.Vdc; import org.jclouds.vcloud.director.v1_5.domain.ovf.Network; import org.jclouds.vcloud.director.v1_5.features.AdminCatalogAsyncClient; import org.jclouds.vcloud.director.v1_5.features.CatalogAsyncClient; +import org.jclouds.vcloud.director.v1_5.features.GroupAsyncClient; import org.jclouds.vcloud.director.v1_5.features.NetworkAsyncClient; import org.jclouds.vcloud.director.v1_5.features.OrgAsyncClient; import org.jclouds.vcloud.director.v1_5.features.QueryAsyncClient; @@ -112,4 +114,10 @@ public interface VCloudDirectorAsyncClient { */ @Delegate AdminCatalogAsyncClient getAdminCatalogClient(); + + /** + * @return asynchronous access to {@link Group} features + */ + @Delegate + GroupAsyncClient getGroupClient(); } diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorClient.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorClient.java index 294b49b5a8..aa922a4239 100644 --- a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorClient.java +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorClient.java @@ -23,6 +23,7 @@ import java.util.concurrent.TimeUnit; import org.jclouds.concurrent.Timeout; import org.jclouds.rest.annotations.Delegate; import org.jclouds.vcloud.director.v1_5.domain.Catalog; +import org.jclouds.vcloud.director.v1_5.domain.Group; import org.jclouds.vcloud.director.v1_5.domain.Media; import org.jclouds.vcloud.director.v1_5.domain.Org; import org.jclouds.vcloud.director.v1_5.domain.Session; @@ -31,6 +32,7 @@ import org.jclouds.vcloud.director.v1_5.domain.Vdc; import org.jclouds.vcloud.director.v1_5.domain.ovf.Network; import org.jclouds.vcloud.director.v1_5.features.AdminCatalogClient; import org.jclouds.vcloud.director.v1_5.features.CatalogClient; +import org.jclouds.vcloud.director.v1_5.features.GroupClient; import org.jclouds.vcloud.director.v1_5.features.MediaClient; import org.jclouds.vcloud.director.v1_5.features.NetworkClient; import org.jclouds.vcloud.director.v1_5.features.OrgClient; @@ -115,5 +117,10 @@ public interface VCloudDirectorClient { */ @Delegate AdminCatalogClient getAdminCatalogClient(); - + + /** + * @return synchronous access to {@link Group} features + */ + @Delegate + GroupClient getGroupClient(); } diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorMediaType.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorMediaType.java index d6a8846239..a81599610d 100644 --- a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorMediaType.java +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/VCloudDirectorMediaType.java @@ -133,6 +133,8 @@ public class VCloudDirectorMediaType { public static final String PUBLISH_CATALOG_PARAMS = "application/vnd.vmware.admin.publishCatalogParams+xml"; + public static final String GROUP = "application/vnd.vmware.admin.group+xml"; + /** * * All acceptable media types. @@ -151,6 +153,6 @@ public class VCloudDirectorMediaType { CONTROL_ACCESS, VAPP_TEMPLATE, CUSTOMIZATION_SECTION, GUEST_CUSTOMIZATION_SECTION, NETWORK_SECTION, NETWORK_CONFIG_SECTION, NETWORK_CONNECTION_SECTION, CLONE_MEDIA_PARAMS, LEASE_SETTINGS_SECTION, RELOCATE_TEMPLATE, ENVELOPE, - PUBLISH_CATALOG_PARAMS + PUBLISH_CATALOG_PARAMS, GROUP ); } diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/config/VCloudDirectorRestClientModule.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/config/VCloudDirectorRestClientModule.java index e5c7a0da58..7bf58b8bb1 100644 --- a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/config/VCloudDirectorRestClientModule.java +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/config/VCloudDirectorRestClientModule.java @@ -86,6 +86,7 @@ public class VCloudDirectorRestClientModule extends RestClientModuleJava class for Group complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+ * <complexType name="Group">
+ *   <complexContent>
+ *     <extension base="{http://www.vmware.com/vcloud/v1.5}EntityType">
+ *       <sequence>
+ *         <element name="NameInSource" type="{http://www.w3.org/2001/XMLSchema}string" minOccurs="0"/>
+ *         <element name="UsersList" type="{http://www.vmware.com/vcloud/v1.5}UsersListType" minOccurs="0"/>
+ *         <element name="Role" type="{http://www.vmware.com/vcloud/v1.5}ReferenceType" minOccurs="0"/>
+ *       </sequence>
+ *       <anyAttribute processContents='lax' namespace='##other'/>
+ *     </extension>
+ *   </complexContent>
+ * </complexType>
+ * 
+ * + * + */ +@XmlAccessorType(XmlAccessType.FIELD) +@XmlRootElement(name = "Group") +@XmlType(propOrder = { + "nameInSource", + "usersList", + "role" +}) +public class Group extends EntityType { + public static Builder builder() { + return new Builder(); + } + + public Builder toBuilder() { + return new Builder().fromGroup(this); + } + + public static class Builder extends EntityType.Builder { + + private String nameInSource; + private UsersList usersList; + private Reference role; + + /** + * @see Group#getNameInSource() + */ + public Builder nameInSource(String nameInSource) { + this.nameInSource = nameInSource; + return this; + } + + /** + * @see Group#getUsersList() + */ + public Builder usersList(UsersList usersList) { + this.usersList = usersList; + return this; + } + + /** + * @see Group#getRole() + */ + public Builder role(Reference role) { + this.role = role; + return this; + } + + public Group build() { + return new Group(href, type, links, description, tasksInProgress, id, name, + nameInSource, usersList, role); + } + + /** + * @see EntityType#getName() + */ + @Override + public Builder name(String name) { + super.name(name); + return this; + } + + /** + * @see EntityType#getDescription() + */ + @Override + public Builder description(String idname) { + super.description(name); + return this; + } + + /** + * @see EntityType#getId() + */ + @Override + public Builder id(String id) { + super.id(id); + return this; + } + + /** + * @see EntityType#getTasksInProgress() + */ + @Override + public Builder tasksInProgress(TasksInProgress tasksInProgress) { + super.tasksInProgress(tasksInProgress); + return this; + } + + /** + * @see ReferenceType#getHref() + */ + @Override + public Builder href(URI href) { + super.href(href); + return this; + } + + /** + * @see ReferenceType#getType() + */ + @Override + public Builder type(String type) { + super.type(type); + return this; + } + + /** + * @see ReferenceType#getLinks() + */ + @Override + public Builder links(Set links) { + super.links(links); + return this; + } + + /** + * @see ReferenceType#getLinks() + */ + @Override + public Builder link(Link link) { + super.link(link); + return this; + } + + @Override + public Builder fromEntityType(EntityType in) { + return Builder.class.cast(super.fromEntityType(in)); + } + public Builder fromGroup(Group in) { + return fromEntityType(in) + .nameInSource(in.getNameInSource()) + .usersList(in.getUsersList()) + .role(in.getRole()); + } + } + + @SuppressWarnings("unused") + private Group() { + // For JAXB + } + + public Group(URI href, String type, Set links, String description, + TasksInProgress tasksInProgress, String id, String name, String nameInSource, + UsersList usersList, Reference role) { + super(href, type, links, description, tasksInProgress, id, name); + this.nameInSource = nameInSource; + this.usersList = usersList; + this.role = role; + } + + @XmlElement(name = "NameInSource") + protected String nameInSource; + @XmlElement(name = "UsersList") + protected UsersList usersList; + @XmlElement(name = "Role") + protected Reference role; + + /** + * Gets the value of the nameInSource property. + * + * @return + * possible object is + * {@link String } + * + */ + public String getNameInSource() { + return nameInSource; + } + + /** + * Gets the value of the usersList property. + * + * @return + * possible object is + * {@link UsersList } + * + */ + public UsersList getUsersList() { + return usersList; + } + + /** + * Gets the value of the role property. + * + * @return + * possible object is + * {@link Reference } + * + */ + public Reference getRole() { + return role; + } + + @Override + public boolean equals(Object o) { + if (this == o) + return true; + if (o == null || getClass() != o.getClass()) + return false; + Group that = Group.class.cast(o); + return super.equals(that) && + equal(nameInSource, that.nameInSource) && + equal(usersList, that.usersList) && + equal(role, that.role); + } + + @Override + public int hashCode() { + return Objects.hashCode(super.hashCode(), + nameInSource, + usersList, + role); + } + + @Override + public String toString() { + return super.string() + .add("nameInSource", nameInSource) + .add("usersList", usersList) + .add("role", role).toString(); + } + +} diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/domain/GroupsList.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/domain/GroupsList.java new file mode 100644 index 0000000000..f74d9c6d77 --- /dev/null +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/domain/GroupsList.java @@ -0,0 +1,165 @@ +/** + * Licensed to jclouds, Inc. (jclouds) under one or more + * contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. jclouds licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package org.jclouds.vcloud.director.v1_5.domain; + +import static com.google.common.base.Objects.equal; +import static com.google.common.base.Preconditions.checkNotNull; + +import java.util.ArrayList; +import java.util.List; + +import javax.xml.bind.annotation.XmlAccessType; +import javax.xml.bind.annotation.XmlAccessorType; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; +import javax.xml.bind.annotation.XmlType; + +import com.google.common.base.Objects; +import com.google.common.collect.ImmutableList; + + +/** + * + * Container for ReferenceType elements that reference groups. + * + * + *

Java class for GroupsList complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+ * <complexType name="GroupsList">
+ *   <complexContent>
+ *     <extension base="{http://www.vmware.com/vcloud/v1.5}VCloudExtensibleType">
+ *       <sequence>
+ *         <element name="GroupReference" type="{http://www.vmware.com/vcloud/v1.5}ReferenceType" maxOccurs="unbounded" minOccurs="0"/>
+ *       </sequence>
+ *       <anyAttribute processContents='lax' namespace='##other'/>
+ *     </extension>
+ *   </complexContent>
+ * </complexType>
+ * 
+ * + * + */ +@XmlAccessorType(XmlAccessType.FIELD) +@XmlRootElement(name = "GroupsList") +@XmlType(propOrder = { + "groupReference" +}) +public class GroupsList { + public static Builder builder() { + return new Builder(); + } + + public Builder toBuilder() { + return new Builder().fromGroupsList(this); + } + + public static class Builder { + private List groups; + + /** + * @see GroupsList#getGroupReference() + */ + public Builder groups(List groups) { + this.groups = ImmutableList.copyOf(groups); + return this; + } + + /** + * @see GroupsList#getGroupReference() + */ + public Builder group(Reference group) { + groups.add(checkNotNull(group, "group")); + return this; + } + + public GroupsList build() { + return new GroupsList(groups); + } + + public Builder fromGroupsList(GroupsList in) { + return groups(in.getGroups()); + } + } + + private GroupsList() { + // For JAXB + } + + private GroupsList(List groups) { + this.groups = groups; + } + + @XmlElement(name = "GroupReference") + protected List groups; + + /** + * Gets the value of the groupReference property. + * + *

+ * This accessor method returns a reference to the live list, + * not a snapshot. Therefore any modification you make to the + * returned list will be present inside the JAXB object. + * This is why there is not a set method for the groupReference property. + * + *

+ * For example, to add a new item, do as follows: + *

+     *    getGroupReference().add(newItem);
+     * 
+ * + * + *

+ * Objects of the following type(s) are allowed in the list + * {@link ReferenceType } + * + * + */ + public List getGroups() { + if (groups == null) { + groups = new ArrayList(); + } + return this.groups; + } + + @Override + public boolean equals(Object o) { + if (this == o) + return true; + if (o == null || getClass() != o.getClass()) + return false; + GroupsList that = GroupsList.class.cast(o); + return equal(groups, that.groups); + } + + @Override + public int hashCode() { + return Objects.hashCode(groups); + } + + @Override + public String toString() { + return Objects.toStringHelper("") + .add("groups", groups).toString(); + } + +} diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/domain/UsersList.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/domain/UsersList.java new file mode 100644 index 0000000000..1e949d30fe --- /dev/null +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/domain/UsersList.java @@ -0,0 +1,165 @@ +/** + * Licensed to jclouds, Inc. (jclouds) under one or more + * contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. jclouds licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +package org.jclouds.vcloud.director.v1_5.domain; + +import static com.google.common.base.Objects.equal; +import static com.google.common.base.Preconditions.checkNotNull; + +import java.util.ArrayList; +import java.util.List; + +import javax.xml.bind.annotation.XmlAccessType; +import javax.xml.bind.annotation.XmlAccessorType; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; +import javax.xml.bind.annotation.XmlType; + +import com.google.common.base.Objects; +import com.google.common.collect.ImmutableList; + + +/** + * + * Container for ReferenceType elements that reference users. + * + * + *

Java class for UsersList complex type. + * + *

The following schema fragment specifies the expected content contained within this class. + * + *

+ * <complexType name="UsersList">
+ *   <complexContent>
+ *     <extension base="{http://www.vmware.com/vcloud/v1.5}VCloudExtensibleType">
+ *       <sequence>
+ *         <element name="UserReference" type="{http://www.vmware.com/vcloud/v1.5}ReferenceType" maxOccurs="unbounded" minOccurs="0"/>
+ *       </sequence>
+ *       <anyAttribute processContents='lax' namespace='##other'/>
+ *     </extension>
+ *   </complexContent>
+ * </complexType>
+ * 
+ * + * + */ +@XmlAccessorType(XmlAccessType.FIELD) +@XmlRootElement(name = "UsersList") +@XmlType(propOrder = { + "userReference" +}) +public class UsersList { + public static Builder builder() { + return new Builder(); + } + + public Builder toBuilder() { + return new Builder().fromUsersList(this); + } + + public static class Builder { + private List users; + + /** + * @see UsersList#getUsers() + */ + public Builder users(List users) { + this.users = ImmutableList.copyOf(users); + return this; + } + + /** + * @see UsersList#getUsers() + */ + public Builder user(Reference user) { + users.add(checkNotNull(user, "user")); + return this; + } + + public UsersList build() { + return new UsersList(users); + } + + public Builder fromUsersList(UsersList in) { + return users(in.getUsers()); + } + } + + private UsersList() { + // For JAXB and builder use + } + + private UsersList(List users) { + this.users = users; + } + + @XmlElement(name = "UserReference") + protected List users; + + /** + * Gets the value of the userReference property. + * + *

+ * This accessor method returns a reference to the live list, + * not a snapshot. Therefore any modification you make to the + * returned list will be present inside the JAXB object. + * This is why there is not a set method for the userReference property. + * + *

+ * For example, to add a new item, do as follows: + *

+     *    getUserReference().add(newItem);
+     * 
+ * + * + *

+ * Objects of the following type(s) are allowed in the list + * {@link ReferenceType } + * + * + */ + public List getUsers() { + if (users == null) { + users = new ArrayList(); + } + return this.users; + } + + @Override + public boolean equals(Object o) { + if (this == o) + return true; + if (o == null || getClass() != o.getClass()) + return false; + UsersList that = UsersList.class.cast(o); + return equal(users, that.users); + } + + @Override + public int hashCode() { + return Objects.hashCode(users); + } + + @Override + public String toString() { + return Objects.toStringHelper("") + .add("userReference", users).toString(); + } + +} diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/features/GroupAsyncClient.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/features/GroupAsyncClient.java new file mode 100644 index 0000000000..76e13dda4b --- /dev/null +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/features/GroupAsyncClient.java @@ -0,0 +1,82 @@ +/** + * Licensed to jclouds, Inc. (jclouds) under one or more + * contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. jclouds licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.jclouds.vcloud.director.v1_5.features; + +import java.net.URI; + +import javax.ws.rs.Consumes; +import javax.ws.rs.DELETE; +import javax.ws.rs.GET; + +import org.jclouds.rest.annotations.EndpointParam; +import org.jclouds.rest.annotations.ExceptionParser; +import org.jclouds.rest.annotations.JAXBResponseParser; +import javax.ws.rs.PUT; +import javax.ws.rs.Produces; + +import org.jclouds.rest.annotations.BinderParam; +import org.jclouds.rest.annotations.EndpointParam; +import org.jclouds.rest.annotations.ExceptionParser; +import org.jclouds.rest.annotations.JAXBResponseParser; +import org.jclouds.rest.annotations.RequestFilters; +import org.jclouds.vcloud.director.v1_5.domain.Group; +import org.jclouds.rest.binders.BindToXMLPayload; +import org.jclouds.vcloud.director.v1_5.VCloudDirectorMediaType; +import org.jclouds.vcloud.director.v1_5.domain.Group; +import org.jclouds.vcloud.director.v1_5.filters.AddVCloudAuthorizationToRequest; +import org.jclouds.vcloud.director.v1_5.functions.ThrowVCloudErrorOn4xx; + +import com.google.common.util.concurrent.ListenableFuture; + +/** + * @see GroupClient + * @author danikov + */ +@RequestFilters(AddVCloudAuthorizationToRequest.class) +public interface GroupAsyncClient { + + /** + * @see GroupClient#getGroup(URI) + */ + @GET + @Consumes + @JAXBResponseParser + @ExceptionParser(ThrowVCloudErrorOn4xx.class) + ListenableFuture getGroup(@EndpointParam URI groupUri); + + /** + * @see GroupClient#updateGroup(URI, Group) + */ + @PUT + @Consumes(VCloudDirectorMediaType.GROUP) + @Produces(VCloudDirectorMediaType.GROUP) + @JAXBResponseParser + @ExceptionParser(ThrowVCloudErrorOn4xx.class) + ListenableFuture updateCatalog(@EndpointParam URI groupRef, + @BinderParam(BindToXMLPayload.class) Group group); + + /** + * @see GroupClient#deleteGroup(URI) + */ + @DELETE + @Consumes + @JAXBResponseParser + @ExceptionParser(ThrowVCloudErrorOn4xx.class) + ListenableFuture deleteGroup(@EndpointParam URI groupRef); +} diff --git a/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/features/GroupClient.java b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/features/GroupClient.java new file mode 100644 index 0000000000..9d0edfb9f9 --- /dev/null +++ b/labs/vcloud-director/src/main/java/org/jclouds/vcloud/director/v1_5/features/GroupClient.java @@ -0,0 +1,66 @@ +/** + * Licensed to jclouds, Inc. (jclouds) under one or more + * contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. jclouds licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.jclouds.vcloud.director.v1_5.features; + +import java.net.URI; +import java.util.concurrent.TimeUnit; + +import org.jclouds.concurrent.Timeout; +import org.jclouds.vcloud.director.v1_5.domain.Group; + +/** + * Provides synchronous access to {@link Group} objects. + * + * @see GroupAsyncClient + * @author danikov + */ +@Timeout(duration = 180, timeUnit = TimeUnit.SECONDS) +public interface GroupClient { + + /** + * Retrieves a group. + * + *

+    * GET /admin/group/{id}
+    * 
+ * + * @param groupURI the reference for the group + * @return a group + */ + Group getGroup(URI groupUri); + /** + * Modifies a group. + * + *
+    * PUT /admin/group/{id}
+    * 
+ * + * @return the updated group + */ + Group updateGroup(URI groupRef, Group group); + + /** + * Deletes a group. + * + *
+    * DELETE /admin/group/{id}
+    * 
+ */ + void deleteGroup(URI groupRef); +} diff --git a/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/domain/Checks.java b/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/domain/Checks.java index 697bfbb720..89d0f76fcf 100644 --- a/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/domain/Checks.java +++ b/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/domain/Checks.java @@ -485,11 +485,43 @@ public class Checks { public static void checkMediaFor(String client, Media media) { // required assertNotNull(media.getImageType(), String.format(OBJ_FIELD_REQ, client, "imageType")); - Checks.checkImageType(media.getImageType()); + checkImageType(media.getImageType()); assertNotNull(media.getSize(), String.format(OBJ_FIELD_REQ, client, "size")); assertTrue(media.getSize() >= 0, String.format(OBJ_FIELD_GTE_0, client, "size", media.getSize())); // parent type - Checks.checkResourceEntityType(media); + checkResourceEntityType(media); + } + + public static void checkGroupsList(GroupsList groupsList) { + // Check optional fields + if (groupsList.getGroups() != null) { + for (Reference group : groupsList.getGroups()) { + checkReferenceType(group); + } + } + } + + public static void checkGroup(Group group) { + // Check optional fields + // NOTE nameInSource cannot be checked + if (group.getUsersList() != null) { + checkUsersList(group.getUsersList()); + } + if (group.getRole() != null) { + checkReferenceType(group.getRole()); + } + + // parent type + checkEntityType(group); + } + + public static void checkUsersList(UsersList usersList) { + // Check optional fields + if (usersList.getUsers() != null) { + for (Reference user : usersList.getUsers()) { + checkReferenceType(user); + } + } } } diff --git a/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/features/GroupClientExpectTest.java b/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/features/GroupClientExpectTest.java new file mode 100644 index 0000000000..c5e5e95464 --- /dev/null +++ b/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/features/GroupClientExpectTest.java @@ -0,0 +1,101 @@ +/* + * Licensed to jclouds, Inc. (jclouds) under one or more + * contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. jclouds licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.jclouds.vcloud.director.v1_5.features; + +import static org.testng.Assert.assertEquals; + +import java.net.URI; + +import org.jclouds.vcloud.director.v1_5.VCloudDirectorClient; +import org.jclouds.vcloud.director.v1_5.VCloudDirectorMediaType; +import org.jclouds.vcloud.director.v1_5.domain.Group; +import org.jclouds.vcloud.director.v1_5.domain.Reference; +import org.jclouds.vcloud.director.v1_5.internal.BaseVCloudDirectorRestClientExpectTest; +import org.testng.annotations.Test; + +/** + * Test the {@link GroupClient} by observing its side effects. + * + * @author danikov + */ +@Test(groups = { "unit", "user", "group"}, singleThreaded = true, testName = "GroupClientExpectTest") +public class GroupClientExpectTest extends BaseVCloudDirectorRestClientExpectTest { + + private Reference groupRef = Reference.builder() + .type("application/vnd.vmware.admin.group+xml") + .name("???") + .href(URI.create(endpoint + "/admin/group/???")) + .build(); + + @Test(enabled = false) + public void testGetGroup() { + VCloudDirectorClient client = requestsSendResponses(loginRequest, sessionResponse, + new VcloudHttpRequestPrimer() + .apiCommand("GET", "/admin/group/???") + .acceptAnyMedia() + .httpRequestBuilder().build(), + new VcloudHttpResponsePrimer() + .xmlFilePayload("/group/group.xml", VCloudDirectorMediaType.GROUP) + .httpResponseBuilder().build()); + + Group expected = group(); + + assertEquals(client.getGroupClient().getGroup(groupRef.getURI()), expected); + } + + public static final Group group() { + return Group.builder() + + .build(); + } + + @Test(enabled = false) + public void testUpdateGroup() { + VCloudDirectorClient client = requestsSendResponses(loginRequest, sessionResponse, + new VcloudHttpRequestPrimer() + .apiCommand("PUT", "/admin/group/???") + .xmlFilePayload("/group/updateGroupSource.xml", VCloudDirectorMediaType.GROUP) + .acceptMedia(VCloudDirectorMediaType.GROUP) + .httpRequestBuilder().build(), + new VcloudHttpResponsePrimer() + .xmlFilePayload("/group/updateGroup.xml", VCloudDirectorMediaType.GROUP) + .httpResponseBuilder().build()); + + Group expected = updateGroup(); + + assertEquals(client.getGroupClient().updateGroup(groupRef.getURI(), expected), expected); + } + + public static Group updateGroup() { + return null; // TODO chain onto group() then toBuilder() and modify? + } + + @Test + public void testDeleteGroup() { + VCloudDirectorClient client = requestsSendResponses(loginRequest, sessionResponse, + new VcloudHttpRequestPrimer() + .apiCommand("DELETE", "/admin/group/???") + .acceptAnyMedia() + .httpRequestBuilder().build(), + new VcloudHttpResponsePrimer() + .httpResponseBuilder().statusCode(204).build()); + + client.getAdminCatalogClient().deleteCatalog(groupRef.getURI()); + } +} diff --git a/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/features/GroupClientLiveTest.java b/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/features/GroupClientLiveTest.java new file mode 100644 index 0000000000..6a618fc4d9 --- /dev/null +++ b/labs/vcloud-director/src/test/java/org/jclouds/vcloud/director/v1_5/features/GroupClientLiveTest.java @@ -0,0 +1,141 @@ +/* + * Licensed to jclouds, Inc. (jclouds) under one or more + * contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. jclouds licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.jclouds.vcloud.director.v1_5.features; + +import static org.jclouds.vcloud.director.v1_5.VCloudDirectorLiveTestConstants.REF_REQ_LIVE; +import static org.testng.Assert.assertNotNull; + +import static org.jclouds.vcloud.director.v1_5.VCloudDirectorLiveTestConstants.OBJ_DEL; +import static org.testng.Assert.assertEquals; +import static org.testng.Assert.assertNull; +import static org.testng.Assert.fail; +import static com.google.common.base.Objects.equal; +import static org.jclouds.vcloud.director.v1_5.VCloudDirectorLiveTestConstants.OBJ_FIELD_UPDATABLE; +import static org.testng.Assert.assertTrue; + + +import java.net.URI; + +import org.jclouds.vcloud.director.v1_5.domain.Checks; +import org.jclouds.vcloud.director.v1_5.VCloudDirectorException; +import org.jclouds.vcloud.director.v1_5.domain.Error; +import org.jclouds.vcloud.director.v1_5.domain.Group; +import org.jclouds.vcloud.director.v1_5.domain.Owner; +import org.jclouds.vcloud.director.v1_5.domain.Reference; +import org.jclouds.vcloud.director.v1_5.domain.ReferenceType; +import org.jclouds.vcloud.director.v1_5.internal.BaseVCloudDirectorClientLiveTest; +import org.testng.annotations.BeforeClass; +import org.testng.annotations.Test; + +/** + * Tests live behavior of {@link AdminGroupClient}. + * + * @author danikov + */ +@Test(groups = { "live", "admin", "group" }, singleThreaded = true, testName = "GroupClientLiveTest") +public class GroupClientLiveTest extends BaseVCloudDirectorClientLiveTest { + + public static final String GROUP = "admin group"; + + /* + * Convenience references to API clients. + */ + + private GroupClient groupClient; + + /* + * Shared state between dependant tests. + */ + private ReferenceType groupRef; + private Group group; + + @BeforeClass(inheritGroups = true) + public void setupRequiredClients() { + groupClient = context.getApi().getGroupClient(); + groupRef = Reference.builder() + .href(URI.create("https://vcloudbeta.bluelock.com/api/admin/group/???")) + .build(); + } + + @Test(testName = "GET /admin/group/{id}", enabled = false) + public void testGetGroup() { + assertNotNull(groupRef, String.format(REF_REQ_LIVE, "Group")); + group = groupClient.getGroup(groupRef.getURI()); + + Checks.checkGroup(group); + } + + @Test(testName = "PUT /admin/group/{id}") // TODO: depends on? + public void updateGroup() { + String oldName = group.getName(); + String newName = "new "+oldName; + String oldDescription = group.getDescription(); + String newDescription = "new "+oldDescription; + //TODO: check other modifiables + + try { + group = group.toBuilder() + .name(newName) + .description(newDescription) + .build(); + + group = groupClient.updateGroup(group.getURI(), group); + + assertTrue(equal(group.getName(), newName), String.format(OBJ_FIELD_UPDATABLE, GROUP, "name")); + assertTrue(equal(group.getDescription(), newDescription), + String.format(OBJ_FIELD_UPDATABLE, GROUP, "description")); + + //TODO negative tests? + + Checks.checkGroup(group); + } finally { + group = group.toBuilder() + .name(oldName) + .description(oldDescription) + .build(); + + group = groupClient.updateGroup(group.getURI(), group); + } + } + + @Test(testName = "DELETE /admin/group/{id}", enabled = false ) + public void testDeleteCatalog() { + groupClient.deleteGroup(groupRef.getURI()); + + Error expected = Error.builder() + .message("???") + .majorErrorCode(403) + .minorErrorCode("ACCESS_TO_RESOURCE_IS_FORBIDDEN") + .build(); + + try { + group = groupClient.getGroup(groupRef.getURI()); + fail("Should give HTTP 403 error"); + } catch (VCloudDirectorException vde) { + assertEquals(vde.getError(), expected); + group = null; + } catch (Exception e) { + fail("Should have thrown a VCloudDirectorException"); + } + + if (group != null) { // guard against NPE on the .toStrings + assertNull(group, String.format(OBJ_DEL, GROUP, group.toString())); + } + } +} diff --git a/labs/vcloud-director/src/test/resources/group/group.xml b/labs/vcloud-director/src/test/resources/group/group.xml new file mode 100644 index 0000000000..e69de29bb2 diff --git a/labs/vcloud-director/src/test/resources/group/updateGroup.xml b/labs/vcloud-director/src/test/resources/group/updateGroup.xml new file mode 100644 index 0000000000..e69de29bb2 diff --git a/labs/vcloud-director/src/test/resources/group/updateGroupSource.xml b/labs/vcloud-director/src/test/resources/group/updateGroupSource.xml new file mode 100644 index 0000000000..e69de29bb2