Merge pull request #125 from richardcloudsoft/cloudstack-template

Complete the Cloudstack "template" API
This commit is contained in:
Adrian Cole 2011-11-10 00:50:13 -08:00
commit 19c2d380f3
14 changed files with 1387 additions and 10 deletions

View File

@ -0,0 +1,53 @@
/**
* 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.cloudstack.binders;
import org.jclouds.cloudstack.domain.TemplateMetadata;
import org.jclouds.http.HttpRequest;
import org.jclouds.http.utils.ModifyRequest;
import org.jclouds.rest.Binder;
import javax.inject.Inject;
import javax.inject.Provider;
import javax.ws.rs.core.UriBuilder;
import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.base.Preconditions.checkNotNull;
/**
* @author Richard Downer
*/
public class BindTemplateMetadataToQueryParams implements Binder {
private final Provider<UriBuilder> uriBuilderProvider;
@Inject
public BindTemplateMetadataToQueryParams(Provider<UriBuilder> uriBuilderProvider) {
this.uriBuilderProvider = checkNotNull(uriBuilderProvider, "uriBuilderProvider");
}
@Override
public <R extends HttpRequest> R bindToRequest(R request, Object input) {
checkArgument(input instanceof TemplateMetadata, "this binder is only valid for TemplateMetadata");
TemplateMetadata metadata = (TemplateMetadata) input;
request = ModifyRequest.addQueryParam(request, "name", metadata.getName(), uriBuilderProvider.get());
request = ModifyRequest.addQueryParam(request, "ostypeid", metadata.getOsTypeId(), uriBuilderProvider.get());
request = ModifyRequest.addQueryParam(request, "displaytext", metadata.getDisplayText(), uriBuilderProvider.get());
return request;
}
}

View File

@ -233,6 +233,19 @@ public class Template implements Comparable<Template> {
} }
} }
public enum ExtractMode {
HTTP_DOWNLOAD, FTP_UPLOAD, UNRECOGNIZED;
public static ExtractMode fromValue(String format) {
try {
return valueOf(checkNotNull(format, "format"));
} catch (IllegalArgumentException e) {
return UNRECOGNIZED;
}
}
}
private long id; private long id;
@SerializedName("displaytext") @SerializedName("displaytext")
private String displayText; private String displayText;

View File

@ -0,0 +1,133 @@
/**
* 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.cloudstack.domain;
/**
* @author Richard Downer
*/
public class TemplateMetadata {
public static Builder builder() {
return new Builder();
}
public static class Builder {
private String name;
private long osTypeId;
private String displayText;
/**
* @param name the name of the template
*/
public Builder name(String name) {
this.name = name;
return this;
}
/**
* @param osTypeId the ID of the OS Type that best represents the OS of this template.
*/
public Builder osTypeId(long osTypeId) {
this.osTypeId = osTypeId;
return this;
}
/**
* @param displayText the display text of the template. This is usually used for display purposes.
*/
public Builder displayText(String displayText) {
this.displayText = displayText;
return this;
}
public TemplateMetadata build() {
return new TemplateMetadata(name, osTypeId, displayText);
}
}
private String name;
private long osTypeId;
private String displayText;
public TemplateMetadata(String name, long osTypeId, String displayText) {
this.name = name;
this.osTypeId = osTypeId;
this.displayText = displayText;
}
/**
* present only for serializer
*/
TemplateMetadata() {
}
/**
* @return the name of the template
*/
public String getName() {
return name;
}
/**
* @return the ID of the OS Type that best represents the OS of this template.
*/
public long getOsTypeId() {
return osTypeId;
}
/**
* @return the display text of the template. This is usually used for display purposes.
*/
public String getDisplayText() {
return displayText;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
TemplateMetadata that = (TemplateMetadata) o;
if (osTypeId != that.osTypeId) return false;
if (displayText != null ? !displayText.equals(that.displayText) : that.displayText != null) return false;
if (name != null ? !name.equals(that.name) : that.name != null) return false;
return true;
}
@Override
public int hashCode() {
int result = name != null ? name.hashCode() : 0;
result = 31 * result + (int) (osTypeId ^ (osTypeId >>> 32));
result = 31 * result + (displayText != null ? displayText.hashCode() : 0);
return result;
}
@Override
public String toString() {
return "[" +
"name='" + name + '\'' +
", osTypeId=" + osTypeId +
", displayText='" + displayText + '\'' +
']';
}
}

View File

@ -0,0 +1,159 @@
/**
* 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.cloudstack.domain;
import com.google.gson.annotations.SerializedName;
/**
* @author Richard Downer
*/
public class TemplatePermission implements Comparable<TemplatePermission> {
public static Builder builder() {
return new Builder();
}
public static class Builder {
private long id;
private String account;
private long domainId;
private boolean isPublic;
public Builder id(long id) {
this.id = id;
return this;
}
public Builder account(String account) {
this.account = account;
return this;
}
public Builder domainId(long domainId) {
this.domainId = domainId;
return this;
}
public Builder isPublic(boolean isPublic) {
this.isPublic = isPublic;
return this;
}
public TemplatePermission build() {
return new TemplatePermission(id, account, domainId, isPublic);
}
}
private long id;
private String account;
@SerializedName("domainid") private long domainId;
@SerializedName("ispublic") private boolean isPublic;
/**
* Construct a new TemplatePermission instance.
* @param id the template ID
* @param account the list of accounts the template is available for
* @param domainId the ID of the domain to which the template belongs
* @param isPublic true if this template is a public template, false otherwise
*/
public TemplatePermission(long id, String account, long domainId, boolean isPublic) {
this.id = id;
this.account = account;
this.domainId = domainId;
this.isPublic = isPublic;
}
/**
* present only for serializer
*/
TemplatePermission() {
}
/**
* Gets the template ID
* @return the template ID
*/
public long getId() {
return id;
}
/**
* Gets the list of accounts the template is available for
* @return the list of accounts the template is available for
*/
public String getAccount() {
return account;
}
/**
* Gets the ID of the domain to which the template belongs
* @return the ID of the domain to which the template belongs
*/
public long getDomainId() {
return domainId;
}
/**
* Returns true if this template is a public template, false otherwise
* @return true if this template is a public template, false otherwise
*/
public boolean isPublic() {
return isPublic;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
TemplatePermission that = (TemplatePermission) o;
if (domainId != that.domainId) return false;
if (id != that.id) return false;
if (isPublic != that.isPublic) return false;
if (account != null ? !account.equals(that.account) : that.account != null) return false;
return true;
}
@Override
public int hashCode() {
int result = (int) (id ^ (id >>> 32));
result = 31 * result + (account != null ? account.hashCode() : 0);
result = 31 * result + (int) (domainId ^ (domainId >>> 32));
result = 31 * result + (isPublic ? 1 : 0);
return result;
}
@Override
public String toString() {
return "[" +
"id=" + id +
", account='" + account + '\'' +
", domainId=" + domainId +
", isPublic=" + isPublic +
']';
}
@Override
public int compareTo(TemplatePermission other) {
return new Long(id).compareTo(other.getId());
}
}

View File

@ -25,18 +25,32 @@ import javax.ws.rs.GET;
import javax.ws.rs.QueryParam; import javax.ws.rs.QueryParam;
import javax.ws.rs.core.MediaType; import javax.ws.rs.core.MediaType;
import org.jclouds.cloudstack.binders.BindTemplateMetadataToQueryParams;
import org.jclouds.cloudstack.domain.AsyncCreateResponse;
import org.jclouds.cloudstack.domain.Template; import org.jclouds.cloudstack.domain.Template;
import org.jclouds.cloudstack.domain.TemplateMetadata;
import org.jclouds.cloudstack.domain.TemplatePermission;
import org.jclouds.cloudstack.filters.QuerySigner; import org.jclouds.cloudstack.filters.QuerySigner;
import org.jclouds.cloudstack.options.AccountInDomainOptions;
import org.jclouds.cloudstack.options.CreateTemplateOptions;
import org.jclouds.cloudstack.options.DeleteTemplateOptions;
import org.jclouds.cloudstack.options.ExtractTemplateOptions;
import org.jclouds.cloudstack.options.ListTemplatesOptions; import org.jclouds.cloudstack.options.ListTemplatesOptions;
import org.jclouds.cloudstack.options.RegisterTemplateOptions;
import org.jclouds.cloudstack.options.UpdateTemplateOptions;
import org.jclouds.cloudstack.options.UpdateTemplatePermissionsOptions;
import org.jclouds.rest.annotations.BinderParam;
import org.jclouds.rest.annotations.ExceptionParser; import org.jclouds.rest.annotations.ExceptionParser;
import org.jclouds.rest.annotations.OnlyElement; import org.jclouds.rest.annotations.OnlyElement;
import org.jclouds.rest.annotations.QueryParams; import org.jclouds.rest.annotations.QueryParams;
import org.jclouds.rest.annotations.RequestFilters; import org.jclouds.rest.annotations.RequestFilters;
import org.jclouds.rest.annotations.SelectJson; import org.jclouds.rest.annotations.SelectJson;
import org.jclouds.rest.annotations.Unwrap;
import org.jclouds.rest.functions.ReturnEmptySetOnNotFoundOr404; import org.jclouds.rest.functions.ReturnEmptySetOnNotFoundOr404;
import org.jclouds.rest.functions.ReturnNullOnNotFoundOr404; import org.jclouds.rest.functions.ReturnNullOnNotFoundOr404;
import com.google.common.util.concurrent.ListenableFuture; import com.google.common.util.concurrent.ListenableFuture;
import org.jclouds.rest.functions.ReturnVoidOnNotFoundOr404;
/** /**
* Provides asynchronous access to cloudstack via their REST API. * Provides asynchronous access to cloudstack via their REST API.
@ -50,6 +64,50 @@ import com.google.common.util.concurrent.ListenableFuture;
@QueryParams(keys = "response", values = "json") @QueryParams(keys = "response", values = "json")
public interface TemplateAsyncClient { public interface TemplateAsyncClient {
/**
* @see TemplateClient#createTemplate
*/
@GET
@QueryParams(keys = "command", values = "createTemplate")
@Unwrap
@Consumes(MediaType.APPLICATION_JSON)
ListenableFuture<AsyncCreateResponse> createTemplate(@BinderParam(BindTemplateMetadataToQueryParams.class) TemplateMetadata templateMetadata, CreateTemplateOptions... options);
/**
* @see TemplateClient#registerTemplate
*/
@GET
@QueryParams(keys = "command", values = "registerTemplate")
@SelectJson("template")
@Consumes(MediaType.APPLICATION_JSON)
ListenableFuture<Template> registerTemplate(@BinderParam(BindTemplateMetadataToQueryParams.class) TemplateMetadata templateMetadata, @QueryParam("format") String format, @QueryParam("hypervisor") String hypervisor, @QueryParam("url") String url, @QueryParam("zoneid") long zoneId, RegisterTemplateOptions... options);
/**
* @see TemplateClient#updateTemplate
*/
@GET
@QueryParams(keys = "command", values = "updateTemplate")
@SelectJson("template")
@Consumes(MediaType.APPLICATION_JSON)
ListenableFuture<Template> updateTemplate(@QueryParam("id") long id, UpdateTemplateOptions... options);
/**
* @see TemplateClient#copyTemplate
*/
@GET
@QueryParams(keys = "command", values = "copyTemplate")
@Unwrap
@Consumes(MediaType.APPLICATION_JSON)
ListenableFuture<AsyncCreateResponse> copyTemplateToZone(@QueryParam("id") long id, @QueryParam("sourcezoneid") long sourceZoneId, @QueryParam("destzoneid") long destZoneId);
/**
* @see TemplateClient#deleteTemplate
*/
@GET
@QueryParams(keys = "command", values = "deleteTemplate")
@ExceptionParser(ReturnVoidOnNotFoundOr404.class)
ListenableFuture<Void> deleteTemplate(@QueryParam("id") long id, DeleteTemplateOptions... options);
/** /**
* @see TemplateClient#listTemplates * @see TemplateClient#listTemplates
*/ */
@ -79,6 +137,30 @@ public interface TemplateAsyncClient {
@OnlyElement @OnlyElement
@Consumes(MediaType.APPLICATION_JSON) @Consumes(MediaType.APPLICATION_JSON)
@ExceptionParser(ReturnNullOnNotFoundOr404.class) @ExceptionParser(ReturnNullOnNotFoundOr404.class)
ListenableFuture<Template> getTemplateInZone(@QueryParam("zoneid") long zoneId, @QueryParam("id") long id); ListenableFuture<Template> getTemplateInZone(@QueryParam("id") long templateId, @QueryParam("zoneid") long zoneId);
/**
* @see TemplateClient#updateTemplatePermissions
*/
@GET
@QueryParams(keys = "command", values = "updateTemplatePermissions")
ListenableFuture<Void> updateTemplatePermissions(@QueryParam("id") long id, UpdateTemplatePermissionsOptions... options);
/**
* @see TemplateClient#listTemplatePermissions
*/
@GET
@QueryParams(keys = "command", values = "listTemplatePermissions")
@Unwrap
@Consumes(MediaType.APPLICATION_JSON)
ListenableFuture<Set<TemplatePermission>> listTemplatePermissions(@QueryParam("id") long id, AccountInDomainOptions... options);
/**
* @see TemplateClient#extractTemplate
*/
@GET
@QueryParams(keys = "command", values = "extractTemplate")
@Unwrap
@Consumes(MediaType.APPLICATION_JSON)
ListenableFuture<AsyncCreateResponse> extractTemplate(@QueryParam("id") long id, @QueryParam("mode") Template.ExtractMode mode, @QueryParam("zoneid") long zoneId, ExtractTemplateOptions... options);
} }

View File

@ -21,9 +21,18 @@ package org.jclouds.cloudstack.features;
import java.util.Set; import java.util.Set;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import org.jclouds.cloudstack.domain.AsyncCreateResponse;
import org.jclouds.cloudstack.domain.Template; import org.jclouds.cloudstack.domain.Template;
import org.jclouds.cloudstack.domain.TemplateFilter; import org.jclouds.cloudstack.domain.TemplateFilter;
import org.jclouds.cloudstack.domain.TemplatePermission;
import org.jclouds.cloudstack.options.AccountInDomainOptions;
import org.jclouds.cloudstack.options.CreateTemplateOptions;
import org.jclouds.cloudstack.options.DeleteTemplateOptions;
import org.jclouds.cloudstack.options.ExtractTemplateOptions;
import org.jclouds.cloudstack.options.ListTemplatesOptions; import org.jclouds.cloudstack.options.ListTemplatesOptions;
import org.jclouds.cloudstack.options.RegisterTemplateOptions;
import org.jclouds.cloudstack.options.UpdateTemplateOptions;
import org.jclouds.cloudstack.options.UpdateTemplatePermissionsOptions;
import org.jclouds.concurrent.Timeout; import org.jclouds.concurrent.Timeout;
/** /**
@ -36,16 +45,69 @@ import org.jclouds.concurrent.Timeout;
*/ */
@Timeout(duration = 60, timeUnit = TimeUnit.SECONDS) @Timeout(duration = 60, timeUnit = TimeUnit.SECONDS)
public interface TemplateClient { public interface TemplateClient {
/**
* Creates a template of a virtual machine. The virtual machine must be in a STOPPED state. A template created from this command is automatically designated as a private template visible to the account that created it.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/createTemplate.html
* @param name the name of the template
* @param osTypeId the ID of the OS Type that best represents the OS of this template.
* @param displayText the display text of the template. This is usually used for display purposes.
* @param options optional arguments
* @return an asynchronous job response
*/
AsyncCreateResponse createTemplate(String name, long osTypeId, String displayText, CreateTemplateOptions... options);
/**
* Registers an existing template into the Cloud.com cloud.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/registerTemplate.html
* @param name the name of the template
* @param osTypeId the ID of the OS Type that best represents the OS of this template.
* @param format the format for the template. Possible values include QCOW2, RAW, and VHD.
* @param hypervisor the target hypervisor for the template
* @param url the URL of where the template is hosted. Possible URL include http:// and https://
* @param zoneId the ID of the zone the template is to be hosted on
* @param displayText the display text of the template. This is usually used for display purposes.
* @param options optional arguments
* @return data about the newly-registered template
*/
Template registerTemplate(String name, long osTypeId, String format, String hypervisor, String url, long zoneId, String displayText, RegisterTemplateOptions... options);
/**
* Updates attributes of a template.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/updateTemplate.html
* @param id the ID of the image file
* @param options optional arguments
* @return updated data about the template
*/
Template updateTemplate(long id, UpdateTemplateOptions... options);
/**
* Copies a template from one zone to another.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/copyTemplate.html
* @param id Template ID.
* @param sourceZoneId ID of the zone the template is currently hosted on.
* @param destZoneId ID of the zone the template is being copied to.
* @return an asynchronous job response
*/
AsyncCreateResponse copyTemplateToZone(long id, long sourceZoneId, long destZoneId);
/**
* Deletes a template from the system. All virtual machines using the deleted template will not be affected.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/deleteTemplate.html
* @param id the ID of the template
* @param options optional arguments
*/
void deleteTemplate(long id, DeleteTemplateOptions... options);
/** /**
* List all executable templates. * List all executable templates.
* * @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/listTemplates.html
* @return all executable templates, or empty set, if no templates are found * @return all executable templates, or empty set, if no templates are found
*/ */
Set<Template> listTemplates(); Set<Template> listTemplates();
/** /**
* List all public, private, and privileged templates. * List all public, private, and privileged templates.
* * @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/listTemplates.html
* @param options * @param options
* if present, how to constrain the list, defaults to all * if present, how to constrain the list, defaults to all
* executable templates * executable templates
@ -56,12 +118,42 @@ public interface TemplateClient {
/** /**
* get a specific template by id * get a specific template by id
* *
*
* @param templateId
* @param zoneId * @param zoneId
* zone template is defined in * zone template is defined in
* @param id
* template to get
* @return template or null if not found * @return template or null if not found
*/ */
Template getTemplateInZone(long zoneId, long id); Template getTemplateInZone(long templateId, long zoneId);
/**
* Updates a template visibility permissions. A public template is visible to all accounts within the same domain. A private
* template is visible only to the owner of the template. A priviledged template is a private template with account
* permissions added. Only accounts specified under the template permissions are visible to them.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/updateTemplatePermissions.html
* @param id the template ID
* @param options optional arguments
*/
void updateTemplatePermissions(long id, UpdateTemplatePermissionsOptions... options);
/**
* List template visibility and all accounts that have permissions to view this template.
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/listTemplatePermissions.html
* @param id the template ID
* @param options optional arguments
* @return the list of permissions that apply to the template
*/
Set<TemplatePermission> listTemplatePermissions(long id, AccountInDomainOptions... options);
/**
*
* @see http://download.cloud.com/releases/2.2.0/api_2.2.8/user/extractTemplate.html
* @param id the ID of the template
* @param mode FIXME the mode of extraction - HTTP_DOWNLOAD or FTP_UPLOAD
* @param zoneId the ID of the zone where the ISO is originally located
* @param options optional arguments
* @return an asynchronous job response
*/
AsyncCreateResponse extractTemplate(long id, String mode, long zoneId, ExtractTemplateOptions... options);
} }

View File

@ -0,0 +1,129 @@
/**
* 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.cloudstack.options;
import com.google.common.collect.ImmutableSet;
import org.jclouds.http.options.BaseHttpRequestOptions;
/**
* Options used to control how a template is created.
*
* @see <a
* href="http://download.cloud.com/releases/2.2.8/api/user/createTemplate.html"
* />
* @author Richard Downer
*/
public class CreateTemplateOptions extends BaseHttpRequestOptions {
public static final CreateTemplateOptions NONE = new CreateTemplateOptions();
/**
* 32 or 64 bit
*/
public CreateTemplateOptions bits(int bits) {
this.queryParameters.replaceValues("bits", ImmutableSet.of(bits + ""));
return this;
}
/**
* true if this template is a featured template, false otherwise
*/
public CreateTemplateOptions isFeatured(boolean isFeatured) {
this.queryParameters.replaceValues("isfeatured", ImmutableSet.of(isFeatured + ""));
return this;
}
/**
* true if this template is a public template, false otherwise
*/
public CreateTemplateOptions isPublic(boolean isPublic) {
this.queryParameters.replaceValues("ispublic", ImmutableSet.of(isPublic + ""));
return this;
}
/**
* true if the template supports the password reset feature; default is false
*/
public CreateTemplateOptions passwordEnabled(boolean passwordEnabled) {
this.queryParameters.replaceValues("passwordenabled", ImmutableSet.of(passwordEnabled + ""));
return this;
}
/**
* true if the template requres HVM, false otherwise
*/
public CreateTemplateOptions requiresHVM(boolean requiresHVM) {
this.queryParameters.replaceValues("requireshvm", ImmutableSet.of(requiresHVM + ""));
return this;
}
/**
* the ID of the snapshot the template is being created from. Either this parameter, or volumeId has to be passed in
*/
public CreateTemplateOptions snapshotId(long snapshotId) {
this.queryParameters.replaceValues("snapshotid", ImmutableSet.of(snapshotId + ""));
return this;
}
/**
* the ID of the disk volume the template is being created from. Either this parameter, or snapshotId has to be passed in
*/
public CreateTemplateOptions volumeId(long volumeId) {
this.queryParameters.replaceValues("volumeid", ImmutableSet.of(volumeId + ""));
return this;
}
public static class Builder {
public static CreateTemplateOptions bits(int bits) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.bits(bits);
}
public static CreateTemplateOptions isFeatured(boolean isFeatured) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.isFeatured(isFeatured);
}
public static CreateTemplateOptions isPublic(boolean isPublic) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.isPublic(isPublic);
}
public static CreateTemplateOptions passwordEnabled(boolean passwordEnabled) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.passwordEnabled(passwordEnabled);
}
public static CreateTemplateOptions requiresHVM(boolean requiresHVM) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.requiresHVM(requiresHVM);
}
public static CreateTemplateOptions snapshotId(long snapshotId) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.snapshotId(snapshotId);
}
public static CreateTemplateOptions volumeId(long volumeId) {
CreateTemplateOptions options = new CreateTemplateOptions();
return options.volumeId(volumeId);
}
}
}

View File

@ -0,0 +1,56 @@
/**
* 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.cloudstack.options;
import com.google.common.collect.ImmutableSet;
import org.jclouds.http.options.BaseHttpRequestOptions;
/**
* Options used to control how a template is created.
*
* @see <a
* href="http://download.cloud.com/releases/2.2.8/api/user/createTemplate.html"
* />
* @author Richard Downer
*/
public class DeleteTemplateOptions extends BaseHttpRequestOptions {
public static final DeleteTemplateOptions NONE = new DeleteTemplateOptions();
/**
* @param zoneId selects the template's zoneId.
*/
public DeleteTemplateOptions zoneId(long zoneId) {
this.queryParameters.replaceValues("zoneid", ImmutableSet.of(zoneId + ""));
return this;
}
public static class Builder {
/**
* @see DeleteTemplateOptions#zoneId
*/
public static DeleteTemplateOptions zoneId(long id) {
DeleteTemplateOptions options = new DeleteTemplateOptions();
return options.zoneId(id);
}
}
}

View File

@ -0,0 +1,48 @@
/**
* 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.cloudstack.options;
import com.google.common.collect.ImmutableSet;
import org.jclouds.http.options.BaseHttpRequestOptions;
/**
* @author Richard Downer
*/
public class ExtractTemplateOptions extends BaseHttpRequestOptions {
public static final ExtractTemplateOptions NONE = new ExtractTemplateOptions();
/**
* the url to which the ISO would be extracted
*/
public ExtractTemplateOptions url(String url) {
this.queryParameters.replaceValues("url", ImmutableSet.of(url));
return this;
}
public static class Builder {
public static ExtractTemplateOptions url(String url) {
ExtractTemplateOptions options = new ExtractTemplateOptions();
return options.url(url);
}
}
}

View File

@ -0,0 +1,145 @@
/**
* 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.cloudstack.options;
import com.google.common.collect.ImmutableSet;
/**
* Options used to control how a template is registered.
*
* @see <a
* href="http://download.cloud.com/releases/2.2.8/api/user/registerTemplate.html"
* />
* @author Richard Downer
*/
public class RegisterTemplateOptions extends AccountInDomainOptions {
public static final RegisterTemplateOptions NONE = new RegisterTemplateOptions();
/**
* 32 or 64 bits support. 64 by default
*/
public RegisterTemplateOptions bits(int bits) {
this.queryParameters.replaceValues("bits", ImmutableSet.of(bits + ""));
return this;
}
/**
* the MD5 checksum value of this template
*/
public RegisterTemplateOptions checksum(String checksum) {
this.queryParameters.replaceValues("checksum", ImmutableSet.of(checksum));
return this;
}
/**
* true if the template or its derivatives are extractable; default is true
*/
public RegisterTemplateOptions isExtractable(boolean isExtractable) {
this.queryParameters.replaceValues("isextractable", ImmutableSet.of(isExtractable + ""));
return this;
}
/**
* true if this template is a featured template, false otherwise
*/
public RegisterTemplateOptions isFeatured(boolean isFeatured) {
this.queryParameters.replaceValues("isfeatured", ImmutableSet.of(isFeatured + ""));
return this;
}
/**
* true if the template is available to all accounts; default is true
*/
public RegisterTemplateOptions isPublic(boolean isPublic) {
this.queryParameters.replaceValues("ispublic", ImmutableSet.of(isPublic + ""));
return this;
}
/**
* true if the template supports the password reset feature; default is false
*/
public RegisterTemplateOptions passwordEnabled(boolean passwordEnabled) {
this.queryParameters.replaceValues("passwordenabled", ImmutableSet.of(passwordEnabled + ""));
return this;
}
/**
* true if this template requires HVM
*/
public RegisterTemplateOptions requiresHVM(boolean requiresHVM) {
this.queryParameters.replaceValues("requireshvm", ImmutableSet.of(requiresHVM + ""));
return this;
}
public static class Builder {
public static RegisterTemplateOptions bits(int bits) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.bits(bits);
}
public static RegisterTemplateOptions checksum(String checksum) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.checksum(checksum);
}
public static RegisterTemplateOptions isExtractable(boolean isExtractable) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.isExtractable(isExtractable);
}
public static RegisterTemplateOptions isFeatured(boolean isFeatured) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.isFeatured(isFeatured);
}
public static RegisterTemplateOptions isPublic(boolean isPublic) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.isPublic(isPublic);
}
public static RegisterTemplateOptions passwordEnabled(boolean passwordEnabled) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.passwordEnabled(passwordEnabled);
}
public static RegisterTemplateOptions requiresHVM(boolean requiresHVM) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return options.requiresHVM(requiresHVM);
}
/**
* @see AccountInDomainOptions#accountInDomain
*/
public static RegisterTemplateOptions accountInDomain(String account, long domain) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return (RegisterTemplateOptions)options.accountInDomain(account, domain);
}
/**
* @see AccountInDomainOptions#domainId
*/
public static RegisterTemplateOptions domainId(long domainId) {
RegisterTemplateOptions options = new RegisterTemplateOptions();
return (RegisterTemplateOptions)options.domainId(domainId);
}
}
}

View File

@ -0,0 +1,116 @@
/**
* 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.cloudstack.options;
import com.google.common.collect.ImmutableSet;
import org.jclouds.cloudstack.domain.Template;
import org.jclouds.http.options.BaseHttpRequestOptions;
/**
* Options used to control how a template should be updated.
*
* @see <a
* href="http://download.cloud.com/releases/2.2.8/api/user/updateTemplate.html"
* />
* @author Richard Downer
*/
public class UpdateTemplateOptions extends BaseHttpRequestOptions {
/**
* true if image is bootable, false otherwise
*/
public UpdateTemplateOptions bootable(boolean bootable) {
this.queryParameters.replaceValues("bootable", ImmutableSet.of(bootable + ""));
return this;
}
/**
* the display text of the image
*/
public UpdateTemplateOptions displayText(String displayText) {
this.queryParameters.replaceValues("displaytext", ImmutableSet.of(displayText));
return this;
}
/**
* the format for the image
*/
public UpdateTemplateOptions format(Template.Format format) {
this.queryParameters.replaceValues("format", ImmutableSet.of(format + ""));
return this;
}
/**
* the name of the image file
*/
public UpdateTemplateOptions name(String name) {
this.queryParameters.replaceValues("name", ImmutableSet.of(name));
return this;
}
/**
* the ID of the OS type that best represents the OS of this image.
*/
public UpdateTemplateOptions osTypeId(long osTypeId) {
this.queryParameters.replaceValues("ostypeid", ImmutableSet.of(osTypeId + ""));
return this;
}
/**
* true if the image supports the password reset feature; default is false
*/
public UpdateTemplateOptions passwordEnabled(boolean passwordEnabled) {
this.queryParameters.replaceValues("passwordenabled", ImmutableSet.of(passwordEnabled + ""));
return this;
}
public static class Builder {
public static UpdateTemplateOptions bootable(boolean bootable) {
UpdateTemplateOptions options = new UpdateTemplateOptions();
return options.bootable(bootable);
}
public static UpdateTemplateOptions displayText(String displayText) {
UpdateTemplateOptions options = new UpdateTemplateOptions();
return options.displayText(displayText);
}
public static UpdateTemplateOptions format(Template.Format format) {
UpdateTemplateOptions options = new UpdateTemplateOptions();
return options.format(format);
}
public static UpdateTemplateOptions name(String name) {
UpdateTemplateOptions options = new UpdateTemplateOptions();
return options.name(name);
}
public static UpdateTemplateOptions osTypeId(long osTypeId) {
UpdateTemplateOptions options = new UpdateTemplateOptions();
return options.osTypeId(osTypeId);
}
public static UpdateTemplateOptions passwordEnabled(boolean passwordEnabled) {
UpdateTemplateOptions options = new UpdateTemplateOptions();
return options.passwordEnabled(passwordEnabled);
}
}
}

View File

@ -0,0 +1,108 @@
/**
* 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.cloudstack.options;
import com.google.common.base.Functions;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Iterables;
import org.jclouds.http.options.BaseHttpRequestOptions;
/**
* Options used to control how a template should be updated.
*
* @see <a
* href="http://download.cloud.com/releases/2.2.8/api/user/updateTemplate.html"
* />
* @author Richard Downer
*/
public class UpdateTemplatePermissionsOptions extends BaseHttpRequestOptions {
/**
* a list of accounts. If specified, "op" parameter has to be passed in.
*/
public UpdateTemplatePermissionsOptions accounts(Iterable<Long> accounts) {
this.queryParameters.replaceValues("accounts", Iterables.transform(accounts, Functions.toStringFunction()));
return this;
}
/**
* true if the template/iso is extractable, false other wise. Can be set only by root admin
*/
public UpdateTemplatePermissionsOptions isExtractable(boolean isExtractable) {
this.queryParameters.replaceValues("isextractable", ImmutableSet.of(isExtractable + ""));
return this;
}
/**
* true for featured template/iso, false otherwise
*/
public UpdateTemplatePermissionsOptions isFeatured(boolean isFeatured) {
this.queryParameters.replaceValues("isfeatured", ImmutableSet.of(isFeatured + ""));
return this;
}
/**
* true for public template/iso, false for private templates/isos
*/
public UpdateTemplatePermissionsOptions isPublic(boolean isPublic) {
this.queryParameters.replaceValues("ispublic", ImmutableSet.of(isPublic + ""));
return this;
}
/**
* permission operator (add, remove, reset)
*/
public UpdateTemplatePermissionsOptions op(Operation op) {
this.queryParameters.replaceValues("op", ImmutableSet.of(op + ""));
return this;
}
public enum Operation {
add, remove, reset
}
public static class Builder {
public static UpdateTemplatePermissionsOptions accounts(Iterable<Long> accounts) {
UpdateTemplatePermissionsOptions options = new UpdateTemplatePermissionsOptions();
return options.accounts(accounts);
}
public static UpdateTemplatePermissionsOptions isExtractable(boolean isExtractable) {
UpdateTemplatePermissionsOptions options = new UpdateTemplatePermissionsOptions();
return options.isExtractable(isExtractable);
}
public static UpdateTemplatePermissionsOptions isFeatured(boolean isFeatured) {
UpdateTemplatePermissionsOptions options = new UpdateTemplatePermissionsOptions();
return options.isFeatured(isFeatured);
}
public static UpdateTemplatePermissionsOptions isPublic(boolean isPublic) {
UpdateTemplatePermissionsOptions options = new UpdateTemplatePermissionsOptions();
return options.isPublic(isPublic);
}
public static UpdateTemplatePermissionsOptions op(Operation op) {
UpdateTemplatePermissionsOptions options = new UpdateTemplatePermissionsOptions();
return options.op(op);
}
}
}

View File

@ -21,19 +21,35 @@ package org.jclouds.cloudstack.features;
import java.io.IOException; import java.io.IOException;
import java.lang.reflect.Method; import java.lang.reflect.Method;
import com.google.common.collect.ImmutableSet;
import org.jclouds.cloudstack.domain.Template;
import org.jclouds.cloudstack.domain.TemplateFilter; import org.jclouds.cloudstack.domain.TemplateFilter;
import org.jclouds.cloudstack.domain.TemplateMetadata;
import org.jclouds.cloudstack.options.AccountInDomainOptions;
import org.jclouds.cloudstack.options.CreateTemplateOptions;
import org.jclouds.cloudstack.options.DeleteTemplateOptions;
import org.jclouds.cloudstack.options.ExtractTemplateOptions;
import org.jclouds.cloudstack.options.ListTemplatesOptions; import org.jclouds.cloudstack.options.ListTemplatesOptions;
import org.jclouds.cloudstack.options.RegisterTemplateOptions;
import org.jclouds.cloudstack.options.UpdateTemplateOptions;
import org.jclouds.cloudstack.options.UpdateTemplatePermissionsOptions;
import org.jclouds.functions.IdentityFunction; import org.jclouds.functions.IdentityFunction;
import org.jclouds.http.HttpRequest; import org.jclouds.http.HttpRequest;
import org.jclouds.http.functions.ParseFirstJsonValueNamed; import org.jclouds.http.functions.ParseFirstJsonValueNamed;
import org.jclouds.http.functions.ReleasePayloadAndReturn;
import org.jclouds.http.functions.UnwrapOnlyJsonValue;
import org.jclouds.rest.functions.MapHttp4xxCodesToExceptions;
import org.jclouds.rest.functions.ReturnEmptySetOnNotFoundOr404; import org.jclouds.rest.functions.ReturnEmptySetOnNotFoundOr404;
import org.jclouds.rest.functions.ReturnNullOnNotFoundOr404; import org.jclouds.rest.functions.ReturnNullOnNotFoundOr404;
import org.jclouds.rest.functions.ReturnVoidOnNotFoundOr404;
import org.jclouds.rest.internal.RestAnnotationProcessor; import org.jclouds.rest.internal.RestAnnotationProcessor;
import org.testng.annotations.Test; import org.testng.annotations.Test;
import com.google.common.base.Functions; import com.google.common.base.Functions;
import com.google.inject.TypeLiteral; import com.google.inject.TypeLiteral;
import javax.annotation.concurrent.Immutable;
/** /**
* Tests behavior of {@code TemplateAsyncClient} * Tests behavior of {@code TemplateAsyncClient}
* *
@ -43,6 +59,143 @@ import com.google.inject.TypeLiteral;
// surefire // surefire
@Test(groups = "unit", testName = "TemplateAsyncClientTest") @Test(groups = "unit", testName = "TemplateAsyncClientTest")
public class TemplateAsyncClientTest extends BaseCloudStackAsyncClientTest<TemplateAsyncClient> { public class TemplateAsyncClientTest extends BaseCloudStackAsyncClientTest<TemplateAsyncClient> {
public void testCreateTemplate() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("createTemplate", TemplateMetadata.class, CreateTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, TemplateMetadata.builder().name("thename").osTypeId(10).displayText("description").build());
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=createTemplate&name=thename&ostypeid=10&displaytext=description HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testCreateTemplateOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("createTemplate", TemplateMetadata.class, CreateTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, TemplateMetadata.builder().name("thename").osTypeId(10).displayText("description").build(), CreateTemplateOptions.Builder.bits(32).isFeatured(true).isPublic(true).passwordEnabled(true).requiresHVM(true).snapshotId(11).volumeId(12));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=createTemplate&bits=32&isfeatured=true&ispublic=true&passwordenabled=true&requireshvm=true&snapshotid=11&volumeid=12&name=thename&ostypeid=10&displaytext=description HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testRegisterTemplate() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("registerTemplate", TemplateMetadata.class, String.class, String.class, String.class, long.class, RegisterTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, TemplateMetadata.builder().name("thename").osTypeId(10).displayText("description").build(), Template.Format.QCOW2, "xen", "http://example.com/", 20);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=registerTemplate&hypervisor=xen&format=QCOW2&url=http%3A%2F%2Fexample.com%2F&zoneid=20&name=thename&ostypeid=10&displaytext=description HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ParseFirstJsonValueNamed.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testRegisterTemplateOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("registerTemplate", TemplateMetadata.class, String.class, String.class, String.class, long.class, RegisterTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, TemplateMetadata.builder().name("thename").osTypeId(10).displayText("description").build(), Template.Format.QCOW2, "xen", "http://example.com/", 20,
RegisterTemplateOptions.Builder.accountInDomain("mydomain", 3).bits(32).checksum("ABC").isExtractable(true).isFeatured(true).isPublic(true).passwordEnabled(true).requiresHVM(true));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=registerTemplate&hypervisor=xen&format=QCOW2&url=http%3A%2F%2Fexample.com%2F&zoneid=20&account=mydomain&domainid=3&bits=32&checksum=ABC&isextractable=true&isfeatured=true&ispublic=true&passwordenabled=true&requireshvm=true&name=thename&ostypeid=10&displaytext=description HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ParseFirstJsonValueNamed.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testUpdateTemplate() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("updateTemplate", long.class, UpdateTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=updateTemplate&id=17 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ParseFirstJsonValueNamed.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testUpdateTemplateOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("updateTemplate", long.class, UpdateTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17, UpdateTemplateOptions.Builder.bootable(true).displayText("description").format(Template.Format.VHD).name("thename").osTypeId(12).passwordEnabled(true));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=updateTemplate&id=17&bootable=true&displaytext=description&format=VHD&name=thename&ostypeid=12&passwordenabled=true HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ParseFirstJsonValueNamed.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testCopyTemplate() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("copyTemplateToZone", long.class, long.class, long.class);
HttpRequest httpRequest = processor.createRequest(method, 17, 18, 19);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=copyTemplate&id=17&destzoneid=19&sourcezoneid=18 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testDeleteTemplate() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("deleteTemplate", long.class, DeleteTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=deleteTemplate&id=17 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ReleasePayloadAndReturn.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, ReturnVoidOnNotFoundOr404.class);
checkFilters(httpRequest);
}
public void testDeleteTemplateOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("deleteTemplate", long.class, DeleteTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17, DeleteTemplateOptions.Builder.zoneId(8));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=deleteTemplate&id=17&zoneid=8 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ReleasePayloadAndReturn.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, ReturnVoidOnNotFoundOr404.class);
checkFilters(httpRequest);
}
public void testListTemplates() throws SecurityException, NoSuchMethodException, IOException { public void testListTemplates() throws SecurityException, NoSuchMethodException, IOException {
Method method = TemplateAsyncClient.class.getMethod("listTemplates"); Method method = TemplateAsyncClient.class.getMethod("listTemplates");
HttpRequest httpRequest = processor.createRequest(method); HttpRequest httpRequest = processor.createRequest(method);
@ -84,11 +237,11 @@ public class TemplateAsyncClientTest extends BaseCloudStackAsyncClientTest<Templ
public void testGetTemplate() throws SecurityException, NoSuchMethodException, IOException { public void testGetTemplate() throws SecurityException, NoSuchMethodException, IOException {
Method method = TemplateAsyncClient.class.getMethod("getTemplateInZone", long.class, long.class); Method method = TemplateAsyncClient.class.getMethod("getTemplateInZone", long.class, long.class);
HttpRequest httpRequest = processor.createRequest(method, 1, 5); HttpRequest httpRequest = processor.createRequest(method, 5, 1);
assertRequestLineEquals( assertRequestLineEquals(
httpRequest, httpRequest,
"GET http://localhost:8080/client/api?response=json&command=listTemplates&templatefilter=executable&zoneid=1&id=5 HTTP/1.1"); "GET http://localhost:8080/client/api?response=json&command=listTemplates&templatefilter=executable&id=5&zoneid=1 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n"); assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false); assertPayloadEquals(httpRequest, null, null, false);
@ -101,6 +254,96 @@ public class TemplateAsyncClientTest extends BaseCloudStackAsyncClientTest<Templ
} }
public void testUpdateTemplatePermissions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("updateTemplatePermissions", long.class, UpdateTemplatePermissionsOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=updateTemplatePermissions&id=17 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ReleasePayloadAndReturn.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testUpdateTemplatePermissionsOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("updateTemplatePermissions", long.class, UpdateTemplatePermissionsOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17, UpdateTemplatePermissionsOptions.Builder.accounts(ImmutableSet.of(5L, 6L)).isExtractable(true).isFeatured(true).isPublic(true).op(UpdateTemplatePermissionsOptions.Operation.add));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=updateTemplatePermissions&id=17&accounts=5,6&isextractable=true&isfeatured=true&ispublic=true&op=add HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, ReleasePayloadAndReturn.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testListTemplatePermissions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("listTemplatePermissions", long.class, AccountInDomainOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=listTemplatePermissions&id=17 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testListTemplatePermissionsOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("listTemplatePermissions", long.class, AccountInDomainOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 17, AccountInDomainOptions.Builder.accountInDomain("fred", 8));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=listTemplatePermissions&id=17&account=fred&domainid=8 HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testExtractTemplate() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("extractTemplate", long.class, Template.ExtractMode.class, long.class, ExtractTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 3, Template.ExtractMode.HTTP_DOWNLOAD, 5);
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=extractTemplate&id=3&zoneid=5&mode=HTTP_DOWNLOAD HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
public void testExtractTemplateOptions() throws NoSuchMethodException {
Method method = TemplateAsyncClient.class.getMethod("extractTemplate", long.class, Template.ExtractMode.class, long.class, ExtractTemplateOptions[].class);
HttpRequest httpRequest = processor.createRequest(method, 3, Template.ExtractMode.HTTP_DOWNLOAD, 5, ExtractTemplateOptions.Builder.url("http://example.com/"));
assertRequestLineEquals(httpRequest, "GET http://localhost:8080/client/api?response=json&command=extractTemplate&id=3&zoneid=5&mode=HTTP_DOWNLOAD&url=http%3A%2F%2Fexample.com%2F HTTP/1.1");
assertNonPayloadHeadersEqual(httpRequest, "Accept: application/json\n");
assertPayloadEquals(httpRequest, null, null, false);
assertResponseParserClassEquals(method, httpRequest, UnwrapOnlyJsonValue.class);
assertSaxResponseParserClassEquals(method, null);
assertExceptionParserClassEquals(method, MapHttp4xxCodesToExceptions.class);
checkFilters(httpRequest);
}
@Override @Override
protected TypeLiteral<RestAnnotationProcessor<TemplateAsyncClient>> createTypeLiteral() { protected TypeLiteral<RestAnnotationProcessor<TemplateAsyncClient>> createTypeLiteral() {
return new TypeLiteral<RestAnnotationProcessor<TemplateAsyncClient>>() { return new TypeLiteral<RestAnnotationProcessor<TemplateAsyncClient>>() {

View File

@ -46,7 +46,7 @@ public class TemplateClientLiveTest extends BaseCloudStackClientLiveTest {
Template newDetails = Iterables.getOnlyElement(client.getTemplateClient().listTemplates( Template newDetails = Iterables.getOnlyElement(client.getTemplateClient().listTemplates(
zoneId(template.getZoneId()).id(template.getId()))); zoneId(template.getZoneId()).id(template.getId())));
assertEquals(template, newDetails); assertEquals(template, newDetails);
assertEquals(template, client.getTemplateClient().getTemplateInZone(template.getZoneId(), template.getId())); assertEquals(template, client.getTemplateClient().getTemplateInZone(template.getId(), template.getZoneId()));
assert template.getId() > 0 : template; assert template.getId() > 0 : template;
assert template.getName() != null : template; assert template.getName() != null : template;
assert template.getDisplayText() != null : template; assert template.getDisplayText() != null : template;