All checks were successful
/ docker (push) Successful in 3m58s
Other software might use different IDs that aren't UUIDs, so shouldn't lock own IDs into UUID either
136 lines
6.7 KiB
Go
136 lines
6.7 KiB
Go
package models
|
|
|
|
import (
|
|
"database/sql"
|
|
"time"
|
|
|
|
"gorm.io/gen"
|
|
"gorm.io/gorm"
|
|
)
|
|
|
|
// A user describes an account for creating content and events.
|
|
// This may be controlled by either a human or some external script
|
|
//
|
|
// Data stored externally:
|
|
// - Feed connections (which note belongs in the feed of this user, for what reason), see [NoteToFeed]
|
|
type User struct {
|
|
// ID is a uuid for this account
|
|
//
|
|
// NOTE: Performance and storage wise, using a UUID (as string) for the primary key
|
|
// is not the best idea and it would be better to use incrementing integers
|
|
// Additionally, there is a risk with inconsistency if postgres crashes during a commit
|
|
// in which case the new entry might not have a valid Id with which it could be found
|
|
// and the username is lost until manual recovery
|
|
// However, a UUID is still necessary in some way to provide a (secondary) stable
|
|
// identifier for users and other servers, especially when changing the username
|
|
// (username != display name) might be a future feature
|
|
// Same also applies for other types that use a UUID as primary key
|
|
ID string `gorm:"primarykey;default:gen_random_uuid()" json:"id"`
|
|
// Username of the user (eg "max" if the full username is @max@example.com)
|
|
// Assume unchangable (once set by a user) to be kind to other implementations
|
|
// Would be an easy avenue to fuck with them though
|
|
Username string `gorm:"unique" json:"username"`
|
|
CreatedAt time.Time ` json:"created_at"` // When this entry was created. Automatically set by gorm
|
|
// When this account was last updated. Will also be used for refreshing remote accounts. Automatically set by gorm
|
|
UpdatedAt time.Time ` json:"updated_at"`
|
|
// When this entry was deleted (for soft deletions)
|
|
// Soft delete means that this entry still exists in the db, but gorm won't include it anymore unless specifically told to
|
|
// If not null, this entry is marked as deleted
|
|
DeletedAt gorm.DeletedAt `gorm:"index" json:"deleted_at"`
|
|
Server RemoteServer ` json:"-"`
|
|
ServerId uint ` json:"server_id"` // Id of the server this user is from, needed for including RemoteServer
|
|
DisplayName string ` json:"display_name"` // The display name of the user. Can be different from the handle
|
|
Description string ` json:"description"` // The description of a user account
|
|
IsBot bool ` json:"is_bot"` // Whether to mark this account as a script controlled one
|
|
Icon *MediaMetadata ` json:"-"`
|
|
IconId sql.NullString ` json:"icon_id"` // ID of a media file used as icon
|
|
Background *MediaMetadata ` json:"-"`
|
|
BackgroundId sql.NullString ` json:"background_id"` // ID of a media file used as background image
|
|
Banner *MediaMetadata ` json:"-"`
|
|
BannerId sql.NullString ` json:"banner_id"` // ID of a media file used as banner
|
|
Indexable bool ` json:"indexable"` // Whether this account can be found by crawlers
|
|
PublicKeyRsa []byte ` json:"public_key_rsa"` // The public RSA key of the account
|
|
PublicKeyEd []byte ` json:"public_key_ed"` // The public Ed25519 key of the account
|
|
// Whether this account restricts following
|
|
// If true, the owner must approve of a follow request first
|
|
RestrictedFollow bool ` json:"restricted_follow"`
|
|
|
|
Location sql.NullString `json:"location"`
|
|
Birthday sql.NullTime `json:"birthday"`
|
|
|
|
// Whether the account got verified and is allowed to be active
|
|
// For local accounts being active means being allowed to login and perform interactions
|
|
// For remote users, if an account is not verified, any interactions it sends are discarded
|
|
Verified bool `json:"verified"`
|
|
// 64 byte unique id for passkeys, because UUIDs are 128 bytes and passkey spec says 64 bytes max
|
|
// In theory, could also slash Id in half, but that would be a lot more calculations than the
|
|
// saved space is worth
|
|
PasskeyId []byte `json:"-"`
|
|
FinishedRegistration bool `json:"-"` // Whether this account has completed registration yet
|
|
PrivateKeyRsa []byte `json:"-"`
|
|
PrivateKeyEd []byte `json:"-"`
|
|
|
|
// ---- "Remote" linked values
|
|
InfoFields []UserInfoField `json:"-"`
|
|
BeingTypes []UserToBeing `json:"-"`
|
|
Tags []UserToTag `json:"-"`
|
|
Relations []UserToUserRelation `json:"-"`
|
|
Pronouns []UserToPronoun `json:"-"`
|
|
Roles []UserToRole `json:"-"`
|
|
RemoteInfo *UserRemoteLinks `json:"-"`
|
|
AuthMethods []UserAuthMethod `json:"-"`
|
|
}
|
|
|
|
type IUser interface {
|
|
// Get a user by a username, ignoring all restrictions on that user
|
|
//
|
|
// SELECT * FROM @@table WHERE username = @username AND deleted_at IS NULL LIMIT 1
|
|
GetByUsernameUnrestricted(username string) (*gen.T, error)
|
|
|
|
// Get a user by the username.
|
|
// Restricted to users visible to ActivityPub
|
|
//
|
|
// SELECT * FROM @@table WHERE
|
|
// username = @username AND
|
|
// deleted_at IS NULL AND
|
|
// finished_registration = true AND
|
|
// verified = true
|
|
// LIMIT 1
|
|
GetByUsername(username string) (*gen.T, error)
|
|
|
|
// Get all true public accounts (verified & no restricted follow & indexable)
|
|
// in a paged manner, sorted by date saved
|
|
//
|
|
// SELECT * FROM @@table WHERE
|
|
// deleted_at IS NULL AND
|
|
// verified = true AND
|
|
// restricted_follow = false AND
|
|
// indexable = true
|
|
// ORDER BY created_at ASC
|
|
// LIMIT 50
|
|
// OFFSET @pageNr * 50
|
|
GetPagedTruePublic(pageNr uint) ([]gen.T, error)
|
|
|
|
// Get all deleted accounts in a paged manner, sorted by date saved
|
|
//
|
|
// SELECT * FROM @@table WHERE
|
|
// deleted_at IS NOT NULL AND
|
|
// ORDER BY created_at ASC
|
|
// LIMIT 50
|
|
// OFFSET @pageNr * 50
|
|
GetPagedAllDeleted(pageNr uint) ([]gen.T, error)
|
|
|
|
// Get all accounts that aren't deleted in a paged manner, sorted by date saved
|
|
//
|
|
// SELECT * FROM @@table WHERE
|
|
// deleted_at IS NULL
|
|
// ORDER BY created_at ASC
|
|
// LIMIT 50
|
|
// OFFSET @pageNr * 50
|
|
GetPagedAllNonDeleted(pageNr uint) ([]gen.T, error)
|
|
|
|
// Gdpr deleted users
|
|
//
|
|
// DELETE FROM @@table WHERE deleted_at IS NOT NULL AND deleted_at + interval '30 days' < NOW()
|
|
GdprUsers() error
|
|
}
|