All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.google.gerrit.server.account.CachedAccountDetails Maven / Gradle / Ivy

The newest version!
// Copyright (C) 2020 The Android Open Source Project
//
// Licensed 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 com.google.gerrit.server.account;

import com.google.auto.value.AutoValue;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableSet;
import com.google.gerrit.common.UsedAt;
import com.google.gerrit.entities.Account;
import com.google.gerrit.entities.NotifyConfig;
import com.google.gerrit.entities.ProjectWatchKey;
import com.google.gerrit.entities.converter.AccountProtoConverter;
import com.google.gerrit.entities.converter.CachedProjectWatchProtoConverter;
import com.google.gerrit.proto.Protos;
import com.google.gerrit.server.cache.proto.Cache;
import com.google.gerrit.server.cache.serialize.CacheSerializer;
import com.google.gerrit.server.cache.serialize.ObjectIdConverter;
import com.google.gerrit.server.config.CachedPreferences;
import java.util.Map;
import java.util.Optional;
import org.eclipse.jgit.lib.ObjectId;

/** Details of an account that are cached persistently in {@link AccountCache}. */
@UsedAt(UsedAt.Project.GOOGLE)
@AutoValue
public abstract class CachedAccountDetails {
  @AutoValue
  public abstract static class Key {
    public static Key create(Account.Id accountId, ObjectId id) {
      return new AutoValue_CachedAccountDetails_Key(accountId, id.copy());
    }

    /** Identifier of the account. */
    public abstract Account.Id accountId();

    /**
     * Git revision at which the account was loaded. Corresponds to a revision on the account ref
     * ({@code refs/users/}).
     */
    public abstract ObjectId id();

    /** Serializer used to read this entity from and write it to a persistent storage. */
    public enum Serializer implements CacheSerializer {
      INSTANCE;

      @Override
      public byte[] serialize(Key object) {
        return Protos.toByteArray(
            Cache.AccountKeyProto.newBuilder()
                .setAccountId(object.accountId().get())
                .setId(ObjectIdConverter.create().toByteString(object.id()))
                .build());
      }

      @Override
      public Key deserialize(byte[] in) {
        Cache.AccountKeyProto proto = Protos.parseUnchecked(Cache.AccountKeyProto.parser(), in);
        return Key.create(
            Account.id(proto.getAccountId()),
            ObjectIdConverter.create().fromByteString(proto.getId()));
      }
    }
  }

  /** Essential attributes of the account, such as name or registration time. */
  public abstract Account account();

  /** Projects that the user has configured to watch. */
  public abstract ImmutableMap>
      projectWatches();

  /** Preferences that this user has. Serialized as Git-config style string. */
  public abstract CachedPreferences preferences();

  public static CachedAccountDetails create(
      Account account,
      ImmutableMap> projectWatches,
      CachedPreferences preferences) {
    return new AutoValue_CachedAccountDetails(account, projectWatches, preferences);
  }

  /** Serializer used to read this entity from and write it to a persistent storage. */
  public enum Serializer implements CacheSerializer {
    INSTANCE;

    private static final AccountProtoConverter ACCOUNT_PROTO_CONVERTER =
        AccountProtoConverter.INSTANCE;
    private static final CachedProjectWatchProtoConverter PROJECT_WATCH_PROTO_CONVERTER =
        CachedProjectWatchProtoConverter.INSTANCE;

    @Override
    public byte[] serialize(CachedAccountDetails cachedAccountDetails) {
      Cache.AccountDetailsProto.Builder serialized = Cache.AccountDetailsProto.newBuilder();
      // We don't care about the difference of empty strings and null in the Account entity.
      Account account = cachedAccountDetails.account();
      serialized.setAccount(ACCOUNT_PROTO_CONVERTER.toProto(account));

      for (Map.Entry> watch :
          cachedAccountDetails.projectWatches().entrySet()) {
        serialized.addProjectWatchProto(PROJECT_WATCH_PROTO_CONVERTER.toProto(watch));
      }

      Optional cachedPreferencesProto =
          cachedAccountDetails.preferences().nonEmptyConfig();
      if (cachedPreferencesProto.isPresent()) {
        serialized.setUserPreferences(cachedPreferencesProto.get());
      }
      return Protos.toByteArray(serialized.build());
    }

    @Override
    public CachedAccountDetails deserialize(byte[] in) {
      Cache.AccountDetailsProto proto =
          Protos.parseUnchecked(Cache.AccountDetailsProto.parser(), in);
      Account account = ACCOUNT_PROTO_CONVERTER.fromProto(proto.getAccount());

      ImmutableMap.Builder> projectWatches =
          ImmutableMap.builder();
      proto.getProjectWatchProtoList().stream()
          .forEach(p -> projectWatches.put(PROJECT_WATCH_PROTO_CONVERTER.fromProto(p)));

      return CachedAccountDetails.create(
          account,
          projectWatches.build(),
          CachedPreferences.fromCachedPreferencesProto(proto.getUserPreferences()));
    }
  }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy