0

我正嘗試使用Google Cloud SDK在Java中以編程方式創建服務帳戶密鑰,以便在App/Compute上運行的應用程序發動機。 This question與我的類似,但它在App引擎上運行,所以我不能使用相同的代碼,因爲它使用App Engine API中的類。如何在不下載Google雲Java SDK的情況下對服務帳戶進行身份驗證(不在App Engine上)

相關代碼如下。我的問題是AppIdentityCredential是AppEngine API的一部分,因此無法在此處使用。我可以通過參數傳遞什麼?新的Builder()方法中的第三個參數需要HttpRequestInitializer,但我不明白這個接口的實現是否應該通過。任何幫助表示讚賞。

import com.google.api.services.iam.v1.Iam; 
import com.google.api.services.iam.v1.model.CreateServiceAccountKeyRequest; 
import com.google.api.services.iam.v1.model.ServiceAccountKey; 

AppIdentityCredential credential = new AppIdentityCredential(
      Arrays.asList("https://www.googleapis.com/auth/cloud-platform")); 
Iam iam = new Iam.Builder(httpTransport, JSON_FACTORY,credential) 
     .setApplicationName(APPLICATION_NAME).build(); 
ServiceAccountKey key = iam.projects().serviceAccounts().keys() 
    .create(SERVICE_ACCOUNT_RESOURCE_NAME, new CreateServiceAccountKeyRequest()).execute(); 

回答

1

您可以使用Application Default Credentials這將允許您使用相同的代碼來獲取基於該應用程序的運行環境的憑據。

例如,它允許您在系統上開發時使用您的gcloud account credentials。當代碼在Google Compute Engine或Google App Engine上運行時,代碼將自動使用關聯的服務帳戶憑據在API中進行身份驗證。您也可以使用GOOGLE_APPLICATION_CREDENTIALS環境變量覆蓋它,如果需要從JSON文件中加載憑據。

下面是一個工作示例,它爲現有服務帳戶創建一個新密鑰並進行打印。

import com.google.api.client.googleapis.auth.oauth2.GoogleCredential; 
import com.google.api.client.googleapis.javanet.GoogleNetHttpTransport; 
import com.google.api.client.http.HttpTransport; 
import com.google.api.client.json.JsonFactory; 
import com.google.api.client.json.jackson2.JacksonFactory; 
import com.google.api.services.iam.v1.Iam; 
import com.google.api.services.iam.v1.IamScopes; 
import com.google.api.services.iam.v1.model.CreateServiceAccountKeyRequest; 
import com.google.api.services.iam.v1.model.ServiceAccountKey; 
import java.io.IOException; 
import java.security.GeneralSecurityException; 
import java.util.ArrayList; 
import java.util.List; 

public class IamDemo { 
    /** Name of the application. */ 
    private static final String APPLICATION_NAME = "IamDemoJava"; 

    /** Project Name. */ 
    private static final String PROJECT_NAME = "MY_PROJECT_NAME"; 

    /** Name of the service account to create a new key for. */ 
    private static final String SERVICE_ACCOUNT_NAME = "dummy-sa"; 

    /** Full email address of the service account. */ 
    private static final String SERVICE_ACCOUNT_EMAIL = 
     SERVICE_ACCOUNT_NAME + "@" + PROJECT_NAME + ".iam.gserviceaccount.com"; 

    /** Full service account resource string expected by the IAM API. */ 
    private static final String SERVICE_ACCOUNT_RESOURCE_NAME = 
     "projects/" + PROJECT_NAME + "/serviceAccounts/" + SERVICE_ACCOUNT_EMAIL; 

    /** Global instance of the HTTP transport. */ 
    private static HttpTransport httpTransport; 

    /** Global instance of the JSON factory. */ 
    private static final JsonFactory JSON_FACTORY = JacksonFactory.getDefaultInstance(); 

    public static void main() throws IOException, GeneralSecurityException { 
    Iam iam = initIam(); 
    ServiceAccountKey key = createServiceAccountKey(iam); 

    // Print the key 
    System.out.println(key.toString()); 
    } 

    private static Iam initIam() throws IOException, GeneralSecurityException { 
    httpTransport = GoogleNetHttpTransport.newTrustedTransport(); 

    // Authenticate using Google Application Default Credentials. 
    GoogleCredential credential = GoogleCredential.getApplicationDefault(); 


    if (credential.createScopedRequired()) { 
     List<String> scopes = new ArrayList<>(); 
     // Enable full Cloud Platform scope. 
     scopes.add(IamScopes.CLOUD_PLATFORM); 
     credential = credential.createScoped(scopes); 
    } 

    // Create IAM API object associated with the authenticated transport. 
    return new Iam.Builder(httpTransport, JSON_FACTORY, credential) 
     .setApplicationName(APPLICATION_NAME) 
     .build(); 
    } 

    private static ServiceAccountKey createServiceAccountKey(Iam iam) 
     throws IOException, GeneralSecurityException { 
    CreateServiceAccountKeyRequest request = new CreateServiceAccountKeyRequest(); 

    // Customize the request parameters if needed 

    return iam.projects() 
     .serviceAccounts() 
     .keys() 
     .create(SERVICE_ACCOUNT_RESOURCE_NAME, request) 
     .execute(); 
    } 
} 
相關問題