From eacfd6818dc51ac8e01588176a054a790b2180e5 Mon Sep 17 00:00:00 2001 From: authzedbot <86801627+authzedbot@users.noreply.github.com> Date: Thu, 24 Sep 2026 20:00:50 +0000 Subject: [PATCH] feat: update api version --- buf.gen.yaml | 2 +- .../Materialize/V0/Roaringlookupresources.cs | 701 ++++++++++++++++++ .../V0/RoaringlookupresourcesGrpc.cs | 308 ++++++++ .../Authzed/Api/V1/PermissionService.cs | 515 ++++++++----- .../Authzed/Api/V1/PermissionServiceGrpc.cs | 18 + 5 files changed, 1342 insertions(+), 202 deletions(-) create mode 100644 src/Authzed.Net/Authzed/Api/Materialize/V0/Roaringlookupresources.cs create mode 100644 src/Authzed.Net/Authzed/Api/Materialize/V0/RoaringlookupresourcesGrpc.cs diff --git a/buf.gen.yaml b/buf.gen.yaml index ac4b0ec..b8c9c47 100644 --- a/buf.gen.yaml +++ b/buf.gen.yaml @@ -12,4 +12,4 @@ plugins: - "base_namespace=" - "no_server=on" inputs: - - module: buf.build/authzed/api:v1.53.0 + - module: buf.build/authzed/api:v1.57.0 diff --git a/src/Authzed.Net/Authzed/Api/Materialize/V0/Roaringlookupresources.cs b/src/Authzed.Net/Authzed/Api/Materialize/V0/Roaringlookupresources.cs new file mode 100644 index 0000000..8bbc067 --- /dev/null +++ b/src/Authzed.Net/Authzed/Api/Materialize/V0/Roaringlookupresources.cs @@ -0,0 +1,701 @@ +// +// Generated by the protocol buffer compiler. DO NOT EDIT! +// source: authzed/api/materialize/v0/roaringlookupresources.proto +// +#pragma warning disable 1591, 0612, 3021, 8981 +#region Designer generated code + +using pb = global::Google.Protobuf; +using pbc = global::Google.Protobuf.Collections; +using pbr = global::Google.Protobuf.Reflection; +using scg = global::System.Collections.Generic; +namespace Authzed.Api.Materialize.V0 { + + /// Holder for reflection information generated from authzed/api/materialize/v0/roaringlookupresources.proto + public static partial class RoaringlookupresourcesReflection { + + #region Descriptor + /// File descriptor for authzed/api/materialize/v0/roaringlookupresources.proto + public static pbr::FileDescriptor Descriptor { + get { return descriptor; } + } + private static pbr::FileDescriptor descriptor; + + static RoaringlookupresourcesReflection() { + byte[] descriptorData = global::System.Convert.FromBase64String( + string.Concat( + "CjdhdXRoemVkL2FwaS9tYXRlcmlhbGl6ZS92MC9yb2FyaW5nbG9va3VwcmVz", + "b3VyY2VzLnByb3RvEhphdXRoemVkLmFwaS5tYXRlcmlhbGl6ZS52MBoZYXV0", + "aHplZC9hcGkvdjEvY29yZS5wcm90bxonYXV0aHplZC9hcGkvdjEvcGVybWlz", + "c2lvbl9zZXJ2aWNlLnByb3RvGhtidWYvdmFsaWRhdGUvdmFsaWRhdGUucHJv", + "dG8aF3ZhbGlkYXRlL3ZhbGlkYXRlLnByb3RvIuwDCilFeHBlcmltZW50YWxS", + "b2FyaW5nTG9va3VwUmVzb3VyY2VzUmVxdWVzdBI9Cgtjb25zaXN0ZW5jeRgB", + "IAEoCzIbLmF1dGh6ZWQuYXBpLnYxLkNvbnNpc3RlbmN5Ugtjb25zaXN0ZW5j", + "eRLDAQoUcmVzb3VyY2Vfb2JqZWN0X3R5cGUYAiABKAlCkAH6QkVyQyiAATI+", + "XihbYS16XVthLXowLTlfXXsxLDYxfVthLXowLTldLykqW2Etel1bYS16MC05", + "X117MSw2Mn1bYS16MC05XSS6SEVyQyiAATI+XihbYS16XVthLXowLTlfXXsx", + "LDYxfVthLXowLTldLykqW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSRS", + "EnJlc291cmNlT2JqZWN0VHlwZRJuCgpwZXJtaXNzaW9uGAMgASgJQk76QiRy", + "IihAMh5eW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSS6SCRyIihAMh5e", + "W2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSRSCnBlcm1pc3Npb24SSgoH", + "c3ViamVjdBgEIAEoCzIgLmF1dGh6ZWQuYXBpLnYxLlN1YmplY3RSZWZlcmVu", + "Y2VCDvpCBYoBAhABukgDyAEBUgdzdWJqZWN0IrEBCipFeHBlcmltZW50YWxS", + "b2FyaW5nTG9va3VwUmVzb3VyY2VzUmVzcG9uc2USFgoGYml0bWFwGAEgASgM", + "UgZiaXRtYXASIAoLY2FyZGluYWxpdHkYAiABKARSC2NhcmRpbmFsaXR5EkkK", + "C2F0X3JldmlzaW9uGAMgASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5C", + "DvpCBYoBAhABukgDyAEBUgphdFJldmlzaW9uMtcBCh1Sb2FyaW5nTG9va3Vw", + "UmVzb3VyY2VzU2VydmljZRK1AQoiRXhwZXJpbWVudGFsUm9hcmluZ0xvb2t1", + "cFJlc291cmNlcxJFLmF1dGh6ZWQuYXBpLm1hdGVyaWFsaXplLnYwLkV4cGVy", + "aW1lbnRhbFJvYXJpbmdMb29rdXBSZXNvdXJjZXNSZXF1ZXN0GkYuYXV0aHpl", + "ZC5hcGkubWF0ZXJpYWxpemUudjAuRXhwZXJpbWVudGFsUm9hcmluZ0xvb2t1", + "cFJlc291cmNlc1Jlc3BvbnNlIgBCYgoeY29tLmF1dGh6ZWQuYXBpLm1hdGVy", + "aWFsaXplLnYwUAFaPmdpdGh1Yi5jb20vYXV0aHplZC9hdXRoemVkLWdvL3By", + "b3RvL2F1dGh6ZWQvYXBpL21hdGVyaWFsaXplL3YwYgZwcm90bzM=")); + descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData, + new pbr::FileDescriptor[] { global::Authzed.Api.V1.CoreReflection.Descriptor, global::Authzed.Api.V1.PermissionServiceReflection.Descriptor, global::Buf.Validate.ValidateReflection.Descriptor, global::Validate.ValidateReflection.Descriptor, }, + new pbr::GeneratedClrTypeInfo(null, null, new pbr::GeneratedClrTypeInfo[] { + new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest), global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest.Parser, new[]{ "Consistency", "ResourceObjectType", "Permission", "Subject" }, null, null, null, null), + new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesResponse), global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesResponse.Parser, new[]{ "Bitmap", "Cardinality", "AtRevision" }, null, null, null, null) + })); + } + #endregion + + } + #region Messages + [global::System.Diagnostics.DebuggerDisplayAttribute("{ToString(),nq}")] + public sealed partial class ExperimentalRoaringLookupResourcesRequest : pb::IMessage + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + , pb::IBufferMessage + #endif + { + private static readonly pb::MessageParser _parser = new pb::MessageParser(() => new ExperimentalRoaringLookupResourcesRequest()); + private pb::UnknownFieldSet _unknownFields; + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public static pb::MessageParser Parser { get { return _parser; } } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public static pbr::MessageDescriptor Descriptor { + get { return global::Authzed.Api.Materialize.V0.RoaringlookupresourcesReflection.Descriptor.MessageTypes[0]; } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + pbr::MessageDescriptor pb::IMessage.Descriptor { + get { return Descriptor; } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ExperimentalRoaringLookupResourcesRequest() { + OnConstruction(); + } + + partial void OnConstruction(); + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ExperimentalRoaringLookupResourcesRequest(ExperimentalRoaringLookupResourcesRequest other) : this() { + consistency_ = other.consistency_ != null ? other.consistency_.Clone() : null; + resourceObjectType_ = other.resourceObjectType_; + permission_ = other.permission_; + subject_ = other.subject_ != null ? other.subject_.Clone() : null; + _unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ExperimentalRoaringLookupResourcesRequest Clone() { + return new ExperimentalRoaringLookupResourcesRequest(this); + } + + /// Field number for the "consistency" field. + public const int ConsistencyFieldNumber = 1; + private global::Authzed.Api.V1.Consistency consistency_; + /// + /// consistency selects the snapshot at which the lookup is performed. If + /// unspecified, minimize_latency is used. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public global::Authzed.Api.V1.Consistency Consistency { + get { return consistency_; } + set { + consistency_ = value; + } + } + + /// Field number for the "resource_object_type" field. + public const int ResourceObjectTypeFieldNumber = 2; + private string resourceObjectType_ = ""; + /// + /// resource_object_type is the type of resource over which to look up access. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public string ResourceObjectType { + get { return resourceObjectType_; } + set { + resourceObjectType_ = pb::ProtoPreconditions.CheckNotNull(value, "value"); + } + } + + /// Field number for the "permission" field. + public const int PermissionFieldNumber = 3; + private string permission_ = ""; + /// + /// permission is the name of the permission or relation to look up. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public string Permission { + get { return permission_; } + set { + permission_ = pb::ProtoPreconditions.CheckNotNull(value, "value"); + } + } + + /// Field number for the "subject" field. + public const int SubjectFieldNumber = 4; + private global::Authzed.Api.V1.SubjectReference subject_; + /// + /// subject is the subject for which access is being looked up. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public global::Authzed.Api.V1.SubjectReference Subject { + get { return subject_; } + set { + subject_ = value; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public override bool Equals(object other) { + return Equals(other as ExperimentalRoaringLookupResourcesRequest); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public bool Equals(ExperimentalRoaringLookupResourcesRequest other) { + if (ReferenceEquals(other, null)) { + return false; + } + if (ReferenceEquals(other, this)) { + return true; + } + if (!object.Equals(Consistency, other.Consistency)) return false; + if (ResourceObjectType != other.ResourceObjectType) return false; + if (Permission != other.Permission) return false; + if (!object.Equals(Subject, other.Subject)) return false; + return Equals(_unknownFields, other._unknownFields); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public override int GetHashCode() { + int hash = 1; + if (consistency_ != null) hash ^= Consistency.GetHashCode(); + if (ResourceObjectType.Length != 0) hash ^= ResourceObjectType.GetHashCode(); + if (Permission.Length != 0) hash ^= Permission.GetHashCode(); + if (subject_ != null) hash ^= Subject.GetHashCode(); + if (_unknownFields != null) { + hash ^= _unknownFields.GetHashCode(); + } + return hash; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public override string ToString() { + return pb::JsonFormatter.ToDiagnosticString(this); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public void WriteTo(pb::CodedOutputStream output) { + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + output.WriteRawMessage(this); + #else + if (consistency_ != null) { + output.WriteRawTag(10); + output.WriteMessage(Consistency); + } + if (ResourceObjectType.Length != 0) { + output.WriteRawTag(18); + output.WriteString(ResourceObjectType); + } + if (Permission.Length != 0) { + output.WriteRawTag(26); + output.WriteString(Permission); + } + if (subject_ != null) { + output.WriteRawTag(34); + output.WriteMessage(Subject); + } + if (_unknownFields != null) { + _unknownFields.WriteTo(output); + } + #endif + } + + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + void pb::IBufferMessage.InternalWriteTo(ref pb::WriteContext output) { + if (consistency_ != null) { + output.WriteRawTag(10); + output.WriteMessage(Consistency); + } + if (ResourceObjectType.Length != 0) { + output.WriteRawTag(18); + output.WriteString(ResourceObjectType); + } + if (Permission.Length != 0) { + output.WriteRawTag(26); + output.WriteString(Permission); + } + if (subject_ != null) { + output.WriteRawTag(34); + output.WriteMessage(Subject); + } + if (_unknownFields != null) { + _unknownFields.WriteTo(ref output); + } + } + #endif + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public int CalculateSize() { + int size = 0; + if (consistency_ != null) { + size += 1 + pb::CodedOutputStream.ComputeMessageSize(Consistency); + } + if (ResourceObjectType.Length != 0) { + size += 1 + pb::CodedOutputStream.ComputeStringSize(ResourceObjectType); + } + if (Permission.Length != 0) { + size += 1 + pb::CodedOutputStream.ComputeStringSize(Permission); + } + if (subject_ != null) { + size += 1 + pb::CodedOutputStream.ComputeMessageSize(Subject); + } + if (_unknownFields != null) { + size += _unknownFields.CalculateSize(); + } + return size; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public void MergeFrom(ExperimentalRoaringLookupResourcesRequest other) { + if (other == null) { + return; + } + if (other.consistency_ != null) { + if (consistency_ == null) { + Consistency = new global::Authzed.Api.V1.Consistency(); + } + Consistency.MergeFrom(other.Consistency); + } + if (other.ResourceObjectType.Length != 0) { + ResourceObjectType = other.ResourceObjectType; + } + if (other.Permission.Length != 0) { + Permission = other.Permission; + } + if (other.subject_ != null) { + if (subject_ == null) { + Subject = new global::Authzed.Api.V1.SubjectReference(); + } + Subject.MergeFrom(other.Subject); + } + _unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public void MergeFrom(pb::CodedInputStream input) { + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + input.ReadRawMessage(this); + #else + uint tag; + while ((tag = input.ReadTag()) != 0) { + if ((tag & 7) == 4) { + // Abort on any end group tag. + return; + } + switch(tag) { + default: + _unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input); + break; + case 10: { + if (consistency_ == null) { + Consistency = new global::Authzed.Api.V1.Consistency(); + } + input.ReadMessage(Consistency); + break; + } + case 18: { + ResourceObjectType = input.ReadString(); + break; + } + case 26: { + Permission = input.ReadString(); + break; + } + case 34: { + if (subject_ == null) { + Subject = new global::Authzed.Api.V1.SubjectReference(); + } + input.ReadMessage(Subject); + break; + } + } + } + #endif + } + + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + void pb::IBufferMessage.InternalMergeFrom(ref pb::ParseContext input) { + uint tag; + while ((tag = input.ReadTag()) != 0) { + if ((tag & 7) == 4) { + // Abort on any end group tag. + return; + } + switch(tag) { + default: + _unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, ref input); + break; + case 10: { + if (consistency_ == null) { + Consistency = new global::Authzed.Api.V1.Consistency(); + } + input.ReadMessage(Consistency); + break; + } + case 18: { + ResourceObjectType = input.ReadString(); + break; + } + case 26: { + Permission = input.ReadString(); + break; + } + case 34: { + if (subject_ == null) { + Subject = new global::Authzed.Api.V1.SubjectReference(); + } + input.ReadMessage(Subject); + break; + } + } + } + } + #endif + + } + + [global::System.Diagnostics.DebuggerDisplayAttribute("{ToString(),nq}")] + public sealed partial class ExperimentalRoaringLookupResourcesResponse : pb::IMessage + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + , pb::IBufferMessage + #endif + { + private static readonly pb::MessageParser _parser = new pb::MessageParser(() => new ExperimentalRoaringLookupResourcesResponse()); + private pb::UnknownFieldSet _unknownFields; + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public static pb::MessageParser Parser { get { return _parser; } } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public static pbr::MessageDescriptor Descriptor { + get { return global::Authzed.Api.Materialize.V0.RoaringlookupresourcesReflection.Descriptor.MessageTypes[1]; } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + pbr::MessageDescriptor pb::IMessage.Descriptor { + get { return Descriptor; } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ExperimentalRoaringLookupResourcesResponse() { + OnConstruction(); + } + + partial void OnConstruction(); + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ExperimentalRoaringLookupResourcesResponse(ExperimentalRoaringLookupResourcesResponse other) : this() { + bitmap_ = other.bitmap_; + cardinality_ = other.cardinality_; + atRevision_ = other.atRevision_ != null ? other.atRevision_.Clone() : null; + _unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ExperimentalRoaringLookupResourcesResponse Clone() { + return new ExperimentalRoaringLookupResourcesResponse(this); + } + + /// Field number for the "bitmap" field. + public const int BitmapFieldNumber = 1; + private pb::ByteString bitmap_ = pb::ByteString.Empty; + /// + /// bitmap is the roaring64 bitmap, in RoaringFormatSpec 64-bit portable + /// format, of the resource object IDs accessible to the subject. The IDs are + /// the object IDs from the relationships themselves, as 44-bit integers. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public pb::ByteString Bitmap { + get { return bitmap_; } + set { + bitmap_ = pb::ProtoPreconditions.CheckNotNull(value, "value"); + } + } + + /// Field number for the "cardinality" field. + public const int CardinalityFieldNumber = 2; + private ulong cardinality_; + /// + /// cardinality is the number of resource IDs in the bitmap. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public ulong Cardinality { + get { return cardinality_; } + set { + cardinality_ = value; + } + } + + /// Field number for the "at_revision" field. + public const int AtRevisionFieldNumber = 3; + private global::Authzed.Api.V1.ZedToken atRevision_; + /// + /// at_revision is the ZedToken at which the lookup was performed. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public global::Authzed.Api.V1.ZedToken AtRevision { + get { return atRevision_; } + set { + atRevision_ = value; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public override bool Equals(object other) { + return Equals(other as ExperimentalRoaringLookupResourcesResponse); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public bool Equals(ExperimentalRoaringLookupResourcesResponse other) { + if (ReferenceEquals(other, null)) { + return false; + } + if (ReferenceEquals(other, this)) { + return true; + } + if (Bitmap != other.Bitmap) return false; + if (Cardinality != other.Cardinality) return false; + if (!object.Equals(AtRevision, other.AtRevision)) return false; + return Equals(_unknownFields, other._unknownFields); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public override int GetHashCode() { + int hash = 1; + if (Bitmap.Length != 0) hash ^= Bitmap.GetHashCode(); + if (Cardinality != 0UL) hash ^= Cardinality.GetHashCode(); + if (atRevision_ != null) hash ^= AtRevision.GetHashCode(); + if (_unknownFields != null) { + hash ^= _unknownFields.GetHashCode(); + } + return hash; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public override string ToString() { + return pb::JsonFormatter.ToDiagnosticString(this); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public void WriteTo(pb::CodedOutputStream output) { + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + output.WriteRawMessage(this); + #else + if (Bitmap.Length != 0) { + output.WriteRawTag(10); + output.WriteBytes(Bitmap); + } + if (Cardinality != 0UL) { + output.WriteRawTag(16); + output.WriteUInt64(Cardinality); + } + if (atRevision_ != null) { + output.WriteRawTag(26); + output.WriteMessage(AtRevision); + } + if (_unknownFields != null) { + _unknownFields.WriteTo(output); + } + #endif + } + + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + void pb::IBufferMessage.InternalWriteTo(ref pb::WriteContext output) { + if (Bitmap.Length != 0) { + output.WriteRawTag(10); + output.WriteBytes(Bitmap); + } + if (Cardinality != 0UL) { + output.WriteRawTag(16); + output.WriteUInt64(Cardinality); + } + if (atRevision_ != null) { + output.WriteRawTag(26); + output.WriteMessage(AtRevision); + } + if (_unknownFields != null) { + _unknownFields.WriteTo(ref output); + } + } + #endif + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public int CalculateSize() { + int size = 0; + if (Bitmap.Length != 0) { + size += 1 + pb::CodedOutputStream.ComputeBytesSize(Bitmap); + } + if (Cardinality != 0UL) { + size += 1 + pb::CodedOutputStream.ComputeUInt64Size(Cardinality); + } + if (atRevision_ != null) { + size += 1 + pb::CodedOutputStream.ComputeMessageSize(AtRevision); + } + if (_unknownFields != null) { + size += _unknownFields.CalculateSize(); + } + return size; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public void MergeFrom(ExperimentalRoaringLookupResourcesResponse other) { + if (other == null) { + return; + } + if (other.Bitmap.Length != 0) { + Bitmap = other.Bitmap; + } + if (other.Cardinality != 0UL) { + Cardinality = other.Cardinality; + } + if (other.atRevision_ != null) { + if (atRevision_ == null) { + AtRevision = new global::Authzed.Api.V1.ZedToken(); + } + AtRevision.MergeFrom(other.AtRevision); + } + _unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public void MergeFrom(pb::CodedInputStream input) { + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + input.ReadRawMessage(this); + #else + uint tag; + while ((tag = input.ReadTag()) != 0) { + if ((tag & 7) == 4) { + // Abort on any end group tag. + return; + } + switch(tag) { + default: + _unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input); + break; + case 10: { + Bitmap = input.ReadBytes(); + break; + } + case 16: { + Cardinality = input.ReadUInt64(); + break; + } + case 26: { + if (atRevision_ == null) { + AtRevision = new global::Authzed.Api.V1.ZedToken(); + } + input.ReadMessage(AtRevision); + break; + } + } + } + #endif + } + + #if !GOOGLE_PROTOBUF_REFSTRUCT_COMPATIBILITY_MODE + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + void pb::IBufferMessage.InternalMergeFrom(ref pb::ParseContext input) { + uint tag; + while ((tag = input.ReadTag()) != 0) { + if ((tag & 7) == 4) { + // Abort on any end group tag. + return; + } + switch(tag) { + default: + _unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, ref input); + break; + case 10: { + Bitmap = input.ReadBytes(); + break; + } + case 16: { + Cardinality = input.ReadUInt64(); + break; + } + case 26: { + if (atRevision_ == null) { + AtRevision = new global::Authzed.Api.V1.ZedToken(); + } + input.ReadMessage(AtRevision); + break; + } + } + } + } + #endif + + } + + #endregion + +} + +#endregion Designer generated code diff --git a/src/Authzed.Net/Authzed/Api/Materialize/V0/RoaringlookupresourcesGrpc.cs b/src/Authzed.Net/Authzed/Api/Materialize/V0/RoaringlookupresourcesGrpc.cs new file mode 100644 index 0000000..dd9f322 --- /dev/null +++ b/src/Authzed.Net/Authzed/Api/Materialize/V0/RoaringlookupresourcesGrpc.cs @@ -0,0 +1,308 @@ +// +// Generated by the protocol buffer compiler. DO NOT EDIT! +// source: authzed/api/materialize/v0/roaringlookupresources.proto +// +#pragma warning disable 0414, 1591, 8981, 0612 +#region Designer generated code + +using grpc = global::Grpc.Core; + +namespace Authzed.Api.Materialize.V0 { + public static partial class RoaringLookupResourcesService + { + static readonly string __ServiceName = "authzed.api.materialize.v0.RoaringLookupResourcesService"; + + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + static void __Helper_SerializeMessage(global::Google.Protobuf.IMessage message, grpc::SerializationContext context) + { + #if !GRPC_DISABLE_PROTOBUF_BUFFER_SERIALIZATION + if (message is global::Google.Protobuf.IBufferMessage) + { + context.SetPayloadLength(message.CalculateSize()); + global::Google.Protobuf.MessageExtensions.WriteTo(message, context.GetBufferWriter()); + context.Complete(); + return; + } + #endif + context.Complete(global::Google.Protobuf.MessageExtensions.ToByteArray(message)); + } + + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + static class __Helper_MessageCache + { + public static readonly bool IsBufferMessage = global::System.Reflection.IntrospectionExtensions.GetTypeInfo(typeof(global::Google.Protobuf.IBufferMessage)).IsAssignableFrom(typeof(T)); + } + + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + static T __Helper_DeserializeMessage(grpc::DeserializationContext context, global::Google.Protobuf.MessageParser parser) where T : global::Google.Protobuf.IMessage + { + #if !GRPC_DISABLE_PROTOBUF_BUFFER_SERIALIZATION + if (__Helper_MessageCache.IsBufferMessage) + { + return parser.ParseFrom(context.PayloadAsReadOnlySequence()); + } + #endif + return parser.ParseFrom(context.PayloadAsNewBuffer()); + } + + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + static readonly grpc::Marshaller __Marshaller_authzed_api_materialize_v0_ExperimentalRoaringLookupResourcesRequest = grpc::Marshallers.Create(__Helper_SerializeMessage, context => __Helper_DeserializeMessage(context, global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest.Parser)); + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + static readonly grpc::Marshaller __Marshaller_authzed_api_materialize_v0_ExperimentalRoaringLookupResourcesResponse = grpc::Marshallers.Create(__Helper_SerializeMessage, context => __Helper_DeserializeMessage(context, global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesResponse.Parser)); + + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + static readonly grpc::Method __Method_ExperimentalRoaringLookupResources = new grpc::Method( + grpc::MethodType.Unary, + __ServiceName, + "ExperimentalRoaringLookupResources", + __Marshaller_authzed_api_materialize_v0_ExperimentalRoaringLookupResourcesRequest, + __Marshaller_authzed_api_materialize_v0_ExperimentalRoaringLookupResourcesResponse); + + /// Service descriptor + public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor + { + get { return global::Authzed.Api.Materialize.V0.RoaringlookupresourcesReflection.Descriptor.Services[0]; } + } + + /// Client for RoaringLookupResourcesService + public partial class RoaringLookupResourcesServiceClient : grpc::ClientBase + { + /// Creates a new client for RoaringLookupResourcesService + /// The channel to use to make remote calls. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + public RoaringLookupResourcesServiceClient(grpc::ChannelBase channel) : base(channel) + { + } + /// Creates a new client for RoaringLookupResourcesService that uses a custom CallInvoker. + /// The callInvoker to use to make remote calls. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + public RoaringLookupResourcesServiceClient(grpc::CallInvoker callInvoker) : base(callInvoker) + { + } + /// Protected parameterless constructor to allow creation of test doubles. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + protected RoaringLookupResourcesServiceClient() : base() + { + } + /// Protected constructor to allow creation of configured clients. + /// The client configuration. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + protected RoaringLookupResourcesServiceClient(ClientBaseConfiguration configuration) : base(configuration) + { + } + + /// + /// EXPERIMENTAL: RoaringLookupResources returns a roaring64 bitmap of the IDs + /// of the resources of the given type on which the given subject has the + /// given permission. This API is experimental and subject to change or + /// removal. + /// + /// The bitmap is serialized in the RoaringFormatSpec 64-bit portable format + /// (https://github.com/RoaringBitmap/RoaringFormatSpec#extention-for-64-bit-implementations), + /// which OpenSearch consumes directly via a `"value_type": "bitmap"` terms + /// query against a `long` field, once Base64-encoded. + /// + /// The IDs in the bitmap are the resource object IDs exactly as they appear + /// in the relationships: no surrogate or internal ID is introduced, so the + /// caller can use the bitmap directly against its own data (for example, a + /// search index keyed by the same IDs). + /// + /// For this API to be usable, every resource object ID of the requested type + /// must be a canonical decimal integer that fits in 44 bits -- at most + /// 17592186044415 (2^44 - 1). Canonical means the string round-trips through + /// uint64 formatting unchanged: `document:007` and `document:7` are distinct + /// objects that would collide as the integer 7, so non-canonical IDs are + /// rejected. If any resource object ID violates either rule, the call fails + /// with FAILED_PRECONDITION rather than returning a partial bitmap, since a + /// bitmap that is quietly too small is a wrong authorization answer. When the + /// permission relates a type to itself (for example `group#member` looked up + /// for a `group#member` subject), the subject is one of its own resources, so + /// the subject's object ID is held to the same rules and can itself be the ID + /// named in that error. + /// + /// Response size: the whole bitmap is returned in a single unary message, and + /// most gRPC clients default to refusing messages larger than 4 MiB. Roaring + /// is compact -- a million sequential IDs encode in a few hundred bytes -- but + /// sparse IDs cost close to 10 bytes each, so a result of more than roughly + /// 400,000 widely-spread IDs can exceed that default and fail on the CLIENT + /// side with RESOURCE_EXHAUSTED ("received message larger than max"). This is + /// a limit of the caller's own gRPC configuration, not of the service: raise + /// it to match the largest result you expect (in Go, + /// grpc.WithDefaultCallOptions(grpc.MaxCallRecvMsgSize(n)); other languages + /// have an equivalent channel option). The `cardinality` field is returned so + /// callers can see how large a result is once received; no server-side result + /// limit is applied. + /// + /// The request to send to the server. + /// The initial metadata to send with the call. This parameter is optional. + /// An optional deadline for the call. The call will be cancelled if deadline is hit. + /// An optional token for canceling the call. + /// The response received from the server. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + public virtual global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesResponse ExperimentalRoaringLookupResources(global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest request, grpc::Metadata headers = null, global::System.DateTime? deadline = null, global::System.Threading.CancellationToken cancellationToken = default(global::System.Threading.CancellationToken)) + { + return ExperimentalRoaringLookupResources(request, new grpc::CallOptions(headers, deadline, cancellationToken)); + } + /// + /// EXPERIMENTAL: RoaringLookupResources returns a roaring64 bitmap of the IDs + /// of the resources of the given type on which the given subject has the + /// given permission. This API is experimental and subject to change or + /// removal. + /// + /// The bitmap is serialized in the RoaringFormatSpec 64-bit portable format + /// (https://github.com/RoaringBitmap/RoaringFormatSpec#extention-for-64-bit-implementations), + /// which OpenSearch consumes directly via a `"value_type": "bitmap"` terms + /// query against a `long` field, once Base64-encoded. + /// + /// The IDs in the bitmap are the resource object IDs exactly as they appear + /// in the relationships: no surrogate or internal ID is introduced, so the + /// caller can use the bitmap directly against its own data (for example, a + /// search index keyed by the same IDs). + /// + /// For this API to be usable, every resource object ID of the requested type + /// must be a canonical decimal integer that fits in 44 bits -- at most + /// 17592186044415 (2^44 - 1). Canonical means the string round-trips through + /// uint64 formatting unchanged: `document:007` and `document:7` are distinct + /// objects that would collide as the integer 7, so non-canonical IDs are + /// rejected. If any resource object ID violates either rule, the call fails + /// with FAILED_PRECONDITION rather than returning a partial bitmap, since a + /// bitmap that is quietly too small is a wrong authorization answer. When the + /// permission relates a type to itself (for example `group#member` looked up + /// for a `group#member` subject), the subject is one of its own resources, so + /// the subject's object ID is held to the same rules and can itself be the ID + /// named in that error. + /// + /// Response size: the whole bitmap is returned in a single unary message, and + /// most gRPC clients default to refusing messages larger than 4 MiB. Roaring + /// is compact -- a million sequential IDs encode in a few hundred bytes -- but + /// sparse IDs cost close to 10 bytes each, so a result of more than roughly + /// 400,000 widely-spread IDs can exceed that default and fail on the CLIENT + /// side with RESOURCE_EXHAUSTED ("received message larger than max"). This is + /// a limit of the caller's own gRPC configuration, not of the service: raise + /// it to match the largest result you expect (in Go, + /// grpc.WithDefaultCallOptions(grpc.MaxCallRecvMsgSize(n)); other languages + /// have an equivalent channel option). The `cardinality` field is returned so + /// callers can see how large a result is once received; no server-side result + /// limit is applied. + /// + /// The request to send to the server. + /// The options for the call. + /// The response received from the server. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + public virtual global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesResponse ExperimentalRoaringLookupResources(global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest request, grpc::CallOptions options) + { + return CallInvoker.BlockingUnaryCall(__Method_ExperimentalRoaringLookupResources, null, options, request); + } + /// + /// EXPERIMENTAL: RoaringLookupResources returns a roaring64 bitmap of the IDs + /// of the resources of the given type on which the given subject has the + /// given permission. This API is experimental and subject to change or + /// removal. + /// + /// The bitmap is serialized in the RoaringFormatSpec 64-bit portable format + /// (https://github.com/RoaringBitmap/RoaringFormatSpec#extention-for-64-bit-implementations), + /// which OpenSearch consumes directly via a `"value_type": "bitmap"` terms + /// query against a `long` field, once Base64-encoded. + /// + /// The IDs in the bitmap are the resource object IDs exactly as they appear + /// in the relationships: no surrogate or internal ID is introduced, so the + /// caller can use the bitmap directly against its own data (for example, a + /// search index keyed by the same IDs). + /// + /// For this API to be usable, every resource object ID of the requested type + /// must be a canonical decimal integer that fits in 44 bits -- at most + /// 17592186044415 (2^44 - 1). Canonical means the string round-trips through + /// uint64 formatting unchanged: `document:007` and `document:7` are distinct + /// objects that would collide as the integer 7, so non-canonical IDs are + /// rejected. If any resource object ID violates either rule, the call fails + /// with FAILED_PRECONDITION rather than returning a partial bitmap, since a + /// bitmap that is quietly too small is a wrong authorization answer. When the + /// permission relates a type to itself (for example `group#member` looked up + /// for a `group#member` subject), the subject is one of its own resources, so + /// the subject's object ID is held to the same rules and can itself be the ID + /// named in that error. + /// + /// Response size: the whole bitmap is returned in a single unary message, and + /// most gRPC clients default to refusing messages larger than 4 MiB. Roaring + /// is compact -- a million sequential IDs encode in a few hundred bytes -- but + /// sparse IDs cost close to 10 bytes each, so a result of more than roughly + /// 400,000 widely-spread IDs can exceed that default and fail on the CLIENT + /// side with RESOURCE_EXHAUSTED ("received message larger than max"). This is + /// a limit of the caller's own gRPC configuration, not of the service: raise + /// it to match the largest result you expect (in Go, + /// grpc.WithDefaultCallOptions(grpc.MaxCallRecvMsgSize(n)); other languages + /// have an equivalent channel option). The `cardinality` field is returned so + /// callers can see how large a result is once received; no server-side result + /// limit is applied. + /// + /// The request to send to the server. + /// The initial metadata to send with the call. This parameter is optional. + /// An optional deadline for the call. The call will be cancelled if deadline is hit. + /// An optional token for canceling the call. + /// The call object. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + public virtual grpc::AsyncUnaryCall ExperimentalRoaringLookupResourcesAsync(global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest request, grpc::Metadata headers = null, global::System.DateTime? deadline = null, global::System.Threading.CancellationToken cancellationToken = default(global::System.Threading.CancellationToken)) + { + return ExperimentalRoaringLookupResourcesAsync(request, new grpc::CallOptions(headers, deadline, cancellationToken)); + } + /// + /// EXPERIMENTAL: RoaringLookupResources returns a roaring64 bitmap of the IDs + /// of the resources of the given type on which the given subject has the + /// given permission. This API is experimental and subject to change or + /// removal. + /// + /// The bitmap is serialized in the RoaringFormatSpec 64-bit portable format + /// (https://github.com/RoaringBitmap/RoaringFormatSpec#extention-for-64-bit-implementations), + /// which OpenSearch consumes directly via a `"value_type": "bitmap"` terms + /// query against a `long` field, once Base64-encoded. + /// + /// The IDs in the bitmap are the resource object IDs exactly as they appear + /// in the relationships: no surrogate or internal ID is introduced, so the + /// caller can use the bitmap directly against its own data (for example, a + /// search index keyed by the same IDs). + /// + /// For this API to be usable, every resource object ID of the requested type + /// must be a canonical decimal integer that fits in 44 bits -- at most + /// 17592186044415 (2^44 - 1). Canonical means the string round-trips through + /// uint64 formatting unchanged: `document:007` and `document:7` are distinct + /// objects that would collide as the integer 7, so non-canonical IDs are + /// rejected. If any resource object ID violates either rule, the call fails + /// with FAILED_PRECONDITION rather than returning a partial bitmap, since a + /// bitmap that is quietly too small is a wrong authorization answer. When the + /// permission relates a type to itself (for example `group#member` looked up + /// for a `group#member` subject), the subject is one of its own resources, so + /// the subject's object ID is held to the same rules and can itself be the ID + /// named in that error. + /// + /// Response size: the whole bitmap is returned in a single unary message, and + /// most gRPC clients default to refusing messages larger than 4 MiB. Roaring + /// is compact -- a million sequential IDs encode in a few hundred bytes -- but + /// sparse IDs cost close to 10 bytes each, so a result of more than roughly + /// 400,000 widely-spread IDs can exceed that default and fail on the CLIENT + /// side with RESOURCE_EXHAUSTED ("received message larger than max"). This is + /// a limit of the caller's own gRPC configuration, not of the service: raise + /// it to match the largest result you expect (in Go, + /// grpc.WithDefaultCallOptions(grpc.MaxCallRecvMsgSize(n)); other languages + /// have an equivalent channel option). The `cardinality` field is returned so + /// callers can see how large a result is once received; no server-side result + /// limit is applied. + /// + /// The request to send to the server. + /// The options for the call. + /// The call object. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + public virtual grpc::AsyncUnaryCall ExperimentalRoaringLookupResourcesAsync(global::Authzed.Api.Materialize.V0.ExperimentalRoaringLookupResourcesRequest request, grpc::CallOptions options) + { + return CallInvoker.AsyncUnaryCall(__Method_ExperimentalRoaringLookupResources, null, options, request); + } + /// Creates a new instance of client from given ClientBaseConfiguration. + [global::System.CodeDom.Compiler.GeneratedCode("grpc_csharp_plugin", null)] + protected override RoaringLookupResourcesServiceClient NewInstance(ClientBaseConfiguration configuration) + { + return new RoaringLookupResourcesServiceClient(configuration); + } + } + + } +} +#endregion diff --git a/src/Authzed.Net/Authzed/Api/V1/PermissionService.cs b/src/Authzed.Net/Authzed/Api/V1/PermissionService.cs index dd2f0f6..edb914e 100644 --- a/src/Authzed.Net/Authzed/Api/V1/PermissionService.cs +++ b/src/Authzed.Net/Authzed/Api/V1/PermissionService.cs @@ -93,7 +93,7 @@ static PermissionServiceReflection() { "aW9uX21ldGFkYXRhGAMgASgLMhcuZ29vZ2xlLnByb3RvYnVmLlN0cnVjdEIO", "+kIFigECEAC6SAPIAQBSG29wdGlvbmFsVHJhbnNhY3Rpb25NZXRhZGF0YSJV", "ChpXcml0ZVJlbGF0aW9uc2hpcHNSZXNwb25zZRI3Cgp3cml0dGVuX2F0GAEg", - "ASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5SCXdyaXR0ZW5BdCLSAwoa", + "ASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5SCXdyaXR0ZW5BdCKTBAoa", "RGVsZXRlUmVsYXRpb25zaGlwc1JlcXVlc3QSYwoTcmVsYXRpb25zaGlwX2Zp", "bHRlchgBIAEoCzIiLmF1dGh6ZWQuYXBpLnYxLlJlbGF0aW9uc2hpcEZpbHRl", "ckIO+kIFigECEAG6SAPIAQFSEnJlbGF0aW9uc2hpcEZpbHRlchJiChZvcHRp", @@ -104,204 +104,207 @@ static PermissionServiceReflection() { "b25zGAQgASgIUh1vcHRpb25hbEFsbG93UGFydGlhbERlbGV0aW9ucxJrCh1v", "cHRpb25hbF90cmFuc2FjdGlvbl9tZXRhZGF0YRgFIAEoCzIXLmdvb2dsZS5w", "cm90b2J1Zi5TdHJ1Y3RCDvpCBYoBAhAAukgDyAEAUhtvcHRpb25hbFRyYW5z", - "YWN0aW9uTWV0YWRhdGEi9wIKG0RlbGV0ZVJlbGF0aW9uc2hpcHNSZXNwb25z", - "ZRI3CgpkZWxldGVkX2F0GAEgASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9r", - "ZW5SCWRlbGV0ZWRBdBJpChFkZWxldGlvbl9wcm9ncmVzcxgCIAEoDjI8LmF1", - "dGh6ZWQuYXBpLnYxLkRlbGV0ZVJlbGF0aW9uc2hpcHNSZXNwb25zZS5EZWxl", - "dGlvblByb2dyZXNzUhBkZWxldGlvblByb2dyZXNzEj4KG3JlbGF0aW9uc2hp", - "cHNfZGVsZXRlZF9jb3VudBgDIAEoBFIZcmVsYXRpb25zaGlwc0RlbGV0ZWRD", - "b3VudCJ0ChBEZWxldGlvblByb2dyZXNzEiEKHURFTEVUSU9OX1BST0dSRVNT", - "X1VOU1BFQ0lGSUVEEAASHgoaREVMRVRJT05fUFJPR1JFU1NfQ09NUExFVEUQ", - "ARIdChlERUxFVElPTl9QUk9HUkVTU19QQVJUSUFMEAIizAMKFkNoZWNrUGVy", - "bWlzc2lvblJlcXVlc3QSPQoLY29uc2lzdGVuY3kYASABKAsyGy5hdXRoemVk", - "LmFwaS52MS5Db25zaXN0ZW5jeVILY29uc2lzdGVuY3kSSwoIcmVzb3VyY2UY", - "AiABKAsyHy5hdXRoemVkLmFwaS52MS5PYmplY3RSZWZlcmVuY2VCDvpCBYoB", - "AhABukgDyAEBUghyZXNvdXJjZRJ0CgpwZXJtaXNzaW9uGAMgASgJQlT6Qidy", - "JShAMiFeKFthLXpdW2EtejAtOV9dezEsNjJ9W2EtejAtOV0pPyS6SCdyJShA", - "MiFeKFthLXpdW2EtejAtOV9dezEsNjJ9W2EtejAtOV0pPyRSCnBlcm1pc3Np", - "b24SSgoHc3ViamVjdBgEIAEoCzIgLmF1dGh6ZWQuYXBpLnYxLlN1YmplY3RS", - "ZWZlcmVuY2VCDvpCBYoBAhABukgDyAEBUgdzdWJqZWN0EkEKB2NvbnRleHQY", - "BSABKAsyFy5nb29nbGUucHJvdG9idWYuU3RydWN0Qg76QgWKAQIQALpIA8gB", - "AFIHY29udGV4dBIhCgx3aXRoX3RyYWNpbmcYBiABKAhSC3dpdGhUcmFjaW5n", - "Iu0EChdDaGVja1Blcm1pc3Npb25SZXNwb25zZRJHCgpjaGVja2VkX2F0GAEg", - "ASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5CDvpCBYoBAhAAukgDyAEA", - "UgljaGVja2VkQXQSdAoOcGVybWlzc2lvbnNoaXAYAiABKA4yNi5hdXRoemVk", - "LmFwaS52MS5DaGVja1Blcm1pc3Npb25SZXNwb25zZS5QZXJtaXNzaW9uc2hp", - "cEIU+kIHggEEEAEgALpIB4IBBBABIABSDnBlcm1pc3Npb25zaGlwEmEKE3Bh", - "cnRpYWxfY2F2ZWF0X2luZm8YAyABKAsyIS5hdXRoemVkLmFwaS52MS5QYXJ0", - "aWFsQ2F2ZWF0SW5mb0IO+kIFigECEAC6SAPIAQBSEXBhcnRpYWxDYXZlYXRJ", - "bmZvEkEKC2RlYnVnX3RyYWNlGAQgASgLMiAuYXV0aHplZC5hcGkudjEuRGVi", - "dWdJbmZvcm1hdGlvblIKZGVidWdUcmFjZRJKChNvcHRpb25hbF9leHBpcmVz", - "X2F0GAUgASgLMhouZ29vZ2xlLnByb3RvYnVmLlRpbWVzdGFtcFIRb3B0aW9u", - "YWxFeHBpcmVzQXQioAEKDlBlcm1pc3Npb25zaGlwEh4KGlBFUk1JU1NJT05T", - "SElQX1VOU1BFQ0lGSUVEEAASIAocUEVSTUlTU0lPTlNISVBfTk9fUEVSTUlT", - "U0lPThABEiEKHVBFUk1JU1NJT05TSElQX0hBU19QRVJNSVNTSU9OEAISKQol", - "UEVSTUlTU0lPTlNISVBfQ09ORElUSU9OQUxfUEVSTUlTU0lPThADItUBChtD", - "aGVja0J1bGtQZXJtaXNzaW9uc1JlcXVlc3QSPQoLY29uc2lzdGVuY3kYASAB", - "KAsyGy5hdXRoemVkLmFwaS52MS5Db25zaXN0ZW5jeVILY29uc2lzdGVuY3kS", - "VAoFaXRlbXMYAiADKAsyLy5hdXRoemVkLmFwaS52MS5DaGVja0J1bGtQZXJt", - "aXNzaW9uc1JlcXVlc3RJdGVtQg36QgqSAQciBYoBAhABUgVpdGVtcxIhCgx3", - "aXRoX3RyYWNpbmcYAyABKAhSC3dpdGhUcmFjaW5nIvMCCh9DaGVja0J1bGtQ", - "ZXJtaXNzaW9uc1JlcXVlc3RJdGVtEksKCHJlc291cmNlGAEgASgLMh8uYXV0", - "aHplZC5hcGkudjEuT2JqZWN0UmVmZXJlbmNlQg76QgWKAQIQAbpIA8gBAVII", - "cmVzb3VyY2USdAoKcGVybWlzc2lvbhgCIAEoCUJU+kInciUoQDIhXihbYS16", - "XVthLXowLTlfXXsxLDYyfVthLXowLTldKT8kukgnciUoQDIhXihbYS16XVth", - "LXowLTlfXXsxLDYyfVthLXowLTldKT8kUgpwZXJtaXNzaW9uEkoKB3N1Ympl", - "Y3QYAyABKAsyIC5hdXRoemVkLmFwaS52MS5TdWJqZWN0UmVmZXJlbmNlQg76", - "QgWKAQIQAbpIA8gBAVIHc3ViamVjdBJBCgdjb250ZXh0GAQgASgLMhcuZ29v", - "Z2xlLnByb3RvYnVmLlN0cnVjdEIO+kIFigECEAC6SAPIAQBSB2NvbnRleHQi", - "tgEKHENoZWNrQnVsa1Blcm1pc3Npb25zUmVzcG9uc2USRwoKY2hlY2tlZF9h", - "dBgBIAEoCzIYLmF1dGh6ZWQuYXBpLnYxLlplZFRva2VuQg76QgWKAQIQALpI", - "A8gBAFIJY2hlY2tlZEF0Ek0KBXBhaXJzGAIgAygLMiguYXV0aHplZC5hcGku", - "djEuQ2hlY2tCdWxrUGVybWlzc2lvbnNQYWlyQg36QgqSAQciBYoBAhABUgVw", - "YWlycyLlAQoYQ2hlY2tCdWxrUGVybWlzc2lvbnNQYWlyEkkKB3JlcXVlc3QY", - "ASABKAsyLy5hdXRoemVkLmFwaS52MS5DaGVja0J1bGtQZXJtaXNzaW9uc1Jl", - "cXVlc3RJdGVtUgdyZXF1ZXN0EkYKBGl0ZW0YAiABKAsyMC5hdXRoemVkLmFw", - "aS52MS5DaGVja0J1bGtQZXJtaXNzaW9uc1Jlc3BvbnNlSXRlbUgAUgRpdGVt", - "EioKBWVycm9yGAMgASgLMhIuZ29vZ2xlLnJwYy5TdGF0dXNIAFIFZXJyb3JC", - "CgoIcmVzcG9uc2UivgIKIENoZWNrQnVsa1Blcm1pc3Npb25zUmVzcG9uc2VJ", - "dGVtEnQKDnBlcm1pc3Npb25zaGlwGAEgASgOMjYuYXV0aHplZC5hcGkudjEu", - "Q2hlY2tQZXJtaXNzaW9uUmVzcG9uc2UuUGVybWlzc2lvbnNoaXBCFPpCB4IB", - "BBABIAC6SAeCAQQQASAAUg5wZXJtaXNzaW9uc2hpcBJhChNwYXJ0aWFsX2Nh", - "dmVhdF9pbmZvGAIgASgLMiEuYXV0aHplZC5hcGkudjEuUGFydGlhbENhdmVh", - "dEluZm9CDvpCBYoBAhAAukgDyAEAUhFwYXJ0aWFsQ2F2ZWF0SW5mbxJBCgtk", - "ZWJ1Z190cmFjZRgDIAEoCzIgLmF1dGh6ZWQuYXBpLnYxLkRlYnVnSW5mb3Jt", - "YXRpb25SCmRlYnVnVHJhY2UinwIKG0V4cGFuZFBlcm1pc3Npb25UcmVlUmVx", - "dWVzdBI9Cgtjb25zaXN0ZW5jeRgBIAEoCzIbLmF1dGh6ZWQuYXBpLnYxLkNv", - "bnNpc3RlbmN5Ugtjb25zaXN0ZW5jeRJLCghyZXNvdXJjZRgCIAEoCzIfLmF1", - "dGh6ZWQuYXBpLnYxLk9iamVjdFJlZmVyZW5jZUIO+kIFigECEAG6SAPIAQFS", - "CHJlc291cmNlEnQKCnBlcm1pc3Npb24YAyABKAlCVPpCJ3IlKEAyIV4oW2Et", - "el1bYS16MC05X117MSw2Mn1bYS16MC05XSk/JLpIJ3IlKEAyIV4oW2Etel1b", - "YS16MC05X117MSw2Mn1bYS16MC05XSk/JFIKcGVybWlzc2lvbiKiAQocRXhw", - "YW5kUGVybWlzc2lvblRyZWVSZXNwb25zZRI5CgtleHBhbmRlZF9hdBgBIAEo", - "CzIYLmF1dGh6ZWQuYXBpLnYxLlplZFRva2VuUgpleHBhbmRlZEF0EkcKCXRy", - "ZWVfcm9vdBgCIAEoCzIqLmF1dGh6ZWQuYXBpLnYxLlBlcm1pc3Npb25SZWxh", - "dGlvbnNoaXBUcmVlUgh0cmVlUm9vdCKzBQoWTG9va3VwUmVzb3VyY2VzUmVx", - "dWVzdBI9Cgtjb25zaXN0ZW5jeRgBIAEoCzIbLmF1dGh6ZWQuYXBpLnYxLkNv", - "bnNpc3RlbmN5Ugtjb25zaXN0ZW5jeRLDAQoUcmVzb3VyY2Vfb2JqZWN0X3R5", - "cGUYAiABKAlCkAH6QkVyQyiAATI+XihbYS16XVthLXowLTlfXXsxLDYxfVth", - "LXowLTldLykqW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSS6SEVyQyiA", - "ATI+XihbYS16XVthLXowLTlfXXsxLDYxfVthLXowLTldLykqW2Etel1bYS16", - "MC05X117MSw2Mn1bYS16MC05XSRSEnJlc291cmNlT2JqZWN0VHlwZRJuCgpw", - "ZXJtaXNzaW9uGAMgASgJQk76QiRyIihAMh5eW2Etel1bYS16MC05X117MSw2", - "Mn1bYS16MC05XSS6SCRyIihAMh5eW2Etel1bYS16MC05X117MSw2Mn1bYS16", - "MC05XSRSCnBlcm1pc3Npb24SSgoHc3ViamVjdBgEIAEoCzIgLmF1dGh6ZWQu", - "YXBpLnYxLlN1YmplY3RSZWZlcmVuY2VCDvpCBYoBAhABukgDyAEBUgdzdWJq", - "ZWN0EkEKB2NvbnRleHQYBSABKAsyFy5nb29nbGUucHJvdG9idWYuU3RydWN0", - "Qg76QgWKAQIQALpIA8gBAFIHY29udGV4dBI1Cg5vcHRpb25hbF9saW1pdBgG", - "IAEoDUIO+kIEKgIoALpIBCoCKABSDW9wdGlvbmFsTGltaXQSPwoPb3B0aW9u", - "YWxfY3Vyc29yGAcgASgLMhYuYXV0aHplZC5hcGkudjEuQ3Vyc29yUg5vcHRp", - "b25hbEN1cnNvchIdCgp3aXRoX2RlYnVnGAggASgIUgl3aXRoRGVidWcikgMK", - "F0xvb2t1cFJlc291cmNlc1Jlc3BvbnNlEjoKDGxvb2tlZF91cF9hdBgBIAEo", - "CzIYLmF1dGh6ZWQuYXBpLnYxLlplZFRva2VuUgpsb29rZWRVcEF0EiwKEnJl", - "c291cmNlX29iamVjdF9pZBgCIAEoCVIQcmVzb3VyY2VPYmplY3RJZBJiCg5w", - "ZXJtaXNzaW9uc2hpcBgDIAEoDjIkLmF1dGh6ZWQuYXBpLnYxLkxvb2t1cFBl", - "cm1pc3Npb25zaGlwQhT6QgeCAQQQASAAukgHggEEEAEgAFIOcGVybWlzc2lv", - "bnNoaXASYQoTcGFydGlhbF9jYXZlYXRfaW5mbxgEIAEoCzIhLmF1dGh6ZWQu", - "YXBpLnYxLlBhcnRpYWxDYXZlYXRJbmZvQg76QgWKAQIQALpIA8gBAFIRcGFy", - "dGlhbENhdmVhdEluZm8SRgoTYWZ0ZXJfcmVzdWx0X2N1cnNvchgFIAEoCzIW", - "LmF1dGh6ZWQuYXBpLnYxLkN1cnNvclIRYWZ0ZXJSZXN1bHRDdXJzb3IinAgK", - "FUxvb2t1cFN1YmplY3RzUmVxdWVzdBI9Cgtjb25zaXN0ZW5jeRgBIAEoCzIb", - "LmF1dGh6ZWQuYXBpLnYxLkNvbnNpc3RlbmN5Ugtjb25zaXN0ZW5jeRJLCghy", - "ZXNvdXJjZRgCIAEoCzIfLmF1dGh6ZWQuYXBpLnYxLk9iamVjdFJlZmVyZW5j", - "ZUIO+kIFigECEAG6SAPIAQFSCHJlc291cmNlEnQKCnBlcm1pc3Npb24YAyAB", - "KAlCVPpCJ3IlKEAyIV4oW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSk/", - "JLpIJ3IlKEAyIV4oW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSk/JFIK", - "cGVybWlzc2lvbhLBAQoTc3ViamVjdF9vYmplY3RfdHlwZRgEIAEoCUKQAfpC", - "RXJDKIABMj5eKFthLXpdW2EtejAtOV9dezEsNjF9W2EtejAtOV0vKSpbYS16", - "XVthLXowLTlfXXsxLDYyfVthLXowLTldJLpIRXJDKIABMj5eKFthLXpdW2Et", - "ejAtOV9dezEsNjF9W2EtejAtOV0vKSpbYS16XVthLXowLTlfXXsxLDYyfVth", - "LXowLTldJFIRc3ViamVjdE9iamVjdFR5cGUSkAEKGW9wdGlvbmFsX3N1Ympl", - "Y3RfcmVsYXRpb24YBSABKAlCVPpCJ3IlKEAyIV4oW2Etel1bYS16MC05X117", - "MSw2Mn1bYS16MC05XSk/JLpIJ3IlKEAyIV4oW2Etel1bYS16MC05X117MSw2", - "Mn1bYS16MC05XSk/JFIXb3B0aW9uYWxTdWJqZWN0UmVsYXRpb24SQQoHY29u", - "dGV4dBgGIAEoCzIXLmdvb2dsZS5wcm90b2J1Zi5TdHJ1Y3RCDvpCBYoBAhAA", - "ukgDyAEAUgdjb250ZXh0EkYKF29wdGlvbmFsX2NvbmNyZXRlX2xpbWl0GAcg", - "ASgNQg76QgQqAigAukgEKgIoAFIVb3B0aW9uYWxDb25jcmV0ZUxpbWl0Ej8K", - "D29wdGlvbmFsX2N1cnNvchgIIAEoCzIWLmF1dGh6ZWQuYXBpLnYxLkN1cnNv", - "clIOb3B0aW9uYWxDdXJzb3ISXQoPd2lsZGNhcmRfb3B0aW9uGAkgASgOMjQu", - "YXV0aHplZC5hcGkudjEuTG9va3VwU3ViamVjdHNSZXF1ZXN0LldpbGRjYXJk", - "T3B0aW9uUg53aWxkY2FyZE9wdGlvbiJ/Cg5XaWxkY2FyZE9wdGlvbhIfChtX", - "SUxEQ0FSRF9PUFRJT05fVU5TUEVDSUZJRUQQABIlCiFXSUxEQ0FSRF9PUFRJ", - "T05fSU5DTFVERV9XSUxEQ0FSRFMQARIlCiFXSUxEQ0FSRF9PUFRJT05fRVhD", - "TFVERV9XSUxEQ0FSRFMQAiLWBAoWTG9va3VwU3ViamVjdHNSZXNwb25zZRI6", - "Cgxsb29rZWRfdXBfYXQYASABKAsyGC5hdXRoemVkLmFwaS52MS5aZWRUb2tl", - "blIKbG9va2VkVXBBdBIuChFzdWJqZWN0X29iamVjdF9pZBgCIAEoCUICGAFS", - "D3N1YmplY3RPYmplY3RJZBI0ChRleGNsdWRlZF9zdWJqZWN0X2lkcxgDIAMo", - "CUICGAFSEmV4Y2x1ZGVkU3ViamVjdElkcxJkCg5wZXJtaXNzaW9uc2hpcBgE", - "IAEoDjIkLmF1dGh6ZWQuYXBpLnYxLkxvb2t1cFBlcm1pc3Npb25zaGlwQhYY", - "AfpCB4IBBBABIAC6SAeCAQQQASAAUg5wZXJtaXNzaW9uc2hpcBJjChNwYXJ0", - "aWFsX2NhdmVhdF9pbmZvGAUgASgLMiEuYXV0aHplZC5hcGkudjEuUGFydGlh", - "bENhdmVhdEluZm9CEBgB+kIFigECEAC6SAPIAQBSEXBhcnRpYWxDYXZlYXRJ", - "bmZvEjkKB3N1YmplY3QYBiABKAsyHy5hdXRoemVkLmFwaS52MS5SZXNvbHZl", - "ZFN1YmplY3RSB3N1YmplY3QSTAoRZXhjbHVkZWRfc3ViamVjdHMYByADKAsy", - "Hy5hdXRoemVkLmFwaS52MS5SZXNvbHZlZFN1YmplY3RSEGV4Y2x1ZGVkU3Vi", - "amVjdHMSRgoTYWZ0ZXJfcmVzdWx0X2N1cnNvchgIIAEoCzIWLmF1dGh6ZWQu", - "YXBpLnYxLkN1cnNvclIRYWZ0ZXJSZXN1bHRDdXJzb3IihAIKD1Jlc29sdmVk", - "U3ViamVjdBIqChFzdWJqZWN0X29iamVjdF9pZBgBIAEoCVIPc3ViamVjdE9i", - "amVjdElkEmIKDnBlcm1pc3Npb25zaGlwGAIgASgOMiQuYXV0aHplZC5hcGku", - "djEuTG9va3VwUGVybWlzc2lvbnNoaXBCFPpCB4IBBBABIAC6SAeCAQQQASAA", - "Ug5wZXJtaXNzaW9uc2hpcBJhChNwYXJ0aWFsX2NhdmVhdF9pbmZvGAMgASgL", - "MiEuYXV0aHplZC5hcGkudjEuUGFydGlhbENhdmVhdEluZm9CDvpCBYoBAhAA", - "ukgDyAEAUhFwYXJ0aWFsQ2F2ZWF0SW5mbyJzCh5JbXBvcnRCdWxrUmVsYXRp", - "b25zaGlwc1JlcXVlc3QSUQoNcmVsYXRpb25zaGlwcxgBIAMoCzIcLmF1dGh6", - "ZWQuYXBpLnYxLlJlbGF0aW9uc2hpcEIN+kIKkgEHIgWKAQIQAVINcmVsYXRp", - "b25zaGlwcyJACh9JbXBvcnRCdWxrUmVsYXRpb25zaGlwc1Jlc3BvbnNlEh0K", - "Cm51bV9sb2FkZWQYASABKARSCW51bUxvYWRlZCK9AgoeRXhwb3J0QnVsa1Jl", - "bGF0aW9uc2hpcHNSZXF1ZXN0Ej0KC2NvbnNpc3RlbmN5GAEgASgLMhsuYXV0", - "aHplZC5hcGkudjEuQ29uc2lzdGVuY3lSC2NvbnNpc3RlbmN5EjUKDm9wdGlv", - "bmFsX2xpbWl0GAIgASgNQg76QgQqAigAukgEKgIoAFINb3B0aW9uYWxMaW1p", - "dBI/Cg9vcHRpb25hbF9jdXJzb3IYAyABKAsyFi5hdXRoemVkLmFwaS52MS5D", - "dXJzb3JSDm9wdGlvbmFsQ3Vyc29yEmQKHG9wdGlvbmFsX3JlbGF0aW9uc2hp", - "cF9maWx0ZXIYBCABKAsyIi5hdXRoemVkLmFwaS52MS5SZWxhdGlvbnNoaXBG", - "aWx0ZXJSGm9wdGlvbmFsUmVsYXRpb25zaGlwRmlsdGVyIq0BCh9FeHBvcnRC", - "dWxrUmVsYXRpb25zaGlwc1Jlc3BvbnNlEkYKE2FmdGVyX3Jlc3VsdF9jdXJz", - "b3IYASABKAsyFi5hdXRoemVkLmFwaS52MS5DdXJzb3JSEWFmdGVyUmVzdWx0", - "Q3Vyc29yEkIKDXJlbGF0aW9uc2hpcHMYAiADKAsyHC5hdXRoemVkLmFwaS52", - "MS5SZWxhdGlvbnNoaXBSDXJlbGF0aW9uc2hpcHMqmQEKFExvb2t1cFBlcm1p", - "c3Npb25zaGlwEiUKIUxPT0tVUF9QRVJNSVNTSU9OU0hJUF9VTlNQRUNJRklF", - "RBAAEigKJExPT0tVUF9QRVJNSVNTSU9OU0hJUF9IQVNfUEVSTUlTU0lPThAB", - "EjAKLExPT0tVUF9QRVJNSVNTSU9OU0hJUF9DT05ESVRJT05BTF9QRVJNSVNT", - "SU9OEAIyig0KElBlcm1pc3Npb25zU2VydmljZRKdAQoRUmVhZFJlbGF0aW9u", - "c2hpcHMSKC5hdXRoemVkLmFwaS52MS5SZWFkUmVsYXRpb25zaGlwc1JlcXVl", - "c3QaKS5hdXRoemVkLmFwaS52MS5SZWFkUmVsYXRpb25zaGlwc1Jlc3BvbnNl", - "IjGSQQ0KC1Blcm1pc3Npb25zgtPkkwIbIhYvdjEvcmVsYXRpb25zaGlwcy9y", - "ZWFkOgEqMAESnwEKEldyaXRlUmVsYXRpb25zaGlwcxIpLmF1dGh6ZWQuYXBp", - "LnYxLldyaXRlUmVsYXRpb25zaGlwc1JlcXVlc3QaKi5hdXRoemVkLmFwaS52", - "MS5Xcml0ZVJlbGF0aW9uc2hpcHNSZXNwb25zZSIykkENCgtQZXJtaXNzaW9u", - "c4LT5JMCHCIXL3YxL3JlbGF0aW9uc2hpcHMvd3JpdGU6ASoSowEKE0RlbGV0", - "ZVJlbGF0aW9uc2hpcHMSKi5hdXRoemVkLmFwaS52MS5EZWxldGVSZWxhdGlv", - "bnNoaXBzUmVxdWVzdBorLmF1dGh6ZWQuYXBpLnYxLkRlbGV0ZVJlbGF0aW9u", - "c2hpcHNSZXNwb25zZSIzkkENCgtQZXJtaXNzaW9uc4LT5JMCHSIYL3YxL3Jl", - "bGF0aW9uc2hpcHMvZGVsZXRlOgEqEpQBCg9DaGVja1Blcm1pc3Npb24SJi5h", - "dXRoemVkLmFwaS52MS5DaGVja1Blcm1pc3Npb25SZXF1ZXN0GicuYXV0aHpl", - "ZC5hcGkudjEuQ2hlY2tQZXJtaXNzaW9uUmVzcG9uc2UiMJJBDQoLUGVybWlz", - "c2lvbnOC0+STAhoiFS92MS9wZXJtaXNzaW9ucy9jaGVjazoBKhKnAQoUQ2hl", - "Y2tCdWxrUGVybWlzc2lvbnMSKy5hdXRoemVkLmFwaS52MS5DaGVja0J1bGtQ", - "ZXJtaXNzaW9uc1JlcXVlc3QaLC5hdXRoemVkLmFwaS52MS5DaGVja0J1bGtQ", - "ZXJtaXNzaW9uc1Jlc3BvbnNlIjSSQQ0KC1Blcm1pc3Npb25zgtPkkwIeIhkv", - "djEvcGVybWlzc2lvbnMvY2hlY2tidWxrOgEqEqQBChRFeHBhbmRQZXJtaXNz", - "aW9uVHJlZRIrLmF1dGh6ZWQuYXBpLnYxLkV4cGFuZFBlcm1pc3Npb25UcmVl", - "UmVxdWVzdBosLmF1dGh6ZWQuYXBpLnYxLkV4cGFuZFBlcm1pc3Npb25UcmVl", - "UmVzcG9uc2UiMZJBDQoLUGVybWlzc2lvbnOC0+STAhsiFi92MS9wZXJtaXNz", - "aW9ucy9leHBhbmQ6ASoSmgEKD0xvb2t1cFJlc291cmNlcxImLmF1dGh6ZWQu", - "YXBpLnYxLkxvb2t1cFJlc291cmNlc1JlcXVlc3QaJy5hdXRoemVkLmFwaS52", - "MS5Mb29rdXBSZXNvdXJjZXNSZXNwb25zZSI0kkENCgtQZXJtaXNzaW9uc4LT", - "5JMCHiIZL3YxL3Blcm1pc3Npb25zL3Jlc291cmNlczoBKjABEpYBCg5Mb29r", - "dXBTdWJqZWN0cxIlLmF1dGh6ZWQuYXBpLnYxLkxvb2t1cFN1YmplY3RzUmVx", - "dWVzdBomLmF1dGh6ZWQuYXBpLnYxLkxvb2t1cFN1YmplY3RzUmVzcG9uc2Ui", - "M5JBDQoLUGVybWlzc2lvbnOC0+STAh0iGC92MS9wZXJtaXNzaW9ucy9zdWJq", - "ZWN0czoBKjABErUBChdJbXBvcnRCdWxrUmVsYXRpb25zaGlwcxIuLmF1dGh6", - "ZWQuYXBpLnYxLkltcG9ydEJ1bGtSZWxhdGlvbnNoaXBzUmVxdWVzdBovLmF1", - "dGh6ZWQuYXBpLnYxLkltcG9ydEJ1bGtSZWxhdGlvbnNoaXBzUmVzcG9uc2Ui", - "N5JBDQoLUGVybWlzc2lvbnOC0+STAiEiHC92MS9yZWxhdGlvbnNoaXBzL2lt", - "cG9ydGJ1bGs6ASooARK1AQoXRXhwb3J0QnVsa1JlbGF0aW9uc2hpcHMSLi5h", - "dXRoemVkLmFwaS52MS5FeHBvcnRCdWxrUmVsYXRpb25zaGlwc1JlcXVlc3Qa", - "Ly5hdXRoemVkLmFwaS52MS5FeHBvcnRCdWxrUmVsYXRpb25zaGlwc1Jlc3Bv", - "bnNlIjeSQQ0KC1Blcm1pc3Npb25zgtPkkwIhIhwvdjEvcmVsYXRpb25zaGlw", - "cy9leHBvcnRidWxrOgEqMAFCSgoSY29tLmF1dGh6ZWQuYXBpLnYxUAFaMmdp", - "dGh1Yi5jb20vYXV0aHplZC9hdXRoemVkLWdvL3Byb3RvL2F1dGh6ZWQvYXBp", - "L3YxYgZwcm90bzM=")); + "YWN0aW9uTWV0YWRhdGESPwoPb3B0aW9uYWxfY3Vyc29yGAYgASgLMhYuYXV0", + "aHplZC5hcGkudjEuQ3Vyc29yUg5vcHRpb25hbEN1cnNvciK/AwobRGVsZXRl", + "UmVsYXRpb25zaGlwc1Jlc3BvbnNlEjcKCmRlbGV0ZWRfYXQYASABKAsyGC5h", + "dXRoemVkLmFwaS52MS5aZWRUb2tlblIJZGVsZXRlZEF0EmkKEWRlbGV0aW9u", + "X3Byb2dyZXNzGAIgASgOMjwuYXV0aHplZC5hcGkudjEuRGVsZXRlUmVsYXRp", + "b25zaGlwc1Jlc3BvbnNlLkRlbGV0aW9uUHJvZ3Jlc3NSEGRlbGV0aW9uUHJv", + "Z3Jlc3MSPgobcmVsYXRpb25zaGlwc19kZWxldGVkX2NvdW50GAMgASgEUhly", + "ZWxhdGlvbnNoaXBzRGVsZXRlZENvdW50EkYKE2FmdGVyX3Jlc3VsdF9jdXJz", + "b3IYBCABKAsyFi5hdXRoemVkLmFwaS52MS5DdXJzb3JSEWFmdGVyUmVzdWx0", + "Q3Vyc29yInQKEERlbGV0aW9uUHJvZ3Jlc3MSIQodREVMRVRJT05fUFJPR1JF", + "U1NfVU5TUEVDSUZJRUQQABIeChpERUxFVElPTl9QUk9HUkVTU19DT01QTEVU", + "RRABEh0KGURFTEVUSU9OX1BST0dSRVNTX1BBUlRJQUwQAiLMAwoWQ2hlY2tQ", + "ZXJtaXNzaW9uUmVxdWVzdBI9Cgtjb25zaXN0ZW5jeRgBIAEoCzIbLmF1dGh6", + "ZWQuYXBpLnYxLkNvbnNpc3RlbmN5Ugtjb25zaXN0ZW5jeRJLCghyZXNvdXJj", + "ZRgCIAEoCzIfLmF1dGh6ZWQuYXBpLnYxLk9iamVjdFJlZmVyZW5jZUIO+kIF", + "igECEAG6SAPIAQFSCHJlc291cmNlEnQKCnBlcm1pc3Npb24YAyABKAlCVPpC", + "J3IlKEAyIV4oW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSk/JLpIJ3Il", + "KEAyIV4oW2Etel1bYS16MC05X117MSw2Mn1bYS16MC05XSk/JFIKcGVybWlz", + "c2lvbhJKCgdzdWJqZWN0GAQgASgLMiAuYXV0aHplZC5hcGkudjEuU3ViamVj", + "dFJlZmVyZW5jZUIO+kIFigECEAG6SAPIAQFSB3N1YmplY3QSQQoHY29udGV4", + "dBgFIAEoCzIXLmdvb2dsZS5wcm90b2J1Zi5TdHJ1Y3RCDvpCBYoBAhAAukgD", + "yAEAUgdjb250ZXh0EiEKDHdpdGhfdHJhY2luZxgGIAEoCFILd2l0aFRyYWNp", + "bmci7QQKF0NoZWNrUGVybWlzc2lvblJlc3BvbnNlEkcKCmNoZWNrZWRfYXQY", + "ASABKAsyGC5hdXRoemVkLmFwaS52MS5aZWRUb2tlbkIO+kIFigECEAC6SAPI", + "AQBSCWNoZWNrZWRBdBJ0Cg5wZXJtaXNzaW9uc2hpcBgCIAEoDjI2LmF1dGh6", + "ZWQuYXBpLnYxLkNoZWNrUGVybWlzc2lvblJlc3BvbnNlLlBlcm1pc3Npb25z", + "aGlwQhT6QgeCAQQQASAAukgHggEEEAEgAFIOcGVybWlzc2lvbnNoaXASYQoT", + "cGFydGlhbF9jYXZlYXRfaW5mbxgDIAEoCzIhLmF1dGh6ZWQuYXBpLnYxLlBh", + "cnRpYWxDYXZlYXRJbmZvQg76QgWKAQIQALpIA8gBAFIRcGFydGlhbENhdmVh", + "dEluZm8SQQoLZGVidWdfdHJhY2UYBCABKAsyIC5hdXRoemVkLmFwaS52MS5E", + "ZWJ1Z0luZm9ybWF0aW9uUgpkZWJ1Z1RyYWNlEkoKE29wdGlvbmFsX2V4cGly", + "ZXNfYXQYBSABKAsyGi5nb29nbGUucHJvdG9idWYuVGltZXN0YW1wUhFvcHRp", + "b25hbEV4cGlyZXNBdCKgAQoOUGVybWlzc2lvbnNoaXASHgoaUEVSTUlTU0lP", + "TlNISVBfVU5TUEVDSUZJRUQQABIgChxQRVJNSVNTSU9OU0hJUF9OT19QRVJN", + "SVNTSU9OEAESIQodUEVSTUlTU0lPTlNISVBfSEFTX1BFUk1JU1NJT04QAhIp", + "CiVQRVJNSVNTSU9OU0hJUF9DT05ESVRJT05BTF9QRVJNSVNTSU9OEAMi1QEK", + "G0NoZWNrQnVsa1Blcm1pc3Npb25zUmVxdWVzdBI9Cgtjb25zaXN0ZW5jeRgB", + "IAEoCzIbLmF1dGh6ZWQuYXBpLnYxLkNvbnNpc3RlbmN5Ugtjb25zaXN0ZW5j", + "eRJUCgVpdGVtcxgCIAMoCzIvLmF1dGh6ZWQuYXBpLnYxLkNoZWNrQnVsa1Bl", + "cm1pc3Npb25zUmVxdWVzdEl0ZW1CDfpCCpIBByIFigECEAFSBWl0ZW1zEiEK", + "DHdpdGhfdHJhY2luZxgDIAEoCFILd2l0aFRyYWNpbmci8wIKH0NoZWNrQnVs", + "a1Blcm1pc3Npb25zUmVxdWVzdEl0ZW0SSwoIcmVzb3VyY2UYASABKAsyHy5h", + "dXRoemVkLmFwaS52MS5PYmplY3RSZWZlcmVuY2VCDvpCBYoBAhABukgDyAEB", + "UghyZXNvdXJjZRJ0CgpwZXJtaXNzaW9uGAIgASgJQlT6QidyJShAMiFeKFth", + "LXpdW2EtejAtOV9dezEsNjJ9W2EtejAtOV0pPyS6SCdyJShAMiFeKFthLXpd", + "W2EtejAtOV9dezEsNjJ9W2EtejAtOV0pPyRSCnBlcm1pc3Npb24SSgoHc3Vi", + "amVjdBgDIAEoCzIgLmF1dGh6ZWQuYXBpLnYxLlN1YmplY3RSZWZlcmVuY2VC", + "DvpCBYoBAhABukgDyAEBUgdzdWJqZWN0EkEKB2NvbnRleHQYBCABKAsyFy5n", + "b29nbGUucHJvdG9idWYuU3RydWN0Qg76QgWKAQIQALpIA8gBAFIHY29udGV4", + "dCK2AQocQ2hlY2tCdWxrUGVybWlzc2lvbnNSZXNwb25zZRJHCgpjaGVja2Vk", + "X2F0GAEgASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5CDvpCBYoBAhAA", + "ukgDyAEAUgljaGVja2VkQXQSTQoFcGFpcnMYAiADKAsyKC5hdXRoemVkLmFw", + "aS52MS5DaGVja0J1bGtQZXJtaXNzaW9uc1BhaXJCDfpCCpIBByIFigECEAFS", + "BXBhaXJzIuUBChhDaGVja0J1bGtQZXJtaXNzaW9uc1BhaXISSQoHcmVxdWVz", + "dBgBIAEoCzIvLmF1dGh6ZWQuYXBpLnYxLkNoZWNrQnVsa1Blcm1pc3Npb25z", + "UmVxdWVzdEl0ZW1SB3JlcXVlc3QSRgoEaXRlbRgCIAEoCzIwLmF1dGh6ZWQu", + "YXBpLnYxLkNoZWNrQnVsa1Blcm1pc3Npb25zUmVzcG9uc2VJdGVtSABSBGl0", + "ZW0SKgoFZXJyb3IYAyABKAsyEi5nb29nbGUucnBjLlN0YXR1c0gAUgVlcnJv", + "ckIKCghyZXNwb25zZSK+AgogQ2hlY2tCdWxrUGVybWlzc2lvbnNSZXNwb25z", + "ZUl0ZW0SdAoOcGVybWlzc2lvbnNoaXAYASABKA4yNi5hdXRoemVkLmFwaS52", + "MS5DaGVja1Blcm1pc3Npb25SZXNwb25zZS5QZXJtaXNzaW9uc2hpcEIU+kIH", + "ggEEEAEgALpIB4IBBBABIABSDnBlcm1pc3Npb25zaGlwEmEKE3BhcnRpYWxf", + "Y2F2ZWF0X2luZm8YAiABKAsyIS5hdXRoemVkLmFwaS52MS5QYXJ0aWFsQ2F2", + "ZWF0SW5mb0IO+kIFigECEAC6SAPIAQBSEXBhcnRpYWxDYXZlYXRJbmZvEkEK", + "C2RlYnVnX3RyYWNlGAMgASgLMiAuYXV0aHplZC5hcGkudjEuRGVidWdJbmZv", + "cm1hdGlvblIKZGVidWdUcmFjZSKfAgobRXhwYW5kUGVybWlzc2lvblRyZWVS", + "ZXF1ZXN0Ej0KC2NvbnNpc3RlbmN5GAEgASgLMhsuYXV0aHplZC5hcGkudjEu", + "Q29uc2lzdGVuY3lSC2NvbnNpc3RlbmN5EksKCHJlc291cmNlGAIgASgLMh8u", + "YXV0aHplZC5hcGkudjEuT2JqZWN0UmVmZXJlbmNlQg76QgWKAQIQAbpIA8gB", + "AVIIcmVzb3VyY2USdAoKcGVybWlzc2lvbhgDIAEoCUJU+kInciUoQDIhXihb", + "YS16XVthLXowLTlfXXsxLDYyfVthLXowLTldKT8kukgnciUoQDIhXihbYS16", + "XVthLXowLTlfXXsxLDYyfVthLXowLTldKT8kUgpwZXJtaXNzaW9uIqIBChxF", + "eHBhbmRQZXJtaXNzaW9uVHJlZVJlc3BvbnNlEjkKC2V4cGFuZGVkX2F0GAEg", + "ASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5SCmV4cGFuZGVkQXQSRwoJ", + "dHJlZV9yb290GAIgASgLMiouYXV0aHplZC5hcGkudjEuUGVybWlzc2lvblJl", + "bGF0aW9uc2hpcFRyZWVSCHRyZWVSb290IrMFChZMb29rdXBSZXNvdXJjZXNS", + "ZXF1ZXN0Ej0KC2NvbnNpc3RlbmN5GAEgASgLMhsuYXV0aHplZC5hcGkudjEu", + "Q29uc2lzdGVuY3lSC2NvbnNpc3RlbmN5EsMBChRyZXNvdXJjZV9vYmplY3Rf", + "dHlwZRgCIAEoCUKQAfpCRXJDKIABMj5eKFthLXpdW2EtejAtOV9dezEsNjF9", + "W2EtejAtOV0vKSpbYS16XVthLXowLTlfXXsxLDYyfVthLXowLTldJLpIRXJD", + "KIABMj5eKFthLXpdW2EtejAtOV9dezEsNjF9W2EtejAtOV0vKSpbYS16XVth", + "LXowLTlfXXsxLDYyfVthLXowLTldJFIScmVzb3VyY2VPYmplY3RUeXBlEm4K", + "CnBlcm1pc3Npb24YAyABKAlCTvpCJHIiKEAyHl5bYS16XVthLXowLTlfXXsx", + "LDYyfVthLXowLTldJLpIJHIiKEAyHl5bYS16XVthLXowLTlfXXsxLDYyfVth", + "LXowLTldJFIKcGVybWlzc2lvbhJKCgdzdWJqZWN0GAQgASgLMiAuYXV0aHpl", + "ZC5hcGkudjEuU3ViamVjdFJlZmVyZW5jZUIO+kIFigECEAG6SAPIAQFSB3N1", + "YmplY3QSQQoHY29udGV4dBgFIAEoCzIXLmdvb2dsZS5wcm90b2J1Zi5TdHJ1", + "Y3RCDvpCBYoBAhAAukgDyAEAUgdjb250ZXh0EjUKDm9wdGlvbmFsX2xpbWl0", + "GAYgASgNQg76QgQqAigAukgEKgIoAFINb3B0aW9uYWxMaW1pdBI/Cg9vcHRp", + "b25hbF9jdXJzb3IYByABKAsyFi5hdXRoemVkLmFwaS52MS5DdXJzb3JSDm9w", + "dGlvbmFsQ3Vyc29yEh0KCndpdGhfZGVidWcYCCABKAhSCXdpdGhEZWJ1ZyKS", + "AwoXTG9va3VwUmVzb3VyY2VzUmVzcG9uc2USOgoMbG9va2VkX3VwX2F0GAEg", + "ASgLMhguYXV0aHplZC5hcGkudjEuWmVkVG9rZW5SCmxvb2tlZFVwQXQSLAoS", + "cmVzb3VyY2Vfb2JqZWN0X2lkGAIgASgJUhByZXNvdXJjZU9iamVjdElkEmIK", + "DnBlcm1pc3Npb25zaGlwGAMgASgOMiQuYXV0aHplZC5hcGkudjEuTG9va3Vw", + "UGVybWlzc2lvbnNoaXBCFPpCB4IBBBABIAC6SAeCAQQQASAAUg5wZXJtaXNz", + "aW9uc2hpcBJhChNwYXJ0aWFsX2NhdmVhdF9pbmZvGAQgASgLMiEuYXV0aHpl", + "ZC5hcGkudjEuUGFydGlhbENhdmVhdEluZm9CDvpCBYoBAhAAukgDyAEAUhFw", + "YXJ0aWFsQ2F2ZWF0SW5mbxJGChNhZnRlcl9yZXN1bHRfY3Vyc29yGAUgASgL", + "MhYuYXV0aHplZC5hcGkudjEuQ3Vyc29yUhFhZnRlclJlc3VsdEN1cnNvciKc", + "CAoVTG9va3VwU3ViamVjdHNSZXF1ZXN0Ej0KC2NvbnNpc3RlbmN5GAEgASgL", + "MhsuYXV0aHplZC5hcGkudjEuQ29uc2lzdGVuY3lSC2NvbnNpc3RlbmN5EksK", + "CHJlc291cmNlGAIgASgLMh8uYXV0aHplZC5hcGkudjEuT2JqZWN0UmVmZXJl", + "bmNlQg76QgWKAQIQAbpIA8gBAVIIcmVzb3VyY2USdAoKcGVybWlzc2lvbhgD", + "IAEoCUJU+kInciUoQDIhXihbYS16XVthLXowLTlfXXsxLDYyfVthLXowLTld", + "KT8kukgnciUoQDIhXihbYS16XVthLXowLTlfXXsxLDYyfVthLXowLTldKT8k", + "UgpwZXJtaXNzaW9uEsEBChNzdWJqZWN0X29iamVjdF90eXBlGAQgASgJQpAB", + "+kJFckMogAEyPl4oW2Etel1bYS16MC05X117MSw2MX1bYS16MC05XS8pKlth", + "LXpdW2EtejAtOV9dezEsNjJ9W2EtejAtOV0kukhFckMogAEyPl4oW2Etel1b", + "YS16MC05X117MSw2MX1bYS16MC05XS8pKlthLXpdW2EtejAtOV9dezEsNjJ9", + "W2EtejAtOV0kUhFzdWJqZWN0T2JqZWN0VHlwZRKQAQoZb3B0aW9uYWxfc3Vi", + "amVjdF9yZWxhdGlvbhgFIAEoCUJU+kInciUoQDIhXihbYS16XVthLXowLTlf", + "XXsxLDYyfVthLXowLTldKT8kukgnciUoQDIhXihbYS16XVthLXowLTlfXXsx", + "LDYyfVthLXowLTldKT8kUhdvcHRpb25hbFN1YmplY3RSZWxhdGlvbhJBCgdj", + "b250ZXh0GAYgASgLMhcuZ29vZ2xlLnByb3RvYnVmLlN0cnVjdEIO+kIFigEC", + "EAC6SAPIAQBSB2NvbnRleHQSRgoXb3B0aW9uYWxfY29uY3JldGVfbGltaXQY", + "ByABKA1CDvpCBCoCKAC6SAQqAigAUhVvcHRpb25hbENvbmNyZXRlTGltaXQS", + "PwoPb3B0aW9uYWxfY3Vyc29yGAggASgLMhYuYXV0aHplZC5hcGkudjEuQ3Vy", + "c29yUg5vcHRpb25hbEN1cnNvchJdCg93aWxkY2FyZF9vcHRpb24YCSABKA4y", + "NC5hdXRoemVkLmFwaS52MS5Mb29rdXBTdWJqZWN0c1JlcXVlc3QuV2lsZGNh", + "cmRPcHRpb25SDndpbGRjYXJkT3B0aW9uIn8KDldpbGRjYXJkT3B0aW9uEh8K", + "G1dJTERDQVJEX09QVElPTl9VTlNQRUNJRklFRBAAEiUKIVdJTERDQVJEX09Q", + "VElPTl9JTkNMVURFX1dJTERDQVJEUxABEiUKIVdJTERDQVJEX09QVElPTl9F", + "WENMVURFX1dJTERDQVJEUxACItYEChZMb29rdXBTdWJqZWN0c1Jlc3BvbnNl", + "EjoKDGxvb2tlZF91cF9hdBgBIAEoCzIYLmF1dGh6ZWQuYXBpLnYxLlplZFRv", + "a2VuUgpsb29rZWRVcEF0Ei4KEXN1YmplY3Rfb2JqZWN0X2lkGAIgASgJQgIY", + "AVIPc3ViamVjdE9iamVjdElkEjQKFGV4Y2x1ZGVkX3N1YmplY3RfaWRzGAMg", + "AygJQgIYAVISZXhjbHVkZWRTdWJqZWN0SWRzEmQKDnBlcm1pc3Npb25zaGlw", + "GAQgASgOMiQuYXV0aHplZC5hcGkudjEuTG9va3VwUGVybWlzc2lvbnNoaXBC", + "FhgB+kIHggEEEAEgALpIB4IBBBABIABSDnBlcm1pc3Npb25zaGlwEmMKE3Bh", + "cnRpYWxfY2F2ZWF0X2luZm8YBSABKAsyIS5hdXRoemVkLmFwaS52MS5QYXJ0", + "aWFsQ2F2ZWF0SW5mb0IQGAH6QgWKAQIQALpIA8gBAFIRcGFydGlhbENhdmVh", + "dEluZm8SOQoHc3ViamVjdBgGIAEoCzIfLmF1dGh6ZWQuYXBpLnYxLlJlc29s", + "dmVkU3ViamVjdFIHc3ViamVjdBJMChFleGNsdWRlZF9zdWJqZWN0cxgHIAMo", + "CzIfLmF1dGh6ZWQuYXBpLnYxLlJlc29sdmVkU3ViamVjdFIQZXhjbHVkZWRT", + "dWJqZWN0cxJGChNhZnRlcl9yZXN1bHRfY3Vyc29yGAggASgLMhYuYXV0aHpl", + "ZC5hcGkudjEuQ3Vyc29yUhFhZnRlclJlc3VsdEN1cnNvciKEAgoPUmVzb2x2", + "ZWRTdWJqZWN0EioKEXN1YmplY3Rfb2JqZWN0X2lkGAEgASgJUg9zdWJqZWN0", + "T2JqZWN0SWQSYgoOcGVybWlzc2lvbnNoaXAYAiABKA4yJC5hdXRoemVkLmFw", + "aS52MS5Mb29rdXBQZXJtaXNzaW9uc2hpcEIU+kIHggEEEAEgALpIB4IBBBAB", + "IABSDnBlcm1pc3Npb25zaGlwEmEKE3BhcnRpYWxfY2F2ZWF0X2luZm8YAyAB", + "KAsyIS5hdXRoemVkLmFwaS52MS5QYXJ0aWFsQ2F2ZWF0SW5mb0IO+kIFigEC", + "EAC6SAPIAQBSEXBhcnRpYWxDYXZlYXRJbmZvInMKHkltcG9ydEJ1bGtSZWxh", + "dGlvbnNoaXBzUmVxdWVzdBJRCg1yZWxhdGlvbnNoaXBzGAEgAygLMhwuYXV0", + "aHplZC5hcGkudjEuUmVsYXRpb25zaGlwQg36QgqSAQciBYoBAhABUg1yZWxh", + "dGlvbnNoaXBzIkAKH0ltcG9ydEJ1bGtSZWxhdGlvbnNoaXBzUmVzcG9uc2US", + "HQoKbnVtX2xvYWRlZBgBIAEoBFIJbnVtTG9hZGVkIr0CCh5FeHBvcnRCdWxr", + "UmVsYXRpb25zaGlwc1JlcXVlc3QSPQoLY29uc2lzdGVuY3kYASABKAsyGy5h", + "dXRoemVkLmFwaS52MS5Db25zaXN0ZW5jeVILY29uc2lzdGVuY3kSNQoOb3B0", + "aW9uYWxfbGltaXQYAiABKA1CDvpCBCoCKAC6SAQqAigAUg1vcHRpb25hbExp", + "bWl0Ej8KD29wdGlvbmFsX2N1cnNvchgDIAEoCzIWLmF1dGh6ZWQuYXBpLnYx", + "LkN1cnNvclIOb3B0aW9uYWxDdXJzb3ISZAocb3B0aW9uYWxfcmVsYXRpb25z", + "aGlwX2ZpbHRlchgEIAEoCzIiLmF1dGh6ZWQuYXBpLnYxLlJlbGF0aW9uc2hp", + "cEZpbHRlclIab3B0aW9uYWxSZWxhdGlvbnNoaXBGaWx0ZXIirQEKH0V4cG9y", + "dEJ1bGtSZWxhdGlvbnNoaXBzUmVzcG9uc2USRgoTYWZ0ZXJfcmVzdWx0X2N1", + "cnNvchgBIAEoCzIWLmF1dGh6ZWQuYXBpLnYxLkN1cnNvclIRYWZ0ZXJSZXN1", + "bHRDdXJzb3ISQgoNcmVsYXRpb25zaGlwcxgCIAMoCzIcLmF1dGh6ZWQuYXBp", + "LnYxLlJlbGF0aW9uc2hpcFINcmVsYXRpb25zaGlwcyqZAQoUTG9va3VwUGVy", + "bWlzc2lvbnNoaXASJQohTE9PS1VQX1BFUk1JU1NJT05TSElQX1VOU1BFQ0lG", + "SUVEEAASKAokTE9PS1VQX1BFUk1JU1NJT05TSElQX0hBU19QRVJNSVNTSU9O", + "EAESMAosTE9PS1VQX1BFUk1JU1NJT05TSElQX0NPTkRJVElPTkFMX1BFUk1J", + "U1NJT04QAjKKDQoSUGVybWlzc2lvbnNTZXJ2aWNlEp0BChFSZWFkUmVsYXRp", + "b25zaGlwcxIoLmF1dGh6ZWQuYXBpLnYxLlJlYWRSZWxhdGlvbnNoaXBzUmVx", + "dWVzdBopLmF1dGh6ZWQuYXBpLnYxLlJlYWRSZWxhdGlvbnNoaXBzUmVzcG9u", + "c2UiMZJBDQoLUGVybWlzc2lvbnOC0+STAhsiFi92MS9yZWxhdGlvbnNoaXBz", + "L3JlYWQ6ASowARKfAQoSV3JpdGVSZWxhdGlvbnNoaXBzEikuYXV0aHplZC5h", + "cGkudjEuV3JpdGVSZWxhdGlvbnNoaXBzUmVxdWVzdBoqLmF1dGh6ZWQuYXBp", + "LnYxLldyaXRlUmVsYXRpb25zaGlwc1Jlc3BvbnNlIjKSQQ0KC1Blcm1pc3Np", + "b25zgtPkkwIcIhcvdjEvcmVsYXRpb25zaGlwcy93cml0ZToBKhKjAQoTRGVs", + "ZXRlUmVsYXRpb25zaGlwcxIqLmF1dGh6ZWQuYXBpLnYxLkRlbGV0ZVJlbGF0", + "aW9uc2hpcHNSZXF1ZXN0GisuYXV0aHplZC5hcGkudjEuRGVsZXRlUmVsYXRp", + "b25zaGlwc1Jlc3BvbnNlIjOSQQ0KC1Blcm1pc3Npb25zgtPkkwIdIhgvdjEv", + "cmVsYXRpb25zaGlwcy9kZWxldGU6ASoSlAEKD0NoZWNrUGVybWlzc2lvbhIm", + "LmF1dGh6ZWQuYXBpLnYxLkNoZWNrUGVybWlzc2lvblJlcXVlc3QaJy5hdXRo", + "emVkLmFwaS52MS5DaGVja1Blcm1pc3Npb25SZXNwb25zZSIwkkENCgtQZXJt", + "aXNzaW9uc4LT5JMCGiIVL3YxL3Blcm1pc3Npb25zL2NoZWNrOgEqEqcBChRD", + "aGVja0J1bGtQZXJtaXNzaW9ucxIrLmF1dGh6ZWQuYXBpLnYxLkNoZWNrQnVs", + "a1Blcm1pc3Npb25zUmVxdWVzdBosLmF1dGh6ZWQuYXBpLnYxLkNoZWNrQnVs", + "a1Blcm1pc3Npb25zUmVzcG9uc2UiNJJBDQoLUGVybWlzc2lvbnOC0+STAh4i", + "GS92MS9wZXJtaXNzaW9ucy9jaGVja2J1bGs6ASoSpAEKFEV4cGFuZFBlcm1p", + "c3Npb25UcmVlEisuYXV0aHplZC5hcGkudjEuRXhwYW5kUGVybWlzc2lvblRy", + "ZWVSZXF1ZXN0GiwuYXV0aHplZC5hcGkudjEuRXhwYW5kUGVybWlzc2lvblRy", + "ZWVSZXNwb25zZSIxkkENCgtQZXJtaXNzaW9uc4LT5JMCGyIWL3YxL3Blcm1p", + "c3Npb25zL2V4cGFuZDoBKhKaAQoPTG9va3VwUmVzb3VyY2VzEiYuYXV0aHpl", + "ZC5hcGkudjEuTG9va3VwUmVzb3VyY2VzUmVxdWVzdBonLmF1dGh6ZWQuYXBp", + "LnYxLkxvb2t1cFJlc291cmNlc1Jlc3BvbnNlIjSSQQ0KC1Blcm1pc3Npb25z", + "gtPkkwIeIhkvdjEvcGVybWlzc2lvbnMvcmVzb3VyY2VzOgEqMAESlgEKDkxv", + "b2t1cFN1YmplY3RzEiUuYXV0aHplZC5hcGkudjEuTG9va3VwU3ViamVjdHNS", + "ZXF1ZXN0GiYuYXV0aHplZC5hcGkudjEuTG9va3VwU3ViamVjdHNSZXNwb25z", + "ZSIzkkENCgtQZXJtaXNzaW9uc4LT5JMCHSIYL3YxL3Blcm1pc3Npb25zL3N1", + "YmplY3RzOgEqMAEStQEKF0ltcG9ydEJ1bGtSZWxhdGlvbnNoaXBzEi4uYXV0", + "aHplZC5hcGkudjEuSW1wb3J0QnVsa1JlbGF0aW9uc2hpcHNSZXF1ZXN0Gi8u", + "YXV0aHplZC5hcGkudjEuSW1wb3J0QnVsa1JlbGF0aW9uc2hpcHNSZXNwb25z", + "ZSI3kkENCgtQZXJtaXNzaW9uc4LT5JMCISIcL3YxL3JlbGF0aW9uc2hpcHMv", + "aW1wb3J0YnVsazoBKigBErUBChdFeHBvcnRCdWxrUmVsYXRpb25zaGlwcxIu", + "LmF1dGh6ZWQuYXBpLnYxLkV4cG9ydEJ1bGtSZWxhdGlvbnNoaXBzUmVxdWVz", + "dBovLmF1dGh6ZWQuYXBpLnYxLkV4cG9ydEJ1bGtSZWxhdGlvbnNoaXBzUmVz", + "cG9uc2UiN5JBDQoLUGVybWlzc2lvbnOC0+STAiEiHC92MS9yZWxhdGlvbnNo", + "aXBzL2V4cG9ydGJ1bGs6ASowAUJKChJjb20uYXV0aHplZC5hcGkudjFQAVoy", + "Z2l0aHViLmNvbS9hdXRoemVkL2F1dGh6ZWQtZ28vcHJvdG8vYXV0aHplZC9h", + "cGkvdjFiBnByb3RvMw==")); descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData, new pbr::FileDescriptor[] { global::Authzed.Api.V1.CoreReflection.Descriptor, global::Authzed.Api.V1.DebugReflection.Descriptor, global::Buf.Validate.ValidateReflection.Descriptor, global::Google.Api.AnnotationsReflection.Descriptor, global::Google.Protobuf.WellKnownTypes.StructReflection.Descriptor, global::Google.Protobuf.WellKnownTypes.TimestampReflection.Descriptor, global::Google.Rpc.StatusReflection.Descriptor, global::Grpc.Gateway.ProtocGenOpenapiv2.Options.AnnotationsReflection.Descriptor, global::Validate.ValidateReflection.Descriptor, }, new pbr::GeneratedClrTypeInfo(new[] {typeof(global::Authzed.Api.V1.LookupPermissionship), }, null, new pbr::GeneratedClrTypeInfo[] { @@ -313,8 +316,8 @@ static PermissionServiceReflection() { new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.Precondition), global::Authzed.Api.V1.Precondition.Parser, new[]{ "Operation", "Filter" }, null, new[]{ typeof(global::Authzed.Api.V1.Precondition.Types.Operation) }, null, null), new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.WriteRelationshipsRequest), global::Authzed.Api.V1.WriteRelationshipsRequest.Parser, new[]{ "Updates", "OptionalPreconditions", "OptionalTransactionMetadata" }, null, null, null, null), new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.WriteRelationshipsResponse), global::Authzed.Api.V1.WriteRelationshipsResponse.Parser, new[]{ "WrittenAt" }, null, null, null, null), - new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.DeleteRelationshipsRequest), global::Authzed.Api.V1.DeleteRelationshipsRequest.Parser, new[]{ "RelationshipFilter", "OptionalPreconditions", "OptionalLimit", "OptionalAllowPartialDeletions", "OptionalTransactionMetadata" }, null, null, null, null), - new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.DeleteRelationshipsResponse), global::Authzed.Api.V1.DeleteRelationshipsResponse.Parser, new[]{ "DeletedAt", "DeletionProgress", "RelationshipsDeletedCount" }, null, new[]{ typeof(global::Authzed.Api.V1.DeleteRelationshipsResponse.Types.DeletionProgress) }, null, null), + new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.DeleteRelationshipsRequest), global::Authzed.Api.V1.DeleteRelationshipsRequest.Parser, new[]{ "RelationshipFilter", "OptionalPreconditions", "OptionalLimit", "OptionalAllowPartialDeletions", "OptionalTransactionMetadata", "OptionalCursor" }, null, null, null, null), + new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.DeleteRelationshipsResponse), global::Authzed.Api.V1.DeleteRelationshipsResponse.Parser, new[]{ "DeletedAt", "DeletionProgress", "RelationshipsDeletedCount", "AfterResultCursor" }, null, new[]{ typeof(global::Authzed.Api.V1.DeleteRelationshipsResponse.Types.DeletionProgress) }, null, null), new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.CheckPermissionRequest), global::Authzed.Api.V1.CheckPermissionRequest.Parser, new[]{ "Consistency", "Resource", "Permission", "Subject", "Context", "WithTracing" }, null, null, null, null), new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.CheckPermissionResponse), global::Authzed.Api.V1.CheckPermissionResponse.Parser, new[]{ "CheckedAt", "Permissionship", "PartialCaveatInfo", "DebugTrace", "OptionalExpiresAt" }, null, new[]{ typeof(global::Authzed.Api.V1.CheckPermissionResponse.Types.Permissionship) }, null, null), new pbr::GeneratedClrTypeInfo(typeof(global::Authzed.Api.V1.CheckBulkPermissionsRequest), global::Authzed.Api.V1.CheckBulkPermissionsRequest.Parser, new[]{ "Consistency", "Items", "WithTracing" }, null, null, null, null), @@ -3138,6 +3141,7 @@ public DeleteRelationshipsRequest(DeleteRelationshipsRequest other) : this() { optionalLimit_ = other.optionalLimit_; optionalAllowPartialDeletions_ = other.optionalAllowPartialDeletions_; optionalTransactionMetadata_ = other.optionalTransactionMetadata_ != null ? other.optionalTransactionMetadata_.Clone() : null; + optionalCursor_ = other.optionalCursor_ != null ? other.optionalCursor_.Clone() : null; _unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields); } @@ -3225,6 +3229,29 @@ public bool OptionalAllowPartialDeletions { } } + /// Field number for the "optional_cursor" field. + public const int OptionalCursorFieldNumber = 6; + private global::Authzed.Api.V1.Cursor optionalCursor_; + /// + /// optional_cursor, if specified, indicates the cursor after which deletion should resume. It is used to + /// continue a batched, partial deletion where a previous call left off, by passing back the + /// after_result_cursor returned on the previous DeleteRelationshipsResponse. + /// + /// A cursor allows a large deletion to be performed as a series of calls without re-examining the + /// relationships already deleted by earlier calls. It therefore requires optional_limit and + /// optional_allow_partial_deletions to be set, and is only supported by datastores whose deletion can be + /// ordered and resumed; datastores that do not support cursored deletion will return an error if a cursor + /// is provided. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public global::Authzed.Api.V1.Cursor OptionalCursor { + get { return optionalCursor_; } + set { + optionalCursor_ = value; + } + } + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] public override bool Equals(object other) { @@ -3245,6 +3272,7 @@ public bool Equals(DeleteRelationshipsRequest other) { if (OptionalLimit != other.OptionalLimit) return false; if (OptionalAllowPartialDeletions != other.OptionalAllowPartialDeletions) return false; if (!object.Equals(OptionalTransactionMetadata, other.OptionalTransactionMetadata)) return false; + if (!object.Equals(OptionalCursor, other.OptionalCursor)) return false; return Equals(_unknownFields, other._unknownFields); } @@ -3257,6 +3285,7 @@ public override int GetHashCode() { if (OptionalLimit != 0) hash ^= OptionalLimit.GetHashCode(); if (OptionalAllowPartialDeletions != false) hash ^= OptionalAllowPartialDeletions.GetHashCode(); if (optionalTransactionMetadata_ != null) hash ^= OptionalTransactionMetadata.GetHashCode(); + if (optionalCursor_ != null) hash ^= OptionalCursor.GetHashCode(); if (_unknownFields != null) { hash ^= _unknownFields.GetHashCode(); } @@ -3292,6 +3321,10 @@ public void WriteTo(pb::CodedOutputStream output) { output.WriteRawTag(42); output.WriteMessage(OptionalTransactionMetadata); } + if (optionalCursor_ != null) { + output.WriteRawTag(50); + output.WriteMessage(OptionalCursor); + } if (_unknownFields != null) { _unknownFields.WriteTo(output); } @@ -3319,6 +3352,10 @@ public void WriteTo(pb::CodedOutputStream output) { output.WriteRawTag(42); output.WriteMessage(OptionalTransactionMetadata); } + if (optionalCursor_ != null) { + output.WriteRawTag(50); + output.WriteMessage(OptionalCursor); + } if (_unknownFields != null) { _unknownFields.WriteTo(ref output); } @@ -3342,6 +3379,9 @@ public int CalculateSize() { if (optionalTransactionMetadata_ != null) { size += 1 + pb::CodedOutputStream.ComputeMessageSize(OptionalTransactionMetadata); } + if (optionalCursor_ != null) { + size += 1 + pb::CodedOutputStream.ComputeMessageSize(OptionalCursor); + } if (_unknownFields != null) { size += _unknownFields.CalculateSize(); } @@ -3373,6 +3413,12 @@ public void MergeFrom(DeleteRelationshipsRequest other) { } OptionalTransactionMetadata.MergeFrom(other.OptionalTransactionMetadata); } + if (other.optionalCursor_ != null) { + if (optionalCursor_ == null) { + OptionalCursor = new global::Authzed.Api.V1.Cursor(); + } + OptionalCursor.MergeFrom(other.OptionalCursor); + } _unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields); } @@ -3418,6 +3464,13 @@ public void MergeFrom(pb::CodedInputStream input) { input.ReadMessage(OptionalTransactionMetadata); break; } + case 50: { + if (optionalCursor_ == null) { + OptionalCursor = new global::Authzed.Api.V1.Cursor(); + } + input.ReadMessage(OptionalCursor); + break; + } } } #endif @@ -3463,6 +3516,13 @@ public void MergeFrom(pb::CodedInputStream input) { input.ReadMessage(OptionalTransactionMetadata); break; } + case 50: { + if (optionalCursor_ == null) { + OptionalCursor = new global::Authzed.Api.V1.Cursor(); + } + input.ReadMessage(OptionalCursor); + break; + } } } } @@ -3508,6 +3568,7 @@ public DeleteRelationshipsResponse(DeleteRelationshipsResponse other) : this() { deletedAt_ = other.deletedAt_ != null ? other.deletedAt_.Clone() : null; deletionProgress_ = other.deletionProgress_; relationshipsDeletedCount_ = other.relationshipsDeletedCount_; + afterResultCursor_ = other.afterResultCursor_ != null ? other.afterResultCursor_.Clone() : null; _unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields); } @@ -3562,6 +3623,25 @@ public ulong RelationshipsDeletedCount { } } + /// Field number for the "after_result_cursor" field. + public const int AfterResultCursorFieldNumber = 4; + private global::Authzed.Api.V1.Cursor afterResultCursor_; + /// + /// after_result_cursor holds a cursor that can be used to resume the deletion after the relationships + /// deleted by this call, by supplying it as the optional_cursor on a subsequent DeleteRelationshipsRequest. + /// + /// It is populated only when deletion_progress is DELETION_PROGRESS_PARTIAL and the datastore supports + /// cursored deletion; it is unset once DELETION_PROGRESS_COMPLETE is returned. + /// + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] + [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] + public global::Authzed.Api.V1.Cursor AfterResultCursor { + get { return afterResultCursor_; } + set { + afterResultCursor_ = value; + } + } + [global::System.Diagnostics.DebuggerNonUserCodeAttribute] [global::System.CodeDom.Compiler.GeneratedCode("protoc", null)] public override bool Equals(object other) { @@ -3580,6 +3660,7 @@ public bool Equals(DeleteRelationshipsResponse other) { if (!object.Equals(DeletedAt, other.DeletedAt)) return false; if (DeletionProgress != other.DeletionProgress) return false; if (RelationshipsDeletedCount != other.RelationshipsDeletedCount) return false; + if (!object.Equals(AfterResultCursor, other.AfterResultCursor)) return false; return Equals(_unknownFields, other._unknownFields); } @@ -3590,6 +3671,7 @@ public override int GetHashCode() { if (deletedAt_ != null) hash ^= DeletedAt.GetHashCode(); if (DeletionProgress != global::Authzed.Api.V1.DeleteRelationshipsResponse.Types.DeletionProgress.Unspecified) hash ^= DeletionProgress.GetHashCode(); if (RelationshipsDeletedCount != 0UL) hash ^= RelationshipsDeletedCount.GetHashCode(); + if (afterResultCursor_ != null) hash ^= AfterResultCursor.GetHashCode(); if (_unknownFields != null) { hash ^= _unknownFields.GetHashCode(); } @@ -3620,6 +3702,10 @@ public void WriteTo(pb::CodedOutputStream output) { output.WriteRawTag(24); output.WriteUInt64(RelationshipsDeletedCount); } + if (afterResultCursor_ != null) { + output.WriteRawTag(34); + output.WriteMessage(AfterResultCursor); + } if (_unknownFields != null) { _unknownFields.WriteTo(output); } @@ -3642,6 +3728,10 @@ public void WriteTo(pb::CodedOutputStream output) { output.WriteRawTag(24); output.WriteUInt64(RelationshipsDeletedCount); } + if (afterResultCursor_ != null) { + output.WriteRawTag(34); + output.WriteMessage(AfterResultCursor); + } if (_unknownFields != null) { _unknownFields.WriteTo(ref output); } @@ -3661,6 +3751,9 @@ public int CalculateSize() { if (RelationshipsDeletedCount != 0UL) { size += 1 + pb::CodedOutputStream.ComputeUInt64Size(RelationshipsDeletedCount); } + if (afterResultCursor_ != null) { + size += 1 + pb::CodedOutputStream.ComputeMessageSize(AfterResultCursor); + } if (_unknownFields != null) { size += _unknownFields.CalculateSize(); } @@ -3685,6 +3778,12 @@ public void MergeFrom(DeleteRelationshipsResponse other) { if (other.RelationshipsDeletedCount != 0UL) { RelationshipsDeletedCount = other.RelationshipsDeletedCount; } + if (other.afterResultCursor_ != null) { + if (afterResultCursor_ == null) { + AfterResultCursor = new global::Authzed.Api.V1.Cursor(); + } + AfterResultCursor.MergeFrom(other.AfterResultCursor); + } _unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields); } @@ -3719,6 +3818,13 @@ public void MergeFrom(pb::CodedInputStream input) { RelationshipsDeletedCount = input.ReadUInt64(); break; } + case 34: { + if (afterResultCursor_ == null) { + AfterResultCursor = new global::Authzed.Api.V1.Cursor(); + } + input.ReadMessage(AfterResultCursor); + break; + } } } #endif @@ -3753,6 +3859,13 @@ public void MergeFrom(pb::CodedInputStream input) { RelationshipsDeletedCount = input.ReadUInt64(); break; } + case 34: { + if (afterResultCursor_ == null) { + AfterResultCursor = new global::Authzed.Api.V1.Cursor(); + } + input.ReadMessage(AfterResultCursor); + break; + } } } } diff --git a/src/Authzed.Net/Authzed/Api/V1/PermissionServiceGrpc.cs b/src/Authzed.Net/Authzed/Api/V1/PermissionServiceGrpc.cs index 0b92d3f..70abbc6 100644 --- a/src/Authzed.Net/Authzed/Api/V1/PermissionServiceGrpc.cs +++ b/src/Authzed.Net/Authzed/Api/V1/PermissionServiceGrpc.cs @@ -508,6 +508,11 @@ protected PermissionsServiceClient(ClientBaseConfiguration configuration) : base /// /// LookupResources returns all the resources of a given type that a subject /// can access whether via a computed permission or relation membership. + /// + /// Results are streamed and **not guaranteed to be unique**: the same resource + /// may be returned more than once (for example via caveated/conditional + /// results, or when a limit is set), possibly with differing permissionship. + /// Callers that require uniqueness should deduplicate results. /// /// The request to send to the server. /// The initial metadata to send with the call. This parameter is optional. @@ -522,6 +527,11 @@ protected PermissionsServiceClient(ClientBaseConfiguration configuration) : base /// /// LookupResources returns all the resources of a given type that a subject /// can access whether via a computed permission or relation membership. + /// + /// Results are streamed and **not guaranteed to be unique**: the same resource + /// may be returned more than once (for example via caveated/conditional + /// results, or when a limit is set), possibly with differing permissionship. + /// Callers that require uniqueness should deduplicate results. /// /// The request to send to the server. /// The options for the call. @@ -534,6 +544,10 @@ protected PermissionsServiceClient(ClientBaseConfiguration configuration) : base /// /// LookupSubjects returns all the subjects of a given type that /// have access whether via a computed permission or relation membership. + /// + /// Results are streamed and **not guaranteed to be unique**: the same subject + /// may be returned more than once, possibly with differing permissionship. + /// Callers that require uniqueness should deduplicate results. /// /// The request to send to the server. /// The initial metadata to send with the call. This parameter is optional. @@ -548,6 +562,10 @@ protected PermissionsServiceClient(ClientBaseConfiguration configuration) : base /// /// LookupSubjects returns all the subjects of a given type that /// have access whether via a computed permission or relation membership. + /// + /// Results are streamed and **not guaranteed to be unique**: the same subject + /// may be returned more than once, possibly with differing permissionship. + /// Callers that require uniqueness should deduplicate results. /// /// The request to send to the server. /// The options for the call.