2022-07-17 17:22:28 -04:00
|
|
|
package matrixbotlib
|
|
|
|
|
|
|
|
import (
|
2023-10-12 21:49:42 -04:00
|
|
|
"log"
|
2023-10-12 20:51:08 -04:00
|
|
|
"os"
|
2022-07-17 17:22:28 -04:00
|
|
|
"strings"
|
|
|
|
|
2023-10-12 20:51:08 -04:00
|
|
|
"gopkg.in/yaml.v2"
|
2022-07-17 17:22:28 -04:00
|
|
|
"maunium.net/go/mautrix"
|
2023-05-30 17:50:10 -04:00
|
|
|
"maunium.net/go/mautrix/event"
|
2022-07-17 17:22:28 -04:00
|
|
|
"maunium.net/go/mautrix/id"
|
|
|
|
)
|
|
|
|
|
2023-10-12 20:51:08 -04:00
|
|
|
// NewMatrixClient returns a new logged in Mautrix Client struct
|
2022-07-17 17:22:28 -04:00
|
|
|
func NewMatrixClient(config *MatrixClientConfig, store mautrix.Storer) (*mautrix.Client, error) {
|
|
|
|
var client *mautrix.Client
|
|
|
|
var err error
|
2023-10-12 20:51:08 -04:00
|
|
|
// make sure username is lower case otherwise token login breaks
|
2022-07-17 17:22:28 -04:00
|
|
|
uname := strings.ToLower(config.Username)
|
|
|
|
if config.Token == "" {
|
|
|
|
client, err = mautrix.NewClient(config.Homeserver, "", "")
|
|
|
|
if err != nil {
|
|
|
|
return client, err
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
client, err = mautrix.NewClient(config.Homeserver, id.NewUserID(uname, config.Domain), config.Token)
|
|
|
|
if err != nil {
|
|
|
|
return client, err
|
|
|
|
}
|
|
|
|
}
|
|
|
|
client.Store = store
|
|
|
|
if config.Token == "" {
|
|
|
|
loginRes, err := client.Login(&mautrix.ReqLogin{
|
|
|
|
Type: "m.login.password",
|
|
|
|
Identifier: mautrix.UserIdentifier{Type: mautrix.IdentifierTypeUser, User: uname},
|
|
|
|
Password: config.Password,
|
|
|
|
StoreCredentials: true,
|
|
|
|
})
|
|
|
|
if err != nil {
|
|
|
|
return client, err
|
|
|
|
}
|
|
|
|
config.Token = loginRes.AccessToken
|
2023-10-12 20:51:08 -04:00
|
|
|
err = SyncToken(config)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
2022-07-17 17:22:28 -04:00
|
|
|
}
|
|
|
|
return client, err
|
|
|
|
}
|
2023-05-30 17:50:10 -04:00
|
|
|
|
2023-10-12 20:51:08 -04:00
|
|
|
func SyncToken(config *MatrixClientConfig) error {
|
2023-10-12 21:49:42 -04:00
|
|
|
log.Println("syncing token")
|
|
|
|
|
|
|
|
t := make(map[string]interface{})
|
|
|
|
data, err := os.ReadFile(config.filename)
|
2023-10-12 20:51:08 -04:00
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
2023-10-12 21:49:42 -04:00
|
|
|
err = yaml.Unmarshal([]byte(data), &t)
|
2023-10-12 20:51:08 -04:00
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
2023-10-12 21:49:42 -04:00
|
|
|
log.Println(t)
|
2023-10-12 20:51:08 -04:00
|
|
|
t["token"] = config.Token
|
2023-10-12 21:49:42 -04:00
|
|
|
file, err := os.OpenFile(config.filename, os.O_RDWR|os.O_CREATE|os.O_TRUNC, 0o600)
|
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
defer file.Close()
|
|
|
|
|
2023-10-12 20:51:08 -04:00
|
|
|
enc := yaml.NewEncoder(file)
|
|
|
|
|
|
|
|
err = enc.Encode(t)
|
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2023-05-30 17:50:10 -04:00
|
|
|
// SetupAccountDataStore sets the client to use a AccountData store and filter appropriately
|
|
|
|
func SetupAccountDataStore(client *mautrix.Client, token string) error {
|
|
|
|
dataFilter := &mautrix.Filter{
|
|
|
|
AccountData: mautrix.FilterPart{
|
|
|
|
Limit: 20,
|
|
|
|
NotTypes: []event.Type{
|
|
|
|
event.NewEventType(token),
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
|
|
|
store := mautrix.NewAccountDataStore(token, client)
|
|
|
|
fID, err := client.CreateFilter(dataFilter)
|
|
|
|
if err != nil {
|
2023-10-12 20:51:08 -04:00
|
|
|
// don't want to continue if we can't keep state
|
2023-05-30 17:50:10 -04:00
|
|
|
return err
|
|
|
|
}
|
|
|
|
uid := client.UserID
|
|
|
|
store.SaveFilterID(uid, fID.FilterID)
|
|
|
|
client.Store = store
|
|
|
|
return nil
|
|
|
|
}
|