Package com.google.appengine.api.labs.modules

Source Code of com.google.appengine.api.labs.modules.ModulesServiceImpl

package com.google.appengine.api.labs.modules;

import com.google.appengine.api.labs.modules.ModulesServicePb.GetDefaultVersionRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetDefaultVersionResponse;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetHostnameRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetHostnameResponse;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetModulesRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetModulesResponse;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetNumInstancesRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetNumInstancesResponse;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetVersionsRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.GetVersionsResponse;
import com.google.appengine.api.labs.modules.ModulesServicePb.ModulesServiceError.ErrorCode;
import com.google.appengine.api.labs.modules.ModulesServicePb.SetNumInstancesRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.StartModuleRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.StartModuleResponse;
import com.google.appengine.api.labs.modules.ModulesServicePb.StopModuleRequest;
import com.google.appengine.api.labs.modules.ModulesServicePb.StopModuleResponse;
import com.google.apphosting.api.ApiProxy;
import com.google.apphosting.api.ApiProxy.Environment;
import com.google.common.base.Pair;
import com.google.common.base.Splitter;
import com.google.common.collect.Sets;
import com.google.protobuf.InvalidProtocolBufferException;
import com.google.protobuf.Message;

import java.util.List;
import java.util.Map;
import java.util.Set;

class ModulesServiceImpl implements ModulesService {
  protected static final String PACKAGE = "modules";

  /**
   * Environment attribute key where the instance id is stored.
   *
   * @see ModulesService#getCurrentInstanceId()
   */
  private static final String INSTANCE_ID_ENV_ATTRIBUTE = "com.google.appengine.instance.id";

  private Pair<String, String> getCurrentModuleAndVersion() {
    Environment env = ApiProxy.getCurrentEnvironment();
    String majorVersion = Splitter.on('.').split(env.getVersionId()).iterator().next();
    if (majorVersion.contains(":")) {
      List<String> result = Splitter.on(':').splitToList(majorVersion);
      return Pair.of(result.get(0), result.get(1));
    } else {
      return Pair.of("default", majorVersion);
    }
  }

  @Override
  public String getCurrentModule() {
    return getCurrentModuleAndVersion().first;
  }

  @Override
  public String getCurrentVersion() {
    return getCurrentModuleAndVersion().second;
  }

  private static Map<String, Object> getThreadLocalAttributes() {
    return ApiProxy.getCurrentEnvironment().getAttributes();
  }

  @Override
  public String getCurrentInstanceId() {
    Map<String, Object> env = getThreadLocalAttributes();
    if (!env.containsKey(INSTANCE_ID_ENV_ATTRIBUTE)) {
      throw new ModulesException("No valid instance id for this instance.");
    }
    String instanceId = (String) getThreadLocalAttributes().get(INSTANCE_ID_ENV_ATTRIBUTE);
    if (instanceId == null) {
      throw new ModulesException("No valid instance id for this instance.");
    }
    return instanceId;
  }

  private static void makeSyncCall(String method, Message.Builder request, Message.Builder response)
      throws ModulesException {
    byte[] responseBytes;
    try {
      responseBytes = ApiProxy.makeSyncCall(PACKAGE, method, request.build().toByteArray());
      response.mergeFrom(responseBytes);
    } catch (ApiProxy.ApplicationException e) {
      switch(ErrorCode.valueOf(e.getApplicationError())) {
        case INVALID_MODULE:
          throw new InvalidModuleException("Given module is not known.");
        case INVALID_VERSION:
          throw new InvalidVersionException("Given module version is not known.");
        case INVALID_INSTANCES:
          throw new InvalidInstanceException("Given instances value is invalid.");
        case UNEXPECTED_STATE:
          if (method.equals("StartModule")) {
            throw new ModuleAlreadyStartedException("Given module version is already started.");
          } else if (method.equals("StopModule")) {
            throw new ModuleAlreadyStoppedException("Given module version is already stopped.");
          }
        default:
          throw new ModulesException("Unknown error occurred.");
      }
    } catch (InvalidProtocolBufferException e) {
      throw new RuntimeException("Internal logic error: Response PB could not be parsed.", e);
    }
  }

  @Override
  public Set<String> getModules() {
    GetModulesResponse.Builder response = GetModulesResponse.newBuilder();
    makeSyncCall("GetModules", GetModulesRequest.newBuilder(), response);
    return Sets.newHashSet(response.getModuleList());
  }

  @Override
  public Set<String> getVersions(String module) {
    GetVersionsRequest.Builder request = GetVersionsRequest.newBuilder();
    request.setModule(module);
    GetVersionsResponse.Builder response = GetVersionsResponse.newBuilder();
    makeSyncCall("GetVersions", request, response);
    return Sets.newHashSet(response.getVersionList());
  }

  @Override
  public String getDefaultVersion(String module) {
    GetDefaultVersionRequest.Builder request = GetDefaultVersionRequest.newBuilder();
    request.setModule(module);
    GetDefaultVersionResponse.Builder response = GetDefaultVersionResponse.newBuilder();
    makeSyncCall("GetDefaultVersion", request, response);
    return response.getVersion();
  }

  @Override
  public long getNumInstances(String module, String version) {
    GetNumInstancesRequest.Builder request = GetNumInstancesRequest.newBuilder();
    request.setModule(module);
    request.setVersion(version);
    GetNumInstancesResponse.Builder response = GetNumInstancesResponse.newBuilder();
    makeSyncCall("GetNumInstances", request, response);
    return response.getInstances();
  }

  @Override
  public void setNumInstances(String module, String version, long instances) {
    SetNumInstancesRequest.Builder request = SetNumInstancesRequest.newBuilder();
    request.setModule(module);
    request.setVersion(version);
    request.setInstances(instances);
    makeSyncCall("SetNumInstances", request, SetNumInstancesRequest.newBuilder());
  }

  @Override
  public void startModule(String module, String version) {
    StartModuleRequest.Builder request = StartModuleRequest.newBuilder();
    request.setModule(module);
    request.setVersion(version);
    makeSyncCall("StartModule", request, StartModuleResponse.newBuilder());
  }

  @Override
  public void stopModule(String module, String version) {
    StopModuleRequest.Builder request = StopModuleRequest.newBuilder();
    request.setModule(module);
    request.setVersion(version);
    makeSyncCall("StopModule", request, StopModuleResponse.newBuilder());
  }

  private String getHostname(GetHostnameRequest.Builder request) {
    GetHostnameResponse.Builder response = GetHostnameResponse.newBuilder();
    makeSyncCall("GetHostname", request, response);
    return response.getHostname();
  }

  @Override
  public String getModuleHostname(String module, String version) {
    GetHostnameRequest.Builder request = GetHostnameRequest.newBuilder();
    request.setModule(module);
    request.setVersion(version);
    return getHostname(request);
  }

  @Override
  public String getModuleHostname(String module, String version, int instance) {
    GetHostnameRequest.Builder request = GetHostnameRequest.newBuilder();
    request.setModule(module);
    request.setVersion(version);
    request.setInstance(Integer.toString(instance));
    return getHostname(request);
  }

  ModulesServiceImpl() { }
}
TOP

Related Classes of com.google.appengine.api.labs.modules.ModulesServiceImpl

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.