2023-09-02 00:12:27 +00:00
|
|
|
package models
|
|
|
|
|
2024-06-30 04:42:35 +00:00
|
|
|
// Supplementary functions to do with Shy Accounts.
|
2023-09-02 00:12:27 +00:00
|
|
|
|
|
|
|
import "code.nonshy.com/nonshy/website/pkg/log"
|
|
|
|
|
|
|
|
// IsShy returns whether the user might have an "empty" profile from the perspective of anybody.
|
|
|
|
//
|
|
|
|
// An empty profile means their profile is Private or else ALL of their photos are non-public; so that
|
|
|
|
// somebody viewing their page might see nothing at all from them and consider them a "blank" profile.
|
|
|
|
func (u *User) IsShy() bool {
|
|
|
|
// NOTE: if you change the logic for Shy Accounts, also align your changes
|
|
|
|
// in the functions: WhereClauseShyAccounts.
|
|
|
|
|
|
|
|
// Non-certified users are considered empty.
|
|
|
|
if !u.Certified {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
|
|
|
|
// Private profile automatically applies.
|
|
|
|
if u.Visibility == UserVisibilityPrivate {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
|
|
|
|
// If ALL of our photos are non-public, that counts too.
|
|
|
|
var photoTypes = u.DistinctPhotoTypes()
|
|
|
|
if _, ok := photoTypes[PhotoPublic]; !ok {
|
|
|
|
log.Info("IsEmptyProfile: true because visibilities %+v did not include public", photoTypes)
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
|
|
|
|
// WhereClauseShyAccounts returns SQL query fragments when running User table queries
|
|
|
|
// that will filter for shy accounts.
|
|
|
|
//
|
|
|
|
// This is used by SearchUsers and MapShyAccounts.
|
|
|
|
func WhereClauseShyAccounts() (where string, placeholders []interface{}) {
|
|
|
|
where = `(
|
|
|
|
certified IS NOT true
|
|
|
|
OR visibility = ?
|
|
|
|
OR NOT EXISTS (
|
|
|
|
SELECT 1 FROM photos
|
|
|
|
WHERE user_id = users.id
|
|
|
|
AND visibility = ?
|
|
|
|
)
|
|
|
|
)`
|
|
|
|
placeholders = []interface{}{
|
|
|
|
UserVisibilityPrivate,
|
|
|
|
PhotoPublic,
|
|
|
|
}
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// ShyMap maps user IDs to Shy Account status in bulk queries.
|
|
|
|
type ShyMap map[uint64]bool
|
|
|
|
|
|
|
|
// MapShyAccounts looks up a set of user IDs in bulk and returns a ShyMap suitable for templates.
|
|
|
|
func MapShyAccounts(users []*User) ShyMap {
|
|
|
|
var (
|
|
|
|
usermap = ShyMap{}
|
|
|
|
set = map[uint64]interface{}{}
|
|
|
|
distinct = []uint64{}
|
|
|
|
)
|
|
|
|
|
|
|
|
// Uniqueify users.
|
|
|
|
for _, user := range users {
|
|
|
|
if _, ok := set[user.ID]; ok {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
set[user.ID] = nil
|
|
|
|
distinct = append(distinct, user.ID)
|
|
|
|
}
|
|
|
|
|
|
|
|
var (
|
|
|
|
matched = []*User{}
|
|
|
|
where, placeholders = WhereClauseShyAccounts()
|
|
|
|
result = (&User{}).
|
|
|
|
Preload().
|
|
|
|
Where("id IN ?", distinct).
|
|
|
|
Where(where, placeholders...).
|
|
|
|
Find(&matched)
|
|
|
|
)
|
|
|
|
|
|
|
|
if result.Error == nil {
|
|
|
|
for _, row := range matched {
|
|
|
|
usermap[row.ID] = true
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return usermap
|
|
|
|
}
|
|
|
|
|
|
|
|
// Get a user from the ShyMap.
|
|
|
|
func (um ShyMap) Get(id uint64) bool {
|
|
|
|
return um[id]
|
|
|
|
}
|