2024-09-12 06:56:57 +00:00
|
|
|
package storage
|
|
|
|
|
|
|
|
import (
|
|
|
|
"errors"
|
|
|
|
"strings"
|
|
|
|
|
|
|
|
"github.com/redis/go-redis/v9"
|
2024-11-06 15:57:44 +00:00
|
|
|
"github.com/rs/zerolog/log"
|
|
|
|
"gitlab.com/mstarongitlab/linstrom/util"
|
2024-09-12 06:56:57 +00:00
|
|
|
)
|
|
|
|
|
2024-09-12 14:57:53 +00:00
|
|
|
// various prefixes for accessing items in the cache (since it's a simple key-value store)
|
2024-09-12 06:56:57 +00:00
|
|
|
const (
|
2024-10-15 14:16:18 +00:00
|
|
|
cacheUserHandleToIdPrefix = "acc-name-to-id:"
|
|
|
|
cacheLocalUsernameToIdPrefix = "acc-local-name-to-id:"
|
|
|
|
cachePasskeyIdToAccIdPrefix = "acc-pkey-id-to-id:"
|
|
|
|
cacheUserIdToAccPrefix = "acc-id-to-data:"
|
|
|
|
cacheNoteIdToNotePrefix = "note-id-to-data:"
|
2024-09-12 06:56:57 +00:00
|
|
|
)
|
|
|
|
|
2024-09-12 14:57:53 +00:00
|
|
|
// An error describing the case where some value was just not found in the cache
|
2024-09-12 06:56:57 +00:00
|
|
|
var errCacheNotFound = errors.New("not found in cache")
|
|
|
|
|
2024-10-15 14:16:18 +00:00
|
|
|
// Find an account id in cache using a given user handle ("@bob@example.com" or "bob@example.com")
|
2024-09-12 14:57:53 +00:00
|
|
|
// accId contains the Id of the account if found
|
|
|
|
// err contains an error describing why an account's id couldn't be found
|
|
|
|
// The most common one should be errCacheNotFound
|
|
|
|
func (s *Storage) cacheHandleToAccUid(handle string) (accId *string, err error) {
|
2024-11-06 15:57:44 +00:00
|
|
|
defer util.Untrace(util.Trace(&log.Logger))
|
2024-09-12 06:56:57 +00:00
|
|
|
// Where to put the data (in case it's found)
|
|
|
|
var target string
|
|
|
|
found, err := s.cache.Get(cacheUserHandleToIdPrefix+strings.TrimLeft(handle, "@"), &target)
|
|
|
|
// If nothing was found, check error
|
|
|
|
if !found {
|
|
|
|
// Case error is set and NOT redis' error for nothing found: Return that error
|
|
|
|
if err != nil && !errors.Is(err, redis.Nil) {
|
|
|
|
return nil, err
|
|
|
|
} else {
|
|
|
|
// Else return errCacheNotFound
|
|
|
|
return nil, errCacheNotFound
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &target, nil
|
|
|
|
}
|
|
|
|
|
2024-10-15 14:16:18 +00:00
|
|
|
// Find a local account's id in cache using a given username ("bob")
|
|
|
|
// accId containst the Id of the account if found
|
|
|
|
// err contains an error describing why an account's id couldn't be found
|
|
|
|
// The most common one should be errCacheNotFound
|
|
|
|
func (s *Storage) cacheLocalUsernameToAccUid(username string) (accId *string, err error) {
|
2024-11-06 15:57:44 +00:00
|
|
|
defer util.Untrace(util.Trace(&log.Logger))
|
2024-10-15 14:16:18 +00:00
|
|
|
// Where to put the data (in case it's found)
|
|
|
|
var target string
|
|
|
|
found, err := s.cache.Get(cacheLocalUsernameToIdPrefix+username, &target)
|
|
|
|
// If nothing was found, check error
|
|
|
|
if !found {
|
|
|
|
// Case error is set and NOT redis' error for nothing found: Return that error
|
|
|
|
if err != nil && !errors.Is(err, redis.Nil) {
|
|
|
|
return nil, err
|
|
|
|
} else {
|
|
|
|
// Else return errCacheNotFound
|
|
|
|
return nil, errCacheNotFound
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &target, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (s *Storage) cachePkeyIdToAccId(pkeyId []byte) (accId *string, err error) {
|
2024-11-06 15:57:44 +00:00
|
|
|
defer util.Untrace(util.Trace(&log.Logger))
|
2024-10-15 14:16:18 +00:00
|
|
|
// Where to put the data (in case it's found)
|
|
|
|
var target string
|
|
|
|
found, err := s.cache.Get(cachePasskeyIdToAccIdPrefix+string(pkeyId), &target)
|
|
|
|
// If nothing was found, check error
|
|
|
|
if !found {
|
|
|
|
// Case error is set and NOT redis' error for nothing found: Return that error
|
|
|
|
if err != nil && !errors.Is(err, redis.Nil) {
|
|
|
|
return nil, err
|
|
|
|
} else {
|
|
|
|
// Else return errCacheNotFound
|
|
|
|
return nil, errCacheNotFound
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &target, nil
|
|
|
|
}
|
|
|
|
|
2024-09-12 06:56:57 +00:00
|
|
|
// Find an account's data in cache using a given account id
|
2024-09-12 14:57:53 +00:00
|
|
|
// acc contains the full account as stored last time if found
|
|
|
|
// err contains an error describing why an account couldn't be found
|
|
|
|
// The most common one should be errCacheNotFound
|
|
|
|
func (s *Storage) cacheAccIdToData(id string) (acc *Account, err error) {
|
2024-11-06 15:57:44 +00:00
|
|
|
defer util.Untrace(util.Trace(&log.Logger))
|
2024-09-12 06:56:57 +00:00
|
|
|
var target Account
|
|
|
|
found, err := s.cache.Get(cacheUserIdToAccPrefix+id, &target)
|
|
|
|
if !found {
|
|
|
|
if err != nil && !errors.Is(err, redis.Nil) {
|
|
|
|
return nil, err
|
|
|
|
} else {
|
|
|
|
return nil, errCacheNotFound
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &target, nil
|
|
|
|
}
|
2024-09-12 14:57:53 +00:00
|
|
|
|
|
|
|
// Find a cached note given its ID
|
|
|
|
// note contains the full note as stored last time if found
|
|
|
|
// err contains an error describing why a note couldn't be found
|
|
|
|
// The most common one should be errCacheNotFound
|
|
|
|
func (s *Storage) cacheNoteIdToData(id string) (note *Note, err error) {
|
2024-11-06 15:57:44 +00:00
|
|
|
defer util.Untrace(util.Trace(&log.Logger))
|
2024-09-12 14:57:53 +00:00
|
|
|
target := Note{}
|
|
|
|
found, err := s.cache.Get(cacheNoteIdToNotePrefix+id, &target)
|
|
|
|
if !found {
|
|
|
|
if err != nil && !errors.Is(err, redis.Nil) {
|
|
|
|
return nil, err
|
|
|
|
} else {
|
|
|
|
return nil, errCacheNotFound
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return &target, nil
|
|
|
|
}
|