0

Context: In my organization, we are using google's services for email. In the UI, we let user change their email alias, and delete their email alias. They can only have one email alias.

I am using Directory API or ADMIN SDK in Spring boot to insert/delete alias.

The Problem: I am inserting an alias using, directoryService.users().aliases().insert(primaryEmailId, alias).execute(); It takes 1 minutes for a new alias to reflect.

Now if a user wants to delete/change the email alias within one minute of adding up a new alias, the request for deletion will fail at the backend since the newly inserted alias has not been reflected yet. As a result, a newest alias will be created but the old one will not get deleted.

How to tackle this? One way to fix this is to disable edit button for 1 minute in the UI, but this is not a good user experience.

So are there any other ways?

Insert Alias METHOD:

  Alias alias = new Alias();
    alias.setAlias(newEmailAlias);
    try {
        directoryService.users().aliases().insert(primaryEmailId, alias).execute();
    } catch (IOException e) {
        e.printStackTrace();
    }

GET ALIAS METHOD:

public List<String> getAliases(String primaryEmailId) {
    User user = null;
    try {
        user = directoryService.users().get(primaryEmailId).execute();
    } catch (IOException e) {
        e.printStackTrace();
    }
    return user.getAliases();
}

Delete alias:

    try {
        directoryService.users().aliases().delete(primaryEmailId, emailAlias).execute();
    } catch (IOException e) {
        e.printStackTrace();
    }

Adding some more details on how i am generating directory object. I am using a service account to get the service object:

private static final String APPLICATION_NAME = "Google Aliases List";
private static final List<String> SCOPES = Collections.singletonList(DirectoryScopes.ADMIN_DIRECTORY_USER);
private static final String CREDENTIALS_FILE_PATH = "/gmail-api-randonnum-randomletter.json";

@Bean
public Directory directoryService() {
    HttpTransport httpTransport = null;
    Directory service = null;
    try {
        httpTransport = GoogleNetHttpTransport.newTrustedTransport();
        JsonFactory jsonFactory = GsonFactory.getDefaultInstance();
        HttpRequestInitializer requestInitializer = new HttpCredentialsAdapter(getCredentials());
        service = new Directory.Builder(httpTransport, jsonFactory, requestInitializer)
                .setApplicationName(APPLICATION_NAME)
                .build();
    } catch (GeneralSecurityException | IOException e) {
        System.out.println(e);
    }
    return service;
}

private GoogleCredentials getCredentials() throws IOException {
    // Load client secrets.
    InputStream in = GoogleDirectoryAPIConfig.class.getResourceAsStream(CREDENTIALS_FILE_PATH);
    if (in == null) {
        throw new FileNotFoundException("Resource not found: " + CREDENTIALS_FILE_PATH);
    }
    return GoogleCredentials.fromStream(in).createScoped(SCOPES).createDelegated("admin@email.com");
}
Avinash Kharche
  • 411
  • 9
  • 25
  • I cannot reproduce this behaviour. It's nowhere close to 1 minute for the alias to be inserted after executing this. When you say `It takes 1 minutes for a new alias to reflect`, where are you looking? What makes you think that's the case? – Iamblichus Mar 24 '21 at 08:55
  • @lamblichus, so the method execution for insert does not take 1 min time, it takes 1 min to get reflected in getAliases() call. So in scenario, if a user updates the email alias (A) again after inserting one (B) within 1 min, the backend wont be able to delete the B before inserting A. At the end, there will be 2 email alias instead of just one. – Avinash Kharche Mar 24 '21 at 20:09
  • That's not what I'm experiencing. If I [list aliases](https://developers.google.com/admin-sdk/directory/reference/rest/v1/users.aliases/list) right after inserting, the inserted alias is returned. Can you provide a minimal reproducible example? – Iamblichus Mar 25 '21 at 08:04
  • @lamblichus I am using service account for getting the Directory Object. Can you please take a look at the way i am inserting, getting email alias and creating directory object? I have added them in the question – Avinash Kharche Mar 25 '21 at 20:30
  • I don't see anything strange in your code. When you mention `UI`, do you mean one developed by you? In this case, this could be a problem of bringing the data to your UI? If you call `aliases.list` directly in the API right after inserting it via `aliases.insert`, is the inserted alias returned? – Iamblichus Mar 26 '21 at 09:13
  • @lamblichus UI is there but i am testing with postman and unit testing only. If I call 'aliases.list' diretly in the API after insert, it does not return the inserted alias. That is precisely the problem. Have you used service account to call the api? If you dont mind can you please test with service account if not already done. May be using service account causing this. – Avinash Kharche Mar 26 '21 at 15:53
  • Is this the service account by itself or with domain-wide delegation, impersonating a regular user? – Iamblichus Mar 26 '21 at 16:29
  • domain-wide delegation. Also, i am using createDelegated("admin@email.com") admin email id when creating GoogleCredential – Avinash Kharche Mar 26 '21 at 16:51
  • I get the same behaviour when using the service account. In fact, if I call `aliases.insert` and `aliases.list` in the same script, with just 1 second between both calls, the inserted alias is listed. I'd consider contacting [Workspace support](https://support.google.com/a/answer/1047213?authuser=0), since this behaviour doesn't seem to be reproducible outside your project/domain. – Iamblichus Mar 29 '21 at 10:15
  • thank you for your help. I'll contact workspace support. Also, one another team in my organization faces the same issue. – Avinash Kharche Mar 29 '21 at 15:40

0 Answers0