1
0
Fork 0
mirror of https://github.com/mautrix/discord.git synced 2026-07-06 22:33:18 -04:00
mautrix-discord/pkg/connector/role.go

106 lines
3.1 KiB
Go
Raw Permalink Normal View History

2026-02-25 07:05:44 -08:00
// mautrix-discord - A Matrix-Discord puppeting bridge.
// Copyright (C) 2026 Tulir Asokan
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Affero General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Affero General Public License for more details.
//
// You should have received a copy of the GNU Affero General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
package connector
import (
"context"
"fmt"
"github.com/bwmarrin/discordgo"
"go.mau.fi/mautrix-discord/pkg/connector/discorddb"
)
// (Used by formatter_tag.go via an interface.)
func (d *DiscordConnector) GetRoleByID(ctx context.Context, guildID, roleID string) (*discorddb.Role, error) {
return d.DB.Role.GetByID(ctx, guildID, roleID)
}
func guildRoleChanged(oldRole *discorddb.Role, newRole *discordgo.Role) bool {
return oldRole.Name != newRole.Name ||
oldRole.Icon != newRole.Icon ||
oldRole.Mentionable != newRole.Mentionable ||
oldRole.Managed != newRole.Managed ||
oldRole.Hoist != newRole.Hoist ||
oldRole.Color != newRole.Color ||
oldRole.Position != newRole.Position ||
oldRole.Permissions != newRole.Permissions
}
func (d *DiscordClient) syncGuildRoles(ctx context.Context, guildID string, roles []*discordgo.Role) error {
if len(roles) == 0 {
return nil
}
existingRoles, err := d.connector.DB.Role.GetByGuildID(ctx, guildID)
if err != nil {
return fmt.Errorf("failed to get existing guild roles: %w", err)
}
existingRoleMap := make(map[string]*discorddb.Role, len(existingRoles))
for _, role := range existingRoles {
existingRoleMap[role.ID] = role
}
err = d.connector.DB.Role.GetDB().DoTxn(ctx, nil, func(ctx context.Context) error {
for _, role := range roles {
if role == nil {
continue
}
existingRole := existingRoleMap[role.ID]
if existingRole == nil || guildRoleChanged(existingRole, role) {
if err := d.connector.DB.Role.Put(ctx, &discorddb.Role{
GuildID: guildID,
Role: *role,
}); err != nil {
return fmt.Errorf("failed to upsert guild role: %w", err)
}
}
delete(existingRoleMap, role.ID)
}
for _, removedRole := range existingRoleMap {
if err := d.connector.DB.Role.DeleteByID(ctx, guildID, removedRole.ID); err != nil {
return fmt.Errorf("failed to delete removed guild role: %w", err)
}
}
return nil
})
if err != nil {
return fmt.Errorf("failed to sync guild roles: %w", err)
}
return nil
}
func (d *DiscordClient) upsertGuildRole(ctx context.Context, guildID string, role *discordgo.Role) error {
if role == nil {
return nil
}
if err := d.connector.DB.Role.Put(ctx, &discorddb.Role{
GuildID: guildID,
Role: *role,
}); err != nil {
return fmt.Errorf("failed to upsert guild role: %w", err)
}
return nil
}