// Copyright (C) 2017 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.index.group;

import static com.google.gerrit.index.SchemaUtil.schema;

import com.google.common.collect.ImmutableList;
import com.google.gerrit.entities.InternalGroup;
import com.google.gerrit.index.Schema;
import com.google.gerrit.index.SchemaDefinitions;

/**
 * Definition of group index versions (schemata). See {@link SchemaDefinitions}.
 *
 * <p>Upgrades are subject to constraints, see {@link
 * com.google.gerrit.index.IndexUpgradeValidator}.
 */
public class GroupSchemaDefinitions extends SchemaDefinitions<InternalGroup> {
  @Deprecated
  static final Schema<InternalGroup> V5 =
      schema(
          /* version= */ 5,
          ImmutableList.of(GroupField.REF_STATE, GroupField.UUID),
          ImmutableList.of(
              GroupField.CREATED_ON_FIELD,
              GroupField.DESCRIPTION_FIELD,
              GroupField.ID_FIELD,
              GroupField.IS_VISIBLE_TO_ALL_FIELD,
              GroupField.MEMBER_FIELD,
              GroupField.NAME_FIELD,
              GroupField.NAME_PART_FIELD,
              GroupField.OWNER_UUID_FIELD,
              GroupField.SUBGROUP_FIELD),
          ImmutableList.of(
              GroupField.CREATED_ON_SPEC,
              GroupField.DESCRIPTION_SPEC,
              GroupField.ID_FIELD_SPEC,
              GroupField.IS_VISIBLE_TO_ALL_SPEC,
              GroupField.MEMBER_SPEC,
              GroupField.NAME_SPEC,
              GroupField.NAME_PART_SPEC,
              GroupField.OWNER_UUID_SPEC,
              GroupField.SUBGROUP_SPEC));

  // Bump Lucene version requires reindexing
  @Deprecated static final Schema<InternalGroup> V6 = schema(V5);

  // Lucene index was changed to add an additional field for sorting.
  @Deprecated static final Schema<InternalGroup> V7 = schema(V6);

  // New numeric types: use dimensional points using the k-d tree geo-spatial data structure
  // to offer fast single- and multi-dimensional numeric range.
  @Deprecated static final Schema<InternalGroup> V8 = schema(V7);

  // Upgrade Lucene to 7.x requires reindexing.
  static final Schema<InternalGroup> V9 = schema(V8);

  /** Singleton instance of the schema definitions. This is one per JVM. */
  public static final GroupSchemaDefinitions INSTANCE = new GroupSchemaDefinitions();

  private GroupSchemaDefinitions() {
    super("groups", InternalGroup.class);
  }
}
