/*
  Сервис домов
*/
syntax = "proto3";

import "google/api/annotations.proto";
import "google/api/field_behavior.proto";
import "google/protobuf/timestamp.proto";
import "google/protobuf/wrappers.proto";
import "keyapis/access_control/v1/keyapis_access_control_access_control_v1.proto";


package keyapis.access_control.v1;

option java_package = "ru.keyapis.access_control.v1";
option java_outer_classname = "KeyapisAccessControlV1Proto";
option java_multiple_files = false;
option java_string_check_utf8 = true;
option go_package = "/keyapis_access_control_v1";
option cc_enable_arenas = true;
option csharp_namespace = "Keyapis.AccessControl.V1";
option objc_class_prefix = "KEYAPISACCESSCONTROLV1";
option php_namespace = "Keyapis\\AccessControl\\V1";
option ruby_package = "Keyapis::AccessControl::V1";
option optimize_for = LITE_RUNTIME;

// Сервис домов
service BuildingService {
  // Метод получения Дома.
  // Для пользователей типов owner, employee: в результат попадают только дома, которые привязаны к компании пользователя или дома квартирограамм привязанных к компании пользователя.
  // Метод доступен для: admin, service, owner, employee, seller, external_seller, ltp_first, bti
  rpc GetBuilding(GetBuildingRequest) returns (GetBuildingResponse) {
    option (google.api.http) = {
      get: "/access_control/api/v1/building/{id}"
    };
  }
  // Метод получения списка домов.
  // Для пользователей типов owner, employee: в результат попадают только дома, которые привязаны к компании пользователя или дома квартирограамм привязанных к компании пользователя.
  // При запросе через ApiKey происходит дополнительная фильтрация домов на основе доступности домов для этого ApiKey (фильтрация происходит по доступным AccessPoint для этой группы).
  // Метод доступен для: admin, service, owner, employee, ltp_first, bti.
  // Метод доступен для: ApiKey
  rpc GetBuildingList(GetBuildingListRequest) returns (stream GetBuildingListResponse) {
    option (google.api.http) = {
      get: "/access_control/api/v1/building/list"
    };
  }
  // Метод получения количества домов.
  // Для пользователей типов owner, employee: в результат попадают только дома, которые привязаны к компании пользователя или дома квартирограамм привязанных к компании пользователя.
  // Метод доступен для: admin, service, owner, employee, ltp_first, bti
  rpc GetBuildingCount(GetBuildingCountRequest) returns (GetBuildingCountResponse) {
    option (google.api.http) = {
      get: "/access_control/api/v1/building/count"
    };
  }
  // Метод получения статуса режима работы с подписками у помещений дома.
  // Возвращает агрегированный статус по всем помещениям дома.
  // Метод доступен для: admin, service, ltp_first, bti
  rpc GetBuildingOrponSubscriptionMode (GetBuildingOrponSubscriptionModeRequest) returns (GetBuildingOrponSubscriptionModeResponse) {
    option (google.api.http) = {
      get: "/access_control/api/v1/building/orpon/{orpon}/subscription_mode"
    };
  }
  // Метод проверки существования дома по ОРПОН.
  // Возвращает true если найден дом с указанным ОРПОН.
  // Метод доступен для: admin, service
  rpc GetBuildingOrponExists(GetBuildingOrponExistsRequest) returns (GetBuildingOrponExistsResponse) {
    option (google.api.http) = {
      get: "/access_control/api/v1/building/orpon/{orpon}/exists"
    };
  }
}

// Дом
message Building {
  // Идентификатор дома
  int32 id = 1;
  // Идентификатор РФ
  int32 rf_id = 2 [(google.api.field_behavior) = REQUIRED];
  // Идентификатор МРФ
  int32 mrf_id = 3 [(google.api.field_behavior) = REQUIRED];
  // ОРПОН
  int64 orpon = 4 [(google.api.field_behavior) = REQUIRED];
  // Город
  string city = 5 [(google.api.field_behavior) = REQUIRED];
  // Улица
  string street = 6 [(google.api.field_behavior) = REQUIRED];
  // Номер дома
  string number = 7;
  // Корпус
  string part = 8;
  // Идентификатор компании
  int32 company_id = 9 [(google.api.field_behavior) = REQUIRED];
  // Префикс
  string prefix = 10;
  // Дата создания.
  // # Тип: DateTime
  google.protobuf.Timestamp created_at = 11 [(google.api.field_behavior) = OUTPUT_ONLY];
  // Дата удаления.
  // # Тип: DateTime
  google.protobuf.Timestamp deleted_at = 12 [(google.api.field_behavior) = OUTPUT_ONLY];
  // Идентификатор квартирограммы
  int32 flatgramm_id = 13 [(google.api.field_behavior) = REQUIRED];
  // ОРПОН города, в котором находится дом
  int64 city_orpon = 14;
  // Идентификатор в федеральной информационной адресной системе.
  // Тип: Guid
  google.protobuf.StringValue fias = 15;
  // Наименование района города.
  // # Диапазон: 0..200
  google.protobuf.StringValue district = 16;
  // Уникальный номер адреса.
  // # Диапазон: 0..9999999999
  google.protobuf.Int64Value unom = 17;
  // ОРПОН региона
  int64 region_orpon = 18;
  // Смещение таймзоны в минутах.
  // # Диапазон: -720..840
  int32 utc_offset = 19;
  // Флаг указывает на то могут ли жители этого дома приобрести ключи домофона в партнёрских салонах или на маркетплейсах
  bool is_key_purchase_possible_in_sale_points = 20;
  // Флаг указывает на то могут ли жители этого дома приобретать ключи через управляющую компанию
  bool is_key_purchase_possible_in_management_company = 21;
  // Флаг указывает на то могут ли жители этого дома приобрести ключи напрямую у домофонной компании
  bool is_key_purchase_possible_in_intercom_company = 22;
  // Флаг указывает на то поддерживает ли дом использование RFID-меток с типом MIFARE
  bool is_rfid_mifare_supported = 23;
  // Наименование муниципального района.
  // # Диапазон: 0..64
  google.protobuf.StringValue area = 24;
  // ОРПОН муниципального района.
  // # Диапазон: 0..9999999999
  google.protobuf.Int64Value area_orpon = 25;
  // КЛАДР муниципального района.
  // # Диапазон: 0..32
  google.protobuf.StringValue area_kladr = 26;
  // Признак принадлежности населённого пункта к столичному статусу.
  // 1 — центр района.
  // 2 — центр региона.
  // 3 — центр района и региона.
  // 4 — центральный район региона.
  // 0 — ничего из перечисленного.
  // # Диапазон: 0..4
  google.protobuf.Int32Value capital_marker = 27;
  // КЛАДР-код города.
  // # Диапазон: 0..17
  google.protobuf.StringValue city_kladr = 28;
  // КЛАДР-код строения.
  // # Диапазон: 0..17
  google.protobuf.StringValue kladr = 29;
  // Уровень детализации, до которого адрес найден в ФИАС.
  // 0 — страна.
  // 1 — регион.
  // 3 — район.
  // 4 — город.
  // 5 — район города.
  // 6 — населенный пункт.
  // 7 — улица.
  // 8 — дом.
  // 9 — квартира.
  // 65 — планировочная структура.
  // 90 — доп. территория.
  // 91 — улица в доп. территории.
  // -1 — иностранный или пустой.
  // # Диапазон: -1..99
  google.protobuf.Int32Value fias_level = 30;
  // Уровень детализации, до которого адрес найден в ФИАС.
  // 0 — актуальный.
  // 1-50 — переименован.
  // 51 — переподчинен.
  // 99 — удален.
  // # Диапазон: 0..99
  google.protobuf.Int32Value fias_actuality_state = 31;
  // Координаты: широта
  google.protobuf.DoubleValue geo_lat = 32;
  // Координаты: долгота
  google.protobuf.DoubleValue geo_lon = 33;
  // Код ОКАТО
  google.protobuf.Int32Value okato = 34;
  // Код ОКТМО
  google.protobuf.Int32Value oktmo = 35;
  // Почтовый индекс
  google.protobuf.Int32Value postal_code = 36;
  // Наименование региона.
  // # Диапазон: 0..64
  google.protobuf.StringValue region = 37;
  // КЛАДР-код региона.
  // # Диапазон: 0..32
  google.protobuf.StringValue region_kladr = 38;
  // КЛАДР-код улицы.
  // # Диапазон: 0..32
  google.protobuf.StringValue street_kladr = 39;
  // ОРПОН улицы.
  // # Диапазон: 0..9999999999
  google.protobuf.Int64Value street_orpon = 40;
}

// Запрос получения дома
message GetBuildingRequest {
  // Идентификатор дома
  int32 id = 1 [(google.api.field_behavior) = REQUIRED];
}

// Ответ на запрос получения дома
message GetBuildingResponse {
  // Ошибка
  message Error {
    // Причина ошибки
    oneof reason {
      // Ошибка валидации
      ValidationError validation = 1;
    }
  }
  // Тип результата
  oneof type {
    // Квартира
    Building data = 1;
    // Ошибка
    Error error = 2;
  }
}

// Запрос получения списка домов
message GetBuildingListRequest {
  // Фильтр
  BuildingFilter filter = 1;
  // Вариант разбиения на страницы
  oneof pagination {
    // Стандартный постраничный вывод
    BuildingPaging paging = 2;
  }
}

// Ответ на запрос получения списка домов
message GetBuildingListResponse {
  // Ошибка
  message Error {
    // Причина ошибки
    oneof reason {
      // Ошибка валидации
      ValidationError validation = 1;
    }
  }
  // Тип результата
  oneof type {
    // Квартира
    Building data = 1;
    // Ошибка
    Error error = 2;
  }
}

// Запрос получения количества домов
message GetBuildingCountRequest {
  // Фильтр
  BuildingFilter filter = 1 [(google.api.field_behavior) = REQUIRED];
}

// Ответ на запрос получения количества домов
message GetBuildingCountResponse {
  // Тип результата
  oneof type {
    // Количество
    int32 data = 1;
  }
}

// Фильтр по домам
message BuildingFilter {
  // По идентификаторам МРФ
  repeated int32 mrf_ids = 1;
  // По идентификаторам РФ
  repeated int32 rf_ids = 2;
  // По идентификаторам устройств
  repeated int32 device_ids = 3;
  // По идентификаторам квартирограмм
  repeated int32 flatgramm_ids = 4;
  // По орпонам
  repeated int64 orpons = 5;
}

// Постраничный вывод
message BuildingPaging {
  // Справочник типов значений сортировки.
  // # Тип: byte
  enum OrderByType {
    // Значение не указано
    ORDER_BY_TYPE_UNKNOWN = 0;
    // По идентификатору
    ID = 1;
    // По времени создания
    CREATED_AT = 2;
    // По улице, номеру дома, корпусу
    STREET_THEN_NUMBER_THEN_PART = 3;
  }
  // Тип значения сортировки.
  // Если значение не передано, то будет взято значение по умолчанию.
  // # По умолчанию: CREATED_AT
  OrderByType order_by_type = 1;
  // Справочник типов направлений сортировки.
  // # Тип: byte
  enum DirectionType {
    // Значение не указано
    DIRECTION_TYPE_UNKNOWN = 0;
    // От большего к меньшему
    DESC = 1;
    // От меньшего к большему
    ASC = 2;
  }
  // Тип направления сортировки.
  // # По умолчанию: DESC
  DirectionType direction_type = 2;
  // Количество записей на страницу.
  // Если значение 0 (не передано), то будет взято значение по умолчанию.
  // # Диапазон: 0..100.
  // # По умолчанию: 20
  int32 limit = 3;
  // Сдвиг.
  // # Диапазон: 0..2147483647
  int32 offset = 4;
}

// Агрегированный статус режима работы с подписками на доме
message BuildingSubscriptionMode {
  // Справочник режимов работы с подписками
  enum SubscriptionModeType {
    // Значение не указано
    SUBSCRIPTION_MODE_TYPE_UNKNOWN = 0;
    // Режим работы с подписками включен на всех помещениях дома
    ENABLED = 1;
    // Режим работы с подписками включен на некоторых помещениях дома
    PARTIALLY_ENABLED = 2;
    // Режим работы с подписками выключен на всех помещениях дома
    DISABLED = 3;
  }
  // Режим работы с подписками на доме
  SubscriptionModeType subscription_mode_type = 1;
}

// Запрос получения агрегированного статуса режима работы с подписками дома
message GetBuildingOrponSubscriptionModeRequest {
  // ОРПОН.
  // # Диапазон: 1..9223372036854775807
  int64 orpon = 1 [(google.api.field_behavior) = REQUIRED];
}

// Ответ на запрос получения агрегированного статуса режима работы с подписками дома
message GetBuildingOrponSubscriptionModeResponse {
  // Ошибка
  message Error {
    // Причина ошибки
    oneof reason {
      // Ошибка валидации
      ValidationError validation = 1;
    }
  }

  // Тип результата
  oneof type {
    // Агрегированный статус режима работы с подписками дома
    BuildingSubscriptionMode data = 1;
    // Ошибка
    Error error = 2;
  }
}


// Запрос проверки существования дома по ОРПОН
message GetBuildingOrponExistsRequest {
  // ОРПОН дома.
  // # Диапазон: 1..9223372036854775807
  int64 orpon = 1 [(google.api.field_behavior) = REQUIRED];
}

// Ответ на запрос проверки существования дома по ОРПОН
message GetBuildingOrponExistsResponse {
  // Ошибка
  message Error {
    // Причина ошибки
    oneof reason {
      // Ошибка валидации
      ValidationError validation = 1;
    }
  }

  // Тип результата
  oneof type {
    // Результат проверки: true - если дом существует, false - в противном случае
    bool data = 1;
    // Ошибка
    Error error = 2;
  }
}