Handle proxy object situation in dispatching API command

This commit is contained in:
Kelven Yang 2013-01-16 11:28:09 -08:00
parent 339c09bdef
commit 4c1257bf18
3 changed files with 36 additions and 17 deletions

View File

@ -65,6 +65,7 @@ import com.cloud.user.AccountManager;
import com.cloud.user.UserContext;
import com.cloud.utils.DateUtil;
import com.cloud.utils.ReflectUtil;
import com.cloud.utils.component.ComponentContext;
import com.cloud.utils.exception.CSExceptionErrorCode;
import com.cloud.utils.exception.CloudRuntimeException;
@ -324,7 +325,9 @@ public class ApiDispatcher {
public static void processParameters(BaseCmd cmd, Map<String, String> params) {
List<Object> entitiesToAccess = new ArrayList<Object>();
Map<String, Object> unpackedParams = cmd.unpackParams(params);
cmd = ComponentContext.getTargetObject(cmd);
if (cmd instanceof BaseListCmd) {
Object pageSizeObj = unpackedParams.get(ApiConstants.PAGE_SIZE);
Long pageSize = null;

View File

@ -106,6 +106,7 @@ import org.apache.http.protocol.ResponseContent;
import org.apache.http.protocol.ResponseDate;
import org.apache.http.protocol.ResponseServer;
import org.apache.log4j.Logger;
import org.springframework.aop.framework.Advised;
import org.springframework.stereotype.Component;
import com.cloud.api.response.ApiResponseSerializer;
@ -348,6 +349,7 @@ public class ApiServer implements HttpRequestHandler {
cmdObj.configure();
cmdObj.setFullUrlParams(paramMap);
cmdObj.setResponseType(responseType);
// This is where the command is either serialized, or directly dispatched
response = queueCommand(cmdObj, paramMap);
buildAuditTrail(auditTrailSb, command[0], response);
@ -404,15 +406,17 @@ public class ApiServer implements HttpRequestHandler {
UserContext ctx = UserContext.current();
Long callerUserId = ctx.getCallerUserId();
Account caller = ctx.getCaller();
BaseCmd realCmdObj = ComponentContext.getTargetObject(cmdObj);
// Queue command based on Cmd super class:
// BaseCmd: cmd is dispatched to ApiDispatcher, executed, serialized and returned.
// BaseAsyncCreateCmd: cmd params are processed and create() is called, then same workflow as BaseAsyncCmd.
// BaseAsyncCmd: cmd is processed and submitted as an AsyncJob, job related info is serialized and returned.
if (cmdObj instanceof BaseAsyncCmd) {
if (realCmdObj instanceof BaseAsyncCmd) {
Long objectId = null;
String objectUuid = null;
if (cmdObj instanceof BaseAsyncCreateCmd) {
if (realCmdObj instanceof BaseAsyncCreateCmd) {
BaseAsyncCreateCmd createCmd = (BaseAsyncCreateCmd) cmdObj;
_dispatcher.dispatchCreateCmd(createCmd, params);
objectId = createCmd.getEntityId();
@ -472,19 +476,19 @@ public class ApiServer implements HttpRequestHandler {
// if the command is of the listXXXCommand, we will need to also return the
// the job id and status if possible
// For those listXXXCommand which we have already created DB views, this step is not needed since async job is joined in their db views.
if (cmdObj instanceof BaseListCmd && !(cmdObj instanceof ListVMsCmd) && !(cmdObj instanceof ListRoutersCmd)
&& !(cmdObj instanceof ListSecurityGroupsCmd)
&& !(cmdObj instanceof ListTagsCmd)
&& !(cmdObj instanceof ListEventsCmd)
&& !(cmdObj instanceof ListVMGroupsCmd)
&& !(cmdObj instanceof ListProjectsCmd)
&& !(cmdObj instanceof ListProjectAccountsCmd)
&& !(cmdObj instanceof ListProjectInvitationsCmd)
&& !(cmdObj instanceof ListHostsCmd)
&& !(cmdObj instanceof ListVolumesCmd)
&& !(cmdObj instanceof ListUsersCmd)
&& !(cmdObj instanceof ListAccountsCmd)
&& !(cmdObj instanceof ListStoragePoolsCmd)
if (realCmdObj instanceof BaseListCmd && !(realCmdObj instanceof ListVMsCmd) && !(realCmdObj instanceof ListRoutersCmd)
&& !(realCmdObj instanceof ListSecurityGroupsCmd)
&& !(realCmdObj instanceof ListTagsCmd)
&& !(realCmdObj instanceof ListEventsCmd)
&& !(realCmdObj instanceof ListVMGroupsCmd)
&& !(realCmdObj instanceof ListProjectsCmd)
&& !(realCmdObj instanceof ListProjectAccountsCmd)
&& !(realCmdObj instanceof ListProjectInvitationsCmd)
&& !(realCmdObj instanceof ListHostsCmd)
&& !(realCmdObj instanceof ListVolumesCmd)
&& !(realCmdObj instanceof ListUsersCmd)
&& !(realCmdObj instanceof ListAccountsCmd)
&& !(realCmdObj instanceof ListStoragePoolsCmd)
) {
buildAsyncListResponse((BaseListCmd) cmdObj, caller);
}

View File

@ -131,6 +131,18 @@ public class ComponentContext implements ApplicationContextAware {
return instance.getClass();
}
public static <T> T getTargetObject(Object instance) {
if(instance instanceof Advised) {
try {
return (T)((Advised)instance).getTargetSource().getTarget();
} catch (Exception e) {
return (T)instance;
}
}
return (T)instance;
}
public static <T> T inject(Class<T> clz) {
T instance = s_appContext.getAutowireCapableBeanFactory().createBean(clz);
return inject(instance);