mirror of
https://github.com/maubot/maubot
synced 2025-08-30 13:20:38 +00:00
Update dependencies
This commit is contained in:
parent
22ef8195dd
commit
2a0106da26
17 changed files with 1229 additions and 347 deletions
499
vendor/maunium.net/go/gomatrix/events.go
generated
vendored
499
vendor/maunium.net/go/gomatrix/events.go
generated
vendored
|
@ -1,110 +1,447 @@
|
|||
package gomatrix
|
||||
|
||||
import (
|
||||
"html"
|
||||
"regexp"
|
||||
"encoding/json"
|
||||
"strings"
|
||||
"sync"
|
||||
)
|
||||
|
||||
type EventTypeClass int
|
||||
|
||||
const (
|
||||
// Normal message events
|
||||
MessageEventType EventTypeClass = iota
|
||||
// State events
|
||||
StateEventType
|
||||
// Ephemeral events
|
||||
EphemeralEventType
|
||||
// Account data events
|
||||
AccountDataEventType
|
||||
// Unknown events
|
||||
UnknownEventType
|
||||
)
|
||||
|
||||
type EventType struct {
|
||||
Type string
|
||||
Class EventTypeClass
|
||||
}
|
||||
|
||||
func NewEventType(name string) EventType {
|
||||
evtType := EventType{Type: name}
|
||||
evtType.Class = evtType.GuessClass()
|
||||
return evtType
|
||||
}
|
||||
|
||||
func (et *EventType) IsState() bool {
|
||||
return et.Class == StateEventType
|
||||
}
|
||||
|
||||
func (et *EventType) IsEphemeral() bool {
|
||||
return et.Class == EphemeralEventType
|
||||
}
|
||||
|
||||
func (et *EventType) IsCustom() bool {
|
||||
return !strings.HasPrefix(et.Type, "m.")
|
||||
}
|
||||
|
||||
func (et *EventType) GuessClass() EventTypeClass {
|
||||
switch et.Type {
|
||||
case StateAliases.Type, StateCanonicalAlias.Type, StateCreate.Type, StateJoinRules.Type, StateMember.Type,
|
||||
StatePowerLevels.Type, StateRoomName.Type, StateRoomAvatar.Type, StateTopic.Type, StatePinnedEvents.Type:
|
||||
return StateEventType
|
||||
case EphemeralEventReceipt.Type, EphemeralEventTyping.Type:
|
||||
return EphemeralEventType
|
||||
case AccountDataDirectChats.Type, AccountDataPushRules.Type, AccountDataRoomTags.Type:
|
||||
return AccountDataEventType
|
||||
case EventRedaction.Type, EventMessage.Type, EventSticker.Type:
|
||||
return MessageEventType
|
||||
default:
|
||||
return UnknownEventType
|
||||
}
|
||||
}
|
||||
|
||||
func (et *EventType) UnmarshalJSON(data []byte) error {
|
||||
err := json.Unmarshal(data, &et.Type)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
et.Class = et.GuessClass()
|
||||
return nil
|
||||
}
|
||||
|
||||
func (et *EventType) MarshalJSON() ([]byte, error) {
|
||||
return json.Marshal(&et.Type)
|
||||
}
|
||||
|
||||
func (et *EventType) String() string {
|
||||
return et.Type
|
||||
}
|
||||
|
||||
// State events
|
||||
var (
|
||||
StateAliases = EventType{"m.room.aliases", StateEventType}
|
||||
StateCanonicalAlias = EventType{"m.room.canonical_alias", StateEventType}
|
||||
StateCreate = EventType{"m.room.create", StateEventType}
|
||||
StateJoinRules = EventType{"m.room.join_rules", StateEventType}
|
||||
StateMember = EventType{"m.room.member", StateEventType}
|
||||
StatePowerLevels = EventType{"m.room.power_levels", StateEventType}
|
||||
StateRoomName = EventType{"m.room.name", StateEventType}
|
||||
StateTopic = EventType{"m.room.topic", StateEventType}
|
||||
StateRoomAvatar = EventType{"m.room.avatar", StateEventType}
|
||||
StatePinnedEvents = EventType{"m.room.pinned_events", StateEventType}
|
||||
)
|
||||
|
||||
// Message events
|
||||
var (
|
||||
EventRedaction = EventType{"m.room.redaction", MessageEventType}
|
||||
EventMessage = EventType{"m.room.message", MessageEventType}
|
||||
EventSticker = EventType{"m.sticker", MessageEventType}
|
||||
)
|
||||
|
||||
// Ephemeral events
|
||||
var (
|
||||
EphemeralEventReceipt = EventType{"m.receipt", EphemeralEventType}
|
||||
EphemeralEventTyping = EventType{"m.typing", EphemeralEventType}
|
||||
)
|
||||
|
||||
// Account data events
|
||||
var (
|
||||
AccountDataDirectChats = EventType{"m.direct", AccountDataEventType}
|
||||
AccountDataPushRules = EventType{"m.push_rules", AccountDataEventType}
|
||||
AccountDataRoomTags = EventType{"m.tag", AccountDataEventType}
|
||||
)
|
||||
|
||||
type MessageType string
|
||||
|
||||
// Msgtypes
|
||||
const (
|
||||
MsgText MessageType = "m.text"
|
||||
MsgEmote = "m.emote"
|
||||
MsgNotice = "m.notice"
|
||||
MsgImage = "m.image"
|
||||
MsgLocation = "m.location"
|
||||
MsgVideo = "m.video"
|
||||
MsgAudio = "m.audio"
|
||||
MsgFile = "m.file"
|
||||
)
|
||||
|
||||
type Format string
|
||||
|
||||
// Message formats
|
||||
const (
|
||||
FormatHTML Format = "org.matrix.custom.html"
|
||||
)
|
||||
|
||||
// Event represents a single Matrix event.
|
||||
type Event struct {
|
||||
StateKey *string `json:"state_key,omitempty"` // The state key for the event. Only present on State Events.
|
||||
Sender string `json:"sender"` // The user ID of the sender of the event
|
||||
Type string `json:"type"` // The event type
|
||||
Timestamp int64 `json:"origin_server_ts"` // The unix timestamp when this message was sent by the origin server
|
||||
ID string `json:"event_id"` // The unique ID of this event
|
||||
RoomID string `json:"room_id"` // The room the event was sent to. May be nil (e.g. for presence)
|
||||
Content map[string]interface{} `json:"content"` // The JSON content of the event.
|
||||
Redacts string `json:"redacts,omitempty"` // The event ID that was redacted if a m.room.redaction event
|
||||
Unsigned Unsigned `json:"unsigned,omitempty"` // Unsigned content set by own homeserver.
|
||||
StateKey *string `json:"state_key,omitempty"` // The state key for the event. Only present on State Events.
|
||||
Sender string `json:"sender"` // The user ID of the sender of the event
|
||||
Type EventType `json:"type"` // The event type
|
||||
Timestamp int64 `json:"origin_server_ts"` // The unix timestamp when this message was sent by the origin server
|
||||
ID string `json:"event_id"` // The unique ID of this event
|
||||
RoomID string `json:"room_id"` // The room the event was sent to. May be nil (e.g. for presence)
|
||||
Content Content `json:"content"` // The JSON content of the event.
|
||||
Redacts string `json:"redacts,omitempty"` // The event ID that was redacted if a m.room.redaction event
|
||||
Unsigned Unsigned `json:"unsigned,omitempty"` // Unsigned content set by own homeserver.
|
||||
|
||||
InviteRoomState []StrippedState `json:"invite_room_state"`
|
||||
}
|
||||
|
||||
func (evt *Event) GetStateKey() string {
|
||||
if evt.StateKey != nil {
|
||||
return *evt.StateKey
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
type StrippedState struct {
|
||||
Content Content `json:"content"`
|
||||
Type EventType `json:"type"`
|
||||
StateKey string `json:"state_key"`
|
||||
}
|
||||
|
||||
type Unsigned struct {
|
||||
PrevContent map[string]interface{} `json:"prev_content,omitempty"`
|
||||
PrevSender string `json:"prev_sender,omitempty"`
|
||||
ReplacesState string `json:"replaces_state,omitempty"`
|
||||
Age int64 `json:"age"`
|
||||
PrevContent *Content `json:"prev_content,omitempty"`
|
||||
PrevSender string `json:"prev_sender,omitempty"`
|
||||
ReplacesState string `json:"replaces_state,omitempty"`
|
||||
Age int64 `json:"age,omitempty"`
|
||||
|
||||
PassiveCommand map[string]*MatchedPassiveCommand `json:"m.passive_command,omitempty"`
|
||||
}
|
||||
|
||||
// Body returns the value of the "body" key in the event content if it is
|
||||
// present and is a string.
|
||||
func (event *Event) Body() (body string, ok bool) {
|
||||
value, exists := event.Content["body"]
|
||||
if !exists {
|
||||
return
|
||||
type MatchedPassiveCommand struct {
|
||||
// Matched string `json:"matched"`
|
||||
// Value string `json:"value"`
|
||||
Captured [][]string `json:"captured"`
|
||||
|
||||
BackCompatCommand string `json:"command"`
|
||||
BackCompatArguments map[string]string `json:"arguments"`
|
||||
}
|
||||
|
||||
type Content struct {
|
||||
VeryRaw json.RawMessage `json:"-"`
|
||||
Raw map[string]interface{} `json:"-"`
|
||||
|
||||
MsgType MessageType `json:"msgtype,omitempty"`
|
||||
Body string `json:"body,omitempty"`
|
||||
Format Format `json:"format,omitempty"`
|
||||
FormattedBody string `json:"formatted_body,omitempty"`
|
||||
|
||||
Info *FileInfo `json:"info,omitempty"`
|
||||
URL string `json:"url,omitempty"`
|
||||
|
||||
// Membership key for easy access in m.room.member events
|
||||
Membership Membership `json:"membership,omitempty"`
|
||||
|
||||
RelatesTo *RelatesTo `json:"m.relates_to,omitempty"`
|
||||
Command *MatchedCommand `json:"m.command,omitempty"`
|
||||
|
||||
PowerLevels
|
||||
Member
|
||||
Aliases []string `json:"aliases,omitempty"`
|
||||
CanonicalAlias
|
||||
RoomName
|
||||
RoomTopic
|
||||
|
||||
RoomTags Tags `json:"tags,omitempty"`
|
||||
TypingUserIDs []string `json:"user_ids,omitempty"`
|
||||
}
|
||||
|
||||
type serializableContent Content
|
||||
|
||||
var DisableFancyEventParsing = false
|
||||
|
||||
func (content *Content) UnmarshalJSON(data []byte) error {
|
||||
content.VeryRaw = data
|
||||
if err := json.Unmarshal(data, &content.Raw); err != nil || DisableFancyEventParsing {
|
||||
return err
|
||||
}
|
||||
body, ok = value.(string)
|
||||
return json.Unmarshal(data, (*serializableContent)(content))
|
||||
}
|
||||
|
||||
func (content *Content) GetCommand() *MatchedCommand {
|
||||
if content.Command == nil {
|
||||
content.Command = &MatchedCommand{}
|
||||
}
|
||||
return content.Command
|
||||
}
|
||||
|
||||
func (content *Content) GetRelatesTo() *RelatesTo {
|
||||
if content.RelatesTo == nil {
|
||||
content.RelatesTo = &RelatesTo{}
|
||||
}
|
||||
return content.RelatesTo
|
||||
}
|
||||
|
||||
func (content *Content) UnmarshalPowerLevels() (pl PowerLevels, err error) {
|
||||
err = json.Unmarshal(content.VeryRaw, &pl)
|
||||
return
|
||||
}
|
||||
|
||||
// MessageType returns the value of the "msgtype" key in the event content if
|
||||
// it is present and is a string.
|
||||
func (event *Event) MessageType() (msgtype string, ok bool) {
|
||||
value, exists := event.Content["msgtype"]
|
||||
if !exists {
|
||||
return
|
||||
}
|
||||
msgtype, ok = value.(string)
|
||||
func (content *Content) UnmarshalMember() (m Member, err error) {
|
||||
err = json.Unmarshal(content.VeryRaw, &m)
|
||||
return
|
||||
}
|
||||
|
||||
// TextMessage is the contents of a Matrix formated message event.
|
||||
type TextMessage struct {
|
||||
MsgType string `json:"msgtype"`
|
||||
Body string `json:"body"`
|
||||
func (content *Content) UnmarshalCanonicalAlias() (ca CanonicalAlias, err error) {
|
||||
err = json.Unmarshal(content.VeryRaw, &ca)
|
||||
return
|
||||
}
|
||||
|
||||
// ImageInfo contains info about an image - http://matrix.org/docs/spec/client_server/r0.2.0.html#m-image
|
||||
type ImageInfo struct {
|
||||
Height uint `json:"h,omitempty"`
|
||||
Width uint `json:"w,omitempty"`
|
||||
Mimetype string `json:"mimetype,omitempty"`
|
||||
Size uint `json:"size,omitempty"`
|
||||
func (content *Content) GetInfo() *FileInfo {
|
||||
if content.Info == nil {
|
||||
content.Info = &FileInfo{}
|
||||
}
|
||||
return content.Info
|
||||
}
|
||||
|
||||
// VideoInfo contains info about a video - http://matrix.org/docs/spec/client_server/r0.2.0.html#m-video
|
||||
type VideoInfo struct {
|
||||
Mimetype string `json:"mimetype,omitempty"`
|
||||
ThumbnailInfo ImageInfo `json:"thumbnail_info"`
|
||||
type Tags map[string]struct {
|
||||
Order string `json:"order"`
|
||||
}
|
||||
|
||||
type RoomName struct {
|
||||
Name string `json:"name,omitempty"`
|
||||
}
|
||||
|
||||
type RoomTopic struct {
|
||||
Topic string `json:"topic,omitempty"`
|
||||
}
|
||||
|
||||
// Membership is an enum specifying the membership state of a room member.
|
||||
type Membership string
|
||||
|
||||
// The allowed membership states as specified in spec section 10.5.5.
|
||||
const (
|
||||
MembershipJoin Membership = "join"
|
||||
MembershipLeave Membership = "leave"
|
||||
MembershipInvite Membership = "invite"
|
||||
MembershipBan Membership = "ban"
|
||||
MembershipKnock Membership = "knock"
|
||||
)
|
||||
|
||||
type Member struct {
|
||||
Membership Membership `json:"membership,omitempty"`
|
||||
AvatarURL string `json:"avatar_url,omitempty"`
|
||||
Displayname string `json:"displayname,omitempty"`
|
||||
ThirdPartyInvite *ThirdPartyInvite `json:"third_party_invite,omitempty"`
|
||||
Reason string `json:"reason,omitempty"`
|
||||
}
|
||||
|
||||
type ThirdPartyInvite struct {
|
||||
DisplayName string `json:"display_name"`
|
||||
Signed struct {
|
||||
Token string `json:"token"`
|
||||
Signatures json.RawMessage `json:"signatures"`
|
||||
MXID string `json:"mxid"`
|
||||
}
|
||||
}
|
||||
|
||||
type CanonicalAlias struct {
|
||||
Alias string `json:"alias,omitempty"`
|
||||
}
|
||||
|
||||
type PowerLevels struct {
|
||||
usersLock sync.RWMutex `json:"-"`
|
||||
Users map[string]int `json:"users,omitempty"`
|
||||
UsersDefault int `json:"users_default,omitempty"`
|
||||
|
||||
eventsLock sync.RWMutex `json:"-"`
|
||||
Events map[string]int `json:"events,omitempty"`
|
||||
EventsDefault int `json:"events_default,omitempty"`
|
||||
|
||||
StateDefaultPtr *int `json:"state_default,omitempty"`
|
||||
|
||||
InvitePtr *int `json:"invite,omitempty"`
|
||||
KickPtr *int `json:"kick,omitempty"`
|
||||
BanPtr *int `json:"ban,omitempty"`
|
||||
RedactPtr *int `json:"redact,omitempty"`
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) Invite() int {
|
||||
if pl.InvitePtr != nil {
|
||||
return *pl.InvitePtr
|
||||
}
|
||||
return 50
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) Kick() int {
|
||||
if pl.KickPtr != nil {
|
||||
return *pl.KickPtr
|
||||
}
|
||||
return 50
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) Ban() int {
|
||||
if pl.BanPtr != nil {
|
||||
return *pl.BanPtr
|
||||
}
|
||||
return 50
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) Redact() int {
|
||||
if pl.RedactPtr != nil {
|
||||
return *pl.RedactPtr
|
||||
}
|
||||
return 50
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) StateDefault() int {
|
||||
if pl.StateDefaultPtr != nil {
|
||||
return *pl.StateDefaultPtr
|
||||
}
|
||||
return 50
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) GetUserLevel(userID string) int {
|
||||
pl.usersLock.RLock()
|
||||
defer pl.usersLock.RUnlock()
|
||||
level, ok := pl.Users[userID]
|
||||
if !ok {
|
||||
return pl.UsersDefault
|
||||
}
|
||||
return level
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) SetUserLevel(userID string, level int) {
|
||||
pl.usersLock.Lock()
|
||||
defer pl.usersLock.Unlock()
|
||||
if level == pl.UsersDefault {
|
||||
delete(pl.Users, userID)
|
||||
} else {
|
||||
pl.Users[userID] = level
|
||||
}
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) EnsureUserLevel(userID string, level int) bool {
|
||||
existingLevel := pl.GetUserLevel(userID)
|
||||
if existingLevel != level {
|
||||
pl.SetUserLevel(userID, level)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) GetEventLevel(eventType EventType) int {
|
||||
pl.eventsLock.RLock()
|
||||
defer pl.eventsLock.RUnlock()
|
||||
level, ok := pl.Events[eventType.String()]
|
||||
if !ok {
|
||||
if eventType.IsState() {
|
||||
return pl.StateDefault()
|
||||
}
|
||||
return pl.EventsDefault
|
||||
}
|
||||
return level
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) SetEventLevel(eventType EventType, level int) {
|
||||
pl.eventsLock.Lock()
|
||||
defer pl.eventsLock.Unlock()
|
||||
if (eventType.IsState() && level == pl.StateDefault()) || (!eventType.IsState() && level == pl.EventsDefault) {
|
||||
delete(pl.Events, eventType.String())
|
||||
} else {
|
||||
pl.Events[eventType.String()] = level
|
||||
}
|
||||
}
|
||||
|
||||
func (pl *PowerLevels) EnsureEventLevel(eventType EventType, level int) bool {
|
||||
existingLevel := pl.GetEventLevel(eventType)
|
||||
if existingLevel != level {
|
||||
pl.SetEventLevel(eventType, level)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
type FileInfo struct {
|
||||
MimeType string `json:"mimetype,omitempty"`
|
||||
ThumbnailInfo *FileInfo `json:"thumbnail_info,omitempty"`
|
||||
ThumbnailURL string `json:"thumbnail_url,omitempty"`
|
||||
Height uint `json:"h,omitempty"`
|
||||
Width uint `json:"w,omitempty"`
|
||||
Height int `json:"h,omitempty"`
|
||||
Width int `json:"w,omitempty"`
|
||||
Duration uint `json:"duration,omitempty"`
|
||||
Size uint `json:"size,omitempty"`
|
||||
Size int `json:"size,omitempty"`
|
||||
}
|
||||
|
||||
// VideoMessage is an m.video - http://matrix.org/docs/spec/client_server/r0.2.0.html#m-video
|
||||
type VideoMessage struct {
|
||||
MsgType string `json:"msgtype"`
|
||||
Body string `json:"body"`
|
||||
URL string `json:"url"`
|
||||
Info VideoInfo `json:"info"`
|
||||
}
|
||||
|
||||
// ImageMessage is an m.image event
|
||||
type ImageMessage struct {
|
||||
MsgType string `json:"msgtype"`
|
||||
Body string `json:"body"`
|
||||
URL string `json:"url"`
|
||||
Info ImageInfo `json:"info"`
|
||||
}
|
||||
|
||||
// An HTMLMessage is the contents of a Matrix HTML formated message event.
|
||||
type HTMLMessage struct {
|
||||
Body string `json:"body"`
|
||||
MsgType string `json:"msgtype"`
|
||||
Format string `json:"format"`
|
||||
FormattedBody string `json:"formatted_body"`
|
||||
}
|
||||
|
||||
var htmlRegex = regexp.MustCompile("<[^<]+?>")
|
||||
|
||||
// GetHTMLMessage returns an HTMLMessage with the body set to a stripped version of the provided HTML, in addition
|
||||
// to the provided HTML.
|
||||
func GetHTMLMessage(msgtype, htmlText string) HTMLMessage {
|
||||
return HTMLMessage{
|
||||
Body: html.UnescapeString(htmlRegex.ReplaceAllLiteralString(htmlText, "")),
|
||||
MsgType: msgtype,
|
||||
Format: "org.matrix.custom.html",
|
||||
FormattedBody: htmlText,
|
||||
func (fileInfo *FileInfo) GetThumbnailInfo() *FileInfo {
|
||||
if fileInfo.ThumbnailInfo == nil {
|
||||
fileInfo.ThumbnailInfo = &FileInfo{}
|
||||
}
|
||||
return fileInfo.ThumbnailInfo
|
||||
}
|
||||
|
||||
type RelatesTo struct {
|
||||
InReplyTo InReplyTo `json:"m.in_reply_to,omitempty"`
|
||||
}
|
||||
|
||||
type InReplyTo struct {
|
||||
EventID string `json:"event_id,omitempty"`
|
||||
// Not required, just for future-proofing
|
||||
RoomID string `json:"room_id,omitempty"`
|
||||
}
|
||||
|
||||
type MatchedCommand struct {
|
||||
Target string `json:"target"`
|
||||
Matched string `json:"matched"`
|
||||
Arguments map[string]string `json:"arguments"`
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue