feat: admins can delete all members messages during the ban (#4834)

This commit is contained in:
Mykhailo Prakhov 2024-02-29 18:54:17 +01:00 committed by GitHub
parent abfaa3cf8d
commit 77214dcb5d
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
13 changed files with 230 additions and 79 deletions

View File

@ -862,10 +862,17 @@ func (o *Community) BanUserFromCommunity(pk *ecdsa.PublicKey, communityBanInfo *
o.banUserFromCommunity(pk, communityBanInfo) o.banUserFromCommunity(pk, communityBanInfo)
o.increaseClock() o.increaseClock()
} else { } else {
err := o.addNewCommunityEvent(o.ToBanCommunityMemberCommunityEvent(common.PubkeyToHex(pk))) pkStr := common.PubkeyToHex(pk)
err := o.addNewCommunityEvent(o.ToBanCommunityMemberCommunityEvent(pkStr))
if err != nil { if err != nil {
return nil, err return nil, err
} }
if communityBanInfo.DeleteAllMessages {
err := o.addNewCommunityEvent(o.ToDeleteAllMemberMessagesEvent(pkStr))
if err != nil {
return nil, err
}
}
} }
return o.config.CommunityDescription, nil return o.config.CommunityDescription, nil
@ -2257,6 +2264,21 @@ func (o *Community) banUserFromCommunity(pk *ecdsa.PublicKey, communityBanInfo *
o.config.CommunityDescription.BanList = append(o.config.CommunityDescription.BanList, key) o.config.CommunityDescription.BanList = append(o.config.CommunityDescription.BanList, key)
} }
func (o *Community) deleteBannedMemberAllMessages(pk *ecdsa.PublicKey) error {
key := common.PubkeyToHex(pk)
if o.config.CommunityDescription.BannedMembers == nil {
return ErrBannedMemberNotFound
}
if _, exists := o.config.CommunityDescription.BannedMembers[key]; !exists {
return ErrBannedMemberNotFound
}
o.config.CommunityDescription.BannedMembers[key].DeleteAllMessages = true
return nil
}
func (o *Community) editChat(chatID string, chat *protobuf.CommunityChat) error { func (o *Community) editChat(chatID string, chat *protobuf.CommunityChat) error {
err := validateCommunityChat(o.config.CommunityDescription, chat) err := validateCommunityChat(o.config.CommunityDescription, chat)
if err != nil { if err != nil {

View File

@ -203,6 +203,10 @@ func (e *CommunityEvent) Validate() error {
if e.TokenMetadata == nil || len(e.TokenMetadata.ContractAddresses) == 0 { if e.TokenMetadata == nil || len(e.TokenMetadata.ContractAddresses) == 0 {
return errors.New("invalid add community token event") return errors.New("invalid add community token event")
} }
case protobuf.CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES:
if len(e.MemberToAction) == 0 {
return errors.New("invalid delete all community member messages event")
}
} }
return nil return nil
} }
@ -233,7 +237,8 @@ func (e *CommunityEvent) EventTypeID() string {
protobuf.CommunityEvent_COMMUNITY_REQUEST_TO_JOIN_REJECT, protobuf.CommunityEvent_COMMUNITY_REQUEST_TO_JOIN_REJECT,
protobuf.CommunityEvent_COMMUNITY_MEMBER_KICK, protobuf.CommunityEvent_COMMUNITY_MEMBER_KICK,
protobuf.CommunityEvent_COMMUNITY_MEMBER_BAN, protobuf.CommunityEvent_COMMUNITY_MEMBER_BAN,
protobuf.CommunityEvent_COMMUNITY_MEMBER_UNBAN: protobuf.CommunityEvent_COMMUNITY_MEMBER_UNBAN,
protobuf.CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES:
return fmt.Sprintf("%d-%s", e.Type, e.MemberToAction) return fmt.Sprintf("%d-%s", e.Type, e.MemberToAction)
case protobuf.CommunityEvent_COMMUNITY_TOKEN_ADD: case protobuf.CommunityEvent_COMMUNITY_TOKEN_ADD:

View File

@ -99,6 +99,14 @@ func (o *Community) ToBanCommunityMemberCommunityEvent(pubkey string) *Community
} }
} }
func (o *Community) ToDeleteAllMemberMessagesEvent(pubkey string) *CommunityEvent {
return &CommunityEvent{
CommunityEventClock: o.nextEventClock(),
Type: protobuf.CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES,
MemberToAction: pubkey,
}
}
func (o *Community) ToUnbanCommunityMemberCommunityEvent(pubkey string) *CommunityEvent { func (o *Community) ToUnbanCommunityMemberCommunityEvent(pubkey string) *CommunityEvent {
return &CommunityEvent{ return &CommunityEvent{
CommunityEventClock: o.nextEventClock(), CommunityEventClock: o.nextEventClock(),

View File

@ -258,6 +258,18 @@ func (o *Community) applyEvent(communityEvent CommunityEvent) error {
} }
case protobuf.CommunityEvent_COMMUNITY_TOKEN_ADD: case protobuf.CommunityEvent_COMMUNITY_TOKEN_ADD:
o.config.CommunityDescription.CommunityTokensMetadata = append(o.config.CommunityDescription.CommunityTokensMetadata, communityEvent.TokenMetadata) o.config.CommunityDescription.CommunityTokensMetadata = append(o.config.CommunityDescription.CommunityTokensMetadata, communityEvent.TokenMetadata)
case protobuf.CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES:
if o.IsControlNode() {
pk, err := common.HexToPubkey(communityEvent.MemberToAction)
if err != nil {
return err
}
err = o.deleteBannedMemberAllMessages(pk)
if err != nil {
return err
}
}
} }
return nil return nil
} }

View File

@ -45,3 +45,4 @@ var ErrRevealedAccountsAbsent = errors.New("revealed accounts is absent")
var ErrNoRevealedAccountsSignature = errors.New("revealed accounts without the signature") var ErrNoRevealedAccountsSignature = errors.New("revealed accounts without the signature")
var ErrNoFreeSpaceForHistoryArchives = errors.New("history archive: No free space for downloading history archives") var ErrNoFreeSpaceForHistoryArchives = errors.New("history archive: No free space for downloading history archives")
var ErrPermissionToJoinNotSatisfied = errors.New("permission to join not satisfied") var ErrPermissionToJoinNotSatisfied = errors.New("permission to join not satisfied")
var ErrBannedMemberNotFound = errors.New("banned member not found")

View File

@ -23,6 +23,7 @@ var adminAuthorizedEventTypes = []protobuf.CommunityEvent_EventType{
protobuf.CommunityEvent_COMMUNITY_MEMBER_KICK, protobuf.CommunityEvent_COMMUNITY_MEMBER_KICK,
protobuf.CommunityEvent_COMMUNITY_MEMBER_BAN, protobuf.CommunityEvent_COMMUNITY_MEMBER_BAN,
protobuf.CommunityEvent_COMMUNITY_MEMBER_UNBAN, protobuf.CommunityEvent_COMMUNITY_MEMBER_UNBAN,
protobuf.CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES,
} }
var tokenMasterAuthorizedEventTypes = append(adminAuthorizedEventTypes, []protobuf.CommunityEvent_EventType{ var tokenMasterAuthorizedEventTypes = append(adminAuthorizedEventTypes, []protobuf.CommunityEvent_EventType{
@ -112,7 +113,9 @@ func RolesAuthorizedToPerformEvent(senderRoles []protobuf.CommunityMember_Roles,
} }
if event.Type == protobuf.CommunityEvent_COMMUNITY_MEMBER_BAN || if event.Type == protobuf.CommunityEvent_COMMUNITY_MEMBER_BAN ||
event.Type == protobuf.CommunityEvent_COMMUNITY_MEMBER_KICK { event.Type == protobuf.CommunityEvent_COMMUNITY_MEMBER_KICK ||
event.Type == protobuf.CommunityEvent_COMMUNITY_MEMBER_UNBAN ||
event.Type == protobuf.CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES {
return canRolesKickOrBanMember(senderRoles, memberRoles) return canRolesKickOrBanMember(senderRoles, memberRoles)
} }

View File

@ -276,3 +276,8 @@ func (s *OwnerWithoutCommunityKeyCommunityEventsSuite) TestMemberReceiveOwnerEve
community := setUpCommunityAndRoles(s, protobuf.CommunityMember_ROLE_OWNER) community := setUpCommunityAndRoles(s, protobuf.CommunityMember_ROLE_OWNER)
testMemberReceiveEventsWhenControlNodeOffline(s, community) testMemberReceiveEventsWhenControlNodeOffline(s, community)
} }
func (s *OwnerWithoutCommunityKeyCommunityEventsSuite) TestOwnerBanMemberWithDeletingAllMessages() {
community := setUpCommunityAndRoles(s, protobuf.CommunityMember_ROLE_OWNER)
testBanMemberWithDeletingAllMessages(s, community)
}

View File

@ -321,3 +321,8 @@ func (s *TokenMasterCommunityEventsSuite) TestTokenMasterAcceptsRequestToJoinAft
s.SetupAdditionalMessengers([]*Messenger{user}) s.SetupAdditionalMessengers([]*Messenger{user})
testPrivilegedMemberAcceptsRequestToJoinAfterMemberLeave(s, community, user) testPrivilegedMemberAcceptsRequestToJoinAfterMemberLeave(s, community, user)
} }
func (s *TokenMasterCommunityEventsSuite) TestTokenMasterBanMemberWithDeletingAllMessages() {
community := setUpCommunityAndRoles(s, protobuf.CommunityMember_ROLE_TOKEN_MASTER)
testBanMemberWithDeletingAllMessages(s, community)
}

View File

@ -6,6 +6,7 @@ import (
"math/big" "math/big"
"github.com/stretchr/testify/suite" "github.com/stretchr/testify/suite"
"go.uber.org/zap"
gethcommon "github.com/ethereum/go-ethereum/common" gethcommon "github.com/ethereum/go-ethereum/common"
hexutil "github.com/ethereum/go-ethereum/common/hexutil" hexutil "github.com/ethereum/go-ethereum/common/hexutil"
@ -48,6 +49,9 @@ func waitOnMessengerResponse(s *suite.Suite, fnWait MessageResponseValidator, us
user, user,
func(r *MessengerResponse) bool { func(r *MessengerResponse) bool {
err := fnWait(r) err := fnWait(r)
if err != nil {
user.logger.Error("WaitOnMessengerResponse: ", zap.Error(err))
}
return err == nil return err == nil
}, },
"MessengerResponse data not received", "MessengerResponse data not received",
@ -690,7 +694,8 @@ func kickMember(base CommunityEventsTestsInterface, communityID types.HexBytes,
} }
func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserFromCommunity) { func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserFromCommunity) {
pubkey := common.PubkeyToHex(&base.GetMember().identity.PublicKey) bannedPK := banRequest.User.String()
communityStr := banRequest.CommunityID.String()
checkBanned := func(response *MessengerResponse) error { checkBanned := func(response *MessengerResponse) error {
modifiedCommmunity, err := getModifiedCommunity(response, types.EncodeHex(banRequest.CommunityID)) modifiedCommmunity, err := getModifiedCommunity(response, types.EncodeHex(banRequest.CommunityID))
@ -706,10 +711,16 @@ func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserF
return errors.New("alice was not added to the banned list") return errors.New("alice was not added to the banned list")
} }
if modifiedCommmunity.PendingAndBannedMembers()[pubkey] != communities.CommunityMemberBanned { if modifiedCommmunity.PendingAndBannedMembers()[bannedPK] != communities.CommunityMemberBanned {
return errors.New("alice should be in the pending state") return errors.New("alice should be in the pending state")
} }
if banRequest.DeleteAllMessages {
if len(response.DeletedMessages()) == 0 {
return errors.New("alice message must be deleted")
}
}
return nil return nil
} }
@ -722,7 +733,7 @@ func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserF
modifiedCommmunity, err := getModifiedCommunity(response, types.EncodeHex(banRequest.CommunityID)) modifiedCommmunity, err := getModifiedCommunity(response, types.EncodeHex(banRequest.CommunityID))
s.Require().NoError(err) s.Require().NoError(err)
s.Require().True(modifiedCommmunity.HasMember(&base.GetMember().identity.PublicKey)) s.Require().True(modifiedCommmunity.HasMember(&base.GetMember().identity.PublicKey))
s.Require().Equal(communities.CommunityMemberBanPending, modifiedCommmunity.PendingAndBannedMembers()[pubkey]) s.Require().Equal(communities.CommunityMemberBanPending, modifiedCommmunity.PendingAndBannedMembers()[bannedPK])
// 2. wait for event as a sender // 2. wait for event as a sender
waitOnMessengerResponse(s, func(response *MessengerResponse) error { waitOnMessengerResponse(s, func(response *MessengerResponse) error {
@ -732,11 +743,11 @@ func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserF
} }
if !modifiedCommmunity.HasMember(&base.GetMember().identity.PublicKey) { if !modifiedCommmunity.HasMember(&base.GetMember().identity.PublicKey) {
return errors.New("alice should not be not banned (yet)") return errors.New("event sender: alice should not be not banned (yet)")
} }
if modifiedCommmunity.PendingAndBannedMembers()[pubkey] != communities.CommunityMemberBanPending { if modifiedCommmunity.PendingAndBannedMembers()[bannedPK] != communities.CommunityMemberBanPending {
return errors.New("alice should be in the pending state") return errors.New("event sender: alice should be in the pending state")
} }
return nil return nil
@ -750,16 +761,27 @@ func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserF
} }
if !modifiedCommmunity.HasMember(&base.GetMember().identity.PublicKey) { if !modifiedCommmunity.HasMember(&base.GetMember().identity.PublicKey) {
return errors.New("alice should not be not banned (yet)") return errors.New("member: alice should not be not banned (yet)")
} }
if len(modifiedCommmunity.PendingAndBannedMembers()) == 0 { if len(modifiedCommmunity.PendingAndBannedMembers()) == 0 {
return errors.New("alice should know about banned and pending members") return errors.New("member: alice should know about banned and pending members")
} }
return nil return nil
}, base.GetMember()) }, base.GetMember())
checkMsgDeletion := func(messenger *Messenger, expectedMsgsCount int) {
msgs, err := messenger.persistence.GetCommunityMemberAllMessagesID(bannedPK, communityStr)
s.Require().NoError(err)
s.Require().Len(msgs, expectedMsgsCount)
}
if banRequest.DeleteAllMessages {
checkMsgDeletion(base.GetEventSender(), 1)
checkMsgDeletion(base.GetMember(), 1)
}
// 4. control node should handle event and actually ban member // 4. control node should handle event and actually ban member
waitOnMessengerResponse(s, checkBanned, base.GetControlNode()) waitOnMessengerResponse(s, checkBanned, base.GetControlNode())
@ -768,6 +790,12 @@ func banMember(base CommunityEventsTestsInterface, banRequest *requests.BanUserF
// 6. member should be notified about actual removal // 6. member should be notified about actual removal
waitOnMessengerResponse(s, checkBanned, base.GetMember()) waitOnMessengerResponse(s, checkBanned, base.GetMember())
if banRequest.DeleteAllMessages {
checkMsgDeletion(base.GetEventSender(), 0)
checkMsgDeletion(base.GetMember(), 0)
checkMsgDeletion(base.GetControlNode(), 0)
}
} }
func unbanMember(base CommunityEventsTestsInterface, unbanRequest *requests.UnbanUserFromCommunity) { func unbanMember(base CommunityEventsTestsInterface, unbanRequest *requests.UnbanUserFromCommunity) {
@ -2446,3 +2474,53 @@ func testPrivilegedMemberAcceptsRequestToJoinAfterMemberLeave(base CommunityEven
s.Require().NoError(err) s.Require().NoError(err)
s.Require().Len(acceptedRequestsPending, 0) s.Require().Len(acceptedRequestsPending, 0)
} }
func testBanMemberWithDeletingAllMessages(base CommunityEventsTestsInterface, community *communities.Community) {
// verify that event sender can't ban a control node and delete his messages
banRequest := &requests.BanUserFromCommunity{
CommunityID: community.ID(),
User: common.PubkeyToHexBytes(&base.GetControlNode().identity.PublicKey),
DeleteAllMessages: true,
}
_, err := base.GetEventSender().BanUserFromCommunity(
context.Background(),
banRequest,
)
s := base.GetSuite()
s.Require().Error(err)
chatIds := community.ChatIDs()
s.Require().Len(chatIds, 1)
chat := base.GetEventSender().Chat(chatIds[0])
s.Require().NotNil(chat)
inputMessage := buildTestMessage(*chat)
sendResponse, err := base.GetMember().SendChatMessage(context.Background(), inputMessage)
s.NoError(err)
s.Require().NotNil(sendResponse)
s.Require().Len(sendResponse.Messages(), 1)
messageID := sendResponse.Messages()[0].ID
checkMsgDelivered := func(response *MessengerResponse) error {
if len(response.Messages()) == 0 {
return errors.New("response does not contain message")
}
for _, message := range response.Messages() {
if message.ID == messageID {
return nil
}
}
return errors.New("messages was not found in the response")
}
waitOnMessengerResponse(s, checkMsgDelivered, base.GetControlNode())
waitOnMessengerResponse(s, checkMsgDelivered, base.GetEventSender())
banRequest.User = common.PubkeyToHexBytes(&base.GetMember().identity.PublicKey)
banMember(base, banRequest)
}

View File

@ -354,3 +354,8 @@ func (s *AdminCommunityEventsSuite) TestAdminAcceptsRequestToJoinAfterMemberLeav
s.SetupAdditionalMessengers([]*Messenger{user}) s.SetupAdditionalMessengers([]*Messenger{user})
testPrivilegedMemberAcceptsRequestToJoinAfterMemberLeave(s, community, user) testPrivilegedMemberAcceptsRequestToJoinAfterMemberLeave(s, community, user)
} }
func (s *AdminCommunityEventsSuite) TestAdminBanMemberWithDeletingAllMessages() {
community := setUpCommunityAndRoles(s, protobuf.CommunityMember_ROLE_ADMIN)
testBanMemberWithDeletingAllMessages(s, community)
}

View File

@ -2676,7 +2676,7 @@ func (m *Messenger) BanUserFromCommunity(ctx context.Context, request *requests.
response.AddCommunity(community) response.AddCommunity(community)
if request.DeleteAllMessages { if request.DeleteAllMessages && community.IsControlNode() {
deleteMessagesResponse, err := m.DeleteAllCommunityMemberMessages(request.User.String(), request.CommunityID.String()) deleteMessagesResponse, err := m.DeleteAllCommunityMemberMessages(request.User.String(), request.CommunityID.String())
if err != nil { if err != nil {
return nil, err return nil, err

View File

@ -41,6 +41,7 @@ const (
CommunityEvent_COMMUNITY_MEMBER_BAN CommunityEvent_EventType = 15 CommunityEvent_COMMUNITY_MEMBER_BAN CommunityEvent_EventType = 15
CommunityEvent_COMMUNITY_MEMBER_UNBAN CommunityEvent_EventType = 16 CommunityEvent_COMMUNITY_MEMBER_UNBAN CommunityEvent_EventType = 16
CommunityEvent_COMMUNITY_TOKEN_ADD CommunityEvent_EventType = 17 CommunityEvent_COMMUNITY_TOKEN_ADD CommunityEvent_EventType = 17
CommunityEvent_COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES CommunityEvent_EventType = 18
) )
// Enum value maps for CommunityEvent_EventType. // Enum value maps for CommunityEvent_EventType.
@ -64,6 +65,7 @@ var (
15: "COMMUNITY_MEMBER_BAN", 15: "COMMUNITY_MEMBER_BAN",
16: "COMMUNITY_MEMBER_UNBAN", 16: "COMMUNITY_MEMBER_UNBAN",
17: "COMMUNITY_TOKEN_ADD", 17: "COMMUNITY_TOKEN_ADD",
18: "COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES",
} }
CommunityEvent_EventType_value = map[string]int32{ CommunityEvent_EventType_value = map[string]int32{
"UNKNOWN": 0, "UNKNOWN": 0,
@ -84,6 +86,7 @@ var (
"COMMUNITY_MEMBER_BAN": 15, "COMMUNITY_MEMBER_BAN": 15,
"COMMUNITY_MEMBER_UNBAN": 16, "COMMUNITY_MEMBER_UNBAN": 16,
"COMMUNITY_TOKEN_ADD": 17, "COMMUNITY_TOKEN_ADD": 17,
"COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES": 18,
} }
) )
@ -661,7 +664,7 @@ var file_community_update_proto_rawDesc = []byte{
0x74, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x08, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x74, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x08, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62,
0x75, 0x66, 0x1a, 0x13, 0x63, 0x68, 0x61, 0x74, 0x5f, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x69, 0x74, 0x75, 0x66, 0x1a, 0x13, 0x63, 0x68, 0x61, 0x74, 0x5f, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x69, 0x74,
0x79, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x11, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x79, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x11, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69,
0x74, 0x69, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0x90, 0x0d, 0x0a, 0x0e, 0x43, 0x74, 0x69, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xbd, 0x0d, 0x0a, 0x0e, 0x43,
0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x32, 0x0a, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x32, 0x0a,
0x15, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x15, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x65, 0x76, 0x65, 0x6e, 0x74,
0x5f, 0x63, 0x6c, 0x6f, 0x63, 0x6b, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x13, 0x63, 0x6f, 0x5f, 0x63, 0x6c, 0x6f, 0x63, 0x6b, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x13, 0x63, 0x6f,
@ -731,7 +734,7 @@ var file_community_update_proto_rawDesc = []byte{
0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e,
0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69,
0x74, 0x79, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x54, 0x6f, 0x4a, 0x6f, 0x69, 0x6e, 0x52, 0x74, 0x79, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x54, 0x6f, 0x4a, 0x6f, 0x69, 0x6e, 0x52,
0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0xb0, 0x04, 0x0a, 0x09, 0x45, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x3a, 0x02, 0x38, 0x01, 0x22, 0xdd, 0x04, 0x0a, 0x09, 0x45,
0x76, 0x65, 0x6e, 0x74, 0x54, 0x79, 0x70, 0x65, 0x12, 0x0b, 0x0a, 0x07, 0x55, 0x4e, 0x4b, 0x4e, 0x76, 0x65, 0x6e, 0x74, 0x54, 0x79, 0x70, 0x65, 0x12, 0x0b, 0x0a, 0x07, 0x55, 0x4e, 0x4b, 0x4e,
0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x12, 0x0a, 0x0e, 0x43, 0x4f, 0x4d, 0x4d, 0x55, 0x4e, 0x49, 0x4f, 0x57, 0x4e, 0x10, 0x00, 0x12, 0x12, 0x0a, 0x0e, 0x43, 0x4f, 0x4d, 0x4d, 0x55, 0x4e, 0x49,
0x54, 0x59, 0x5f, 0x45, 0x44, 0x49, 0x54, 0x10, 0x01, 0x12, 0x2c, 0x0a, 0x28, 0x43, 0x4f, 0x4d, 0x54, 0x59, 0x5f, 0x45, 0x44, 0x49, 0x54, 0x10, 0x01, 0x12, 0x2c, 0x0a, 0x28, 0x43, 0x4f, 0x4d,
@ -766,71 +769,74 @@ var file_community_update_proto_rawDesc = []byte{
0x45, 0x52, 0x5f, 0x42, 0x41, 0x4e, 0x10, 0x0f, 0x12, 0x1a, 0x0a, 0x16, 0x43, 0x4f, 0x4d, 0x4d, 0x45, 0x52, 0x5f, 0x42, 0x41, 0x4e, 0x10, 0x0f, 0x12, 0x1a, 0x0a, 0x16, 0x43, 0x4f, 0x4d, 0x4d,
0x55, 0x4e, 0x49, 0x54, 0x59, 0x5f, 0x4d, 0x45, 0x4d, 0x42, 0x45, 0x52, 0x5f, 0x55, 0x4e, 0x42, 0x55, 0x4e, 0x49, 0x54, 0x59, 0x5f, 0x4d, 0x45, 0x4d, 0x42, 0x45, 0x52, 0x5f, 0x55, 0x4e, 0x42,
0x41, 0x4e, 0x10, 0x10, 0x12, 0x17, 0x0a, 0x13, 0x43, 0x4f, 0x4d, 0x4d, 0x55, 0x4e, 0x49, 0x54, 0x41, 0x4e, 0x10, 0x10, 0x12, 0x17, 0x0a, 0x13, 0x43, 0x4f, 0x4d, 0x4d, 0x55, 0x4e, 0x49, 0x54,
0x59, 0x5f, 0x54, 0x4f, 0x4b, 0x45, 0x4e, 0x5f, 0x41, 0x44, 0x44, 0x10, 0x11, 0x22, 0xae, 0x02, 0x59, 0x5f, 0x54, 0x4f, 0x4b, 0x45, 0x4e, 0x5f, 0x41, 0x44, 0x44, 0x10, 0x11, 0x12, 0x2b, 0x0a,
0x0a, 0x0f, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x27, 0x43, 0x4f, 0x4d, 0x4d, 0x55, 0x4e, 0x49, 0x54, 0x59, 0x5f, 0x44, 0x45, 0x4c, 0x45, 0x54,
0x67, 0x12, 0x32, 0x0a, 0x08, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x18, 0x01, 0x20, 0x45, 0x5f, 0x42, 0x41, 0x4e, 0x4e, 0x45, 0x44, 0x5f, 0x4d, 0x45, 0x4d, 0x42, 0x45, 0x52, 0x5f,
0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x4d, 0x45, 0x53, 0x53, 0x41, 0x47, 0x45, 0x53, 0x10, 0x12, 0x22, 0xae, 0x02, 0x0a, 0x0f, 0x43,
0x68, 0x61, 0x74, 0x49, 0x64, 0x65, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x52, 0x08, 0x69, 0x64, 0x65, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x32,
0x6e, 0x74, 0x69, 0x74, 0x79, 0x12, 0x40, 0x0a, 0x0b, 0x70, 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x0a, 0x08, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b,
0x69, 0x6f, 0x6e, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x32, 0x16, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x68, 0x61, 0x74,
0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x50, 0x49, 0x64, 0x65, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x52, 0x08, 0x69, 0x64, 0x65, 0x6e, 0x74, 0x69,
0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x52, 0x0b, 0x70, 0x65, 0x72, 0x6d, 0x74, 0x79, 0x12, 0x40, 0x0a, 0x0b, 0x70, 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e,
0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x47, 0x0a, 0x0e, 0x61, 0x64, 0x6d, 0x69, 0x6e, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62,
0x5f, 0x73, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x50, 0x65, 0x72, 0x6d,
0x20, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x69, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x52, 0x0b, 0x70, 0x65, 0x72, 0x6d, 0x69, 0x73, 0x73,
0x6e, 0x69, 0x74, 0x79, 0x41, 0x64, 0x6d, 0x69, 0x6e, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x47, 0x0a, 0x0e, 0x61, 0x64, 0x6d, 0x69, 0x6e, 0x5f, 0x73, 0x65,
0x73, 0x52, 0x0d, 0x61, 0x64, 0x6d, 0x69, 0x6e, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x73, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x70,
0x12, 0x23, 0x0a, 0x0d, 0x69, 0x6e, 0x74, 0x72, 0x6f, 0x5f, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74,
0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x69, 0x6e, 0x74, 0x72, 0x6f, 0x4d, 0x65, 0x79, 0x41, 0x64, 0x6d, 0x69, 0x6e, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x73, 0x52, 0x0d,
0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x23, 0x0a, 0x0d, 0x6f, 0x75, 0x74, 0x72, 0x6f, 0x5f, 0x6d, 0x61, 0x64, 0x6d, 0x69, 0x6e, 0x53, 0x65, 0x74, 0x74, 0x69, 0x6e, 0x67, 0x73, 0x12, 0x23, 0x0a,
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x6f, 0x75, 0x0d, 0x69, 0x6e, 0x74, 0x72, 0x6f, 0x5f, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x18, 0x04,
0x74, 0x72, 0x6f, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x61, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x69, 0x6e, 0x74, 0x72, 0x6f, 0x4d, 0x65, 0x73, 0x73, 0x61,
0x67, 0x73, 0x18, 0x06, 0x20, 0x03, 0x28, 0x09, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x22, 0x82, 0x67, 0x65, 0x12, 0x23, 0x0a, 0x0d, 0x6f, 0x75, 0x74, 0x72, 0x6f, 0x5f, 0x6d, 0x65, 0x73, 0x73,
0x01, 0x0a, 0x0c, 0x43, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x44, 0x61, 0x74, 0x61, 0x12, 0x61, 0x67, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x6f, 0x75, 0x74, 0x72, 0x6f,
0x1f, 0x0a, 0x0b, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x61, 0x67, 0x73, 0x18,
0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x49, 0x64, 0x06, 0x20, 0x03, 0x28, 0x09, 0x52, 0x04, 0x74, 0x61, 0x67, 0x73, 0x22, 0x82, 0x01, 0x0a, 0x0c,
0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x43, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x44, 0x61, 0x74, 0x61, 0x12, 0x1f, 0x0a, 0x0b,
0x6e, 0x61, 0x6d, 0x65, 0x12, 0x21, 0x0a, 0x0c, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x73, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28,
0x5f, 0x69, 0x64, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x68, 0x61, 0x6e, 0x09, 0x52, 0x0a, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x49, 0x64, 0x12, 0x12, 0x0a,
0x6e, 0x65, 0x6c, 0x73, 0x49, 0x64, 0x73, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d,
0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x65, 0x12, 0x21, 0x0a, 0x0c, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x73, 0x5f, 0x69, 0x64,
0x69, 0x6f, 0x6e, 0x22, 0x9c, 0x01, 0x0a, 0x0b, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x44, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x09, 0x52, 0x0b, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c,
0x61, 0x74, 0x61, 0x12, 0x1f, 0x0a, 0x0b, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x5f, 0x73, 0x49, 0x64, 0x73, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e,
0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e,
0x72, 0x79, 0x49, 0x64, 0x12, 0x1d, 0x0a, 0x0a, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x22, 0x9c, 0x01, 0x0a, 0x0b, 0x43, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x44, 0x61, 0x74, 0x61,
0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x12, 0x1f, 0x0a, 0x0b, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x5f, 0x69, 0x64, 0x18,
0x6c, 0x49, 0x64, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x49,
0x03, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x64, 0x12, 0x1d, 0x0a, 0x0a, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x5f, 0x69, 0x64, 0x18,
0x31, 0x0a, 0x07, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x49, 0x64,
0x32, 0x17, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01,
0x75, 0x6e, 0x69, 0x74, 0x79, 0x43, 0x68, 0x61, 0x74, 0x52, 0x07, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x28, 0x05, 0x52, 0x08, 0x70, 0x6f, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x31, 0x0a, 0x07,
0x65, 0x6c, 0x22, 0x4e, 0x0a, 0x14, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x17, 0x2e,
0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x73, 0x69, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69,
0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x74, 0x79, 0x43, 0x68, 0x61, 0x74, 0x52, 0x07, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x22,
0x69, 0x67, 0x6e, 0x61, 0x74, 0x75, 0x72, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x70, 0x61, 0x79, 0x6c, 0x4e, 0x0a, 0x14, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69,
0x6f, 0x61, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x07, 0x70, 0x61, 0x79, 0x6c, 0x6f, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x73, 0x69, 0x67, 0x6e, 0x61,
0x61, 0x64, 0x22, 0xe7, 0x01, 0x0a, 0x16, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x74, 0x75, 0x72, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x09, 0x73, 0x69, 0x67, 0x6e,
0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x21, 0x0a, 0x61, 0x74, 0x75, 0x72, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x70, 0x61, 0x79, 0x6c, 0x6f, 0x61, 0x64,
0x0c, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x07, 0x70, 0x61, 0x79, 0x6c, 0x6f, 0x61, 0x64, 0x22,
0x01, 0x28, 0x0c, 0x52, 0x0b, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x49, 0x64, 0xe7, 0x01, 0x0a, 0x16, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65,
0x12, 0x49, 0x0a, 0x21, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x5f, 0x62, 0x61, 0x73, 0x65, 0x5f, 0x6e, 0x74, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x21, 0x0a, 0x0c, 0x63, 0x6f,
0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c,
0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x1e, 0x65, 0x76, 0x65, 0x52, 0x0b, 0x63, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x49, 0x64, 0x12, 0x49, 0x0a,
0x6e, 0x74, 0x73, 0x42, 0x61, 0x73, 0x65, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x21, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x5f, 0x62, 0x61, 0x73, 0x65, 0x5f, 0x63, 0x6f, 0x6d,
0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x1a, 0x0a, 0x06, 0x65, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69,
0x76, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0c, 0x42, 0x02, 0x18, 0x01, 0x52, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x1e, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x73,
0x06, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x43, 0x0a, 0x0d, 0x73, 0x69, 0x67, 0x6e, 0x65, 0x42, 0x61, 0x73, 0x65, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x44, 0x65, 0x73,
0x64, 0x5f, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1e, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x1a, 0x0a, 0x06, 0x65, 0x76, 0x65, 0x6e,
0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x74, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0c, 0x42, 0x02, 0x18, 0x01, 0x52, 0x06, 0x65, 0x76,
0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x52, 0x0c, 0x65, 0x6e, 0x74, 0x73, 0x12, 0x43, 0x0a, 0x0d, 0x73, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x5f, 0x65,
0x73, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x22, 0x54, 0x0a, 0x1e, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x18, 0x04, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1e, 0x2e, 0x70, 0x72,
0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x4d, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x53, 0x69, 0x67, 0x6e, 0x65, 0x64, 0x43, 0x6f, 0x6d,
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x65, 0x6a, 0x65, 0x63, 0x74, 0x65, 0x64, 0x12, 0x32, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x52, 0x0c, 0x73, 0x69, 0x67,
0x0a, 0x03, 0x6d, 0x73, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x70, 0x72, 0x6e, 0x65, 0x64, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x22, 0x54, 0x0a, 0x1e, 0x43, 0x6f, 0x6d,
0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x4d, 0x65, 0x73, 0x73,
0x45, 0x76, 0x65, 0x6e, 0x74, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x03, 0x6d, 0x61, 0x67, 0x65, 0x52, 0x65, 0x6a, 0x65, 0x63, 0x74, 0x65, 0x64, 0x12, 0x32, 0x0a, 0x03, 0x6d,
0x73, 0x67, 0x42, 0x0d, 0x5a, 0x0b, 0x2e, 0x2f, 0x3b, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x73, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x20, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
0x66, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, 0x62, 0x75, 0x66, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x75, 0x6e, 0x69, 0x74, 0x79, 0x45, 0x76, 0x65,
0x6e, 0x74, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x03, 0x6d, 0x73, 0x67, 0x42,
0x0d, 0x5a, 0x0b, 0x2e, 0x2f, 0x3b, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x62, 0x06,
0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
} }
var ( var (

View File

@ -38,6 +38,7 @@ message CommunityEvent {
COMMUNITY_MEMBER_BAN = 15; COMMUNITY_MEMBER_BAN = 15;
COMMUNITY_MEMBER_UNBAN = 16; COMMUNITY_MEMBER_UNBAN = 16;
COMMUNITY_TOKEN_ADD = 17; COMMUNITY_TOKEN_ADD = 17;
COMMUNITY_DELETE_BANNED_MEMBER_MESSAGES = 18;
} }
} }