IceCubesApp/Packages/Models/Sources/Models/Account.swift

190 lines
6.4 KiB
Swift
Raw Normal View History

import Foundation
public final class Account: Codable, Identifiable, Hashable, Sendable, Equatable {
public static func == (lhs: Account, rhs: Account) -> Bool {
lhs.id == rhs.id &&
2023-02-22 18:09:39 +00:00
lhs.username == rhs.username &&
lhs.note.asRawText == rhs.note.asRawText &&
lhs.statusesCount == rhs.statusesCount &&
lhs.followersCount == rhs.followersCount &&
lhs.followingCount == rhs.followingCount &&
lhs.acct == rhs.acct &&
lhs.displayName == rhs.displayName &&
lhs.fields == rhs.fields &&
lhs.lastStatusAt == rhs.lastStatusAt &&
lhs.discoverable == rhs.discoverable &&
2023-02-24 06:55:24 +00:00
lhs.bot == rhs.bot &&
2024-01-02 20:16:27 +00:00
lhs.locked == rhs.locked &&
lhs.avatar == rhs.avatar &&
lhs.header == rhs.header
}
2023-02-18 06:26:48 +00:00
2022-12-17 12:37:46 +00:00
public func hash(into hasher: inout Hasher) {
hasher.combine(id)
}
2023-01-17 10:36:01 +00:00
public struct Field: Codable, Equatable, Identifiable, Sendable {
2022-12-21 19:53:23 +00:00
public var id: String {
value.asRawText + name
2022-12-21 19:53:23 +00:00
}
2023-01-17 10:36:01 +00:00
2022-12-17 12:37:46 +00:00
public let name: String
2022-12-21 19:53:23 +00:00
public let value: HTMLString
2022-12-17 12:37:46 +00:00
public let verifiedAt: String?
}
2023-01-17 10:36:01 +00:00
public struct Source: Codable, Equatable, Sendable {
2023-01-10 07:24:05 +00:00
public let privacy: Visibility
public let sensitive: Bool
public let language: String?
public let note: String
public let fields: [Field]
}
2023-01-17 10:36:01 +00:00
public let id: String
public let username: String
2023-03-02 19:15:07 +00:00
public let displayName: String?
2024-01-24 15:22:44 +00:00
public let cachedDisplayName: HTMLString
public let avatar: URL
2022-12-17 12:37:46 +00:00
public let header: URL
2022-11-21 13:42:59 +00:00
public let acct: String
2022-12-17 12:37:46 +00:00
public let note: HTMLString
public let createdAt: ServerDate
2023-07-04 06:37:30 +00:00
public let followersCount: Int?
public let followingCount: Int?
public let statusesCount: Int?
2022-12-17 12:37:46 +00:00
public let lastStatusAt: String?
public let fields: [Field]
public let locked: Bool
2022-12-21 16:39:48 +00:00
public let emojis: [Emoji]
2023-01-04 17:37:58 +00:00
public let url: URL?
2023-01-10 07:24:05 +00:00
public let source: Source?
public let bot: Bool
public let discoverable: Bool?
public let moved: Account?
2023-01-17 10:36:01 +00:00
public var haveAvatar: Bool {
2023-09-16 12:15:03 +00:00
avatar.lastPathComponent != "missing.png"
}
public var haveHeader: Bool {
2023-09-16 12:15:03 +00:00
header.lastPathComponent != "missing.png"
}
public init(id: String, username: String, displayName: String?, avatar: URL, header: URL, acct: String, note: HTMLString, createdAt: ServerDate, followersCount: Int, followingCount: Int, statusesCount: Int, lastStatusAt: String? = nil, fields: [Account.Field], locked: Bool, emojis: [Emoji], url: URL? = nil, source: Account.Source? = nil, bot: Bool, discoverable: Bool? = nil, moved: Account? = nil) {
self.id = id
self.username = username
self.displayName = displayName
self.avatar = avatar
self.header = header
self.acct = acct
self.note = note
self.createdAt = createdAt
self.followersCount = followersCount
self.followingCount = followingCount
self.statusesCount = statusesCount
self.lastStatusAt = lastStatusAt
self.fields = fields
self.locked = locked
self.emojis = emojis
self.url = url
self.source = source
self.bot = bot
self.discoverable = discoverable
self.moved = moved
2024-02-14 11:48:14 +00:00
2024-01-24 15:22:44 +00:00
if let displayName, !displayName.isEmpty {
2024-02-14 11:48:14 +00:00
cachedDisplayName = .init(stringValue: displayName)
2024-01-24 15:22:44 +00:00
} else {
2024-02-14 11:48:14 +00:00
cachedDisplayName = .init(stringValue: "@\(username)")
2024-01-24 15:22:44 +00:00
}
}
2024-02-14 11:48:14 +00:00
2024-01-24 15:22:44 +00:00
public enum CodingKeys: CodingKey {
case id
case username
case displayName
case avatar
case header
case acct
case note
case createdAt
case followersCount
case followingCount
case statusesCount
case lastStatusAt
case fields
case locked
case emojis
case url
case source
case bot
case discoverable
case moved
2024-01-24 15:22:44 +00:00
}
2024-02-14 11:48:14 +00:00
2024-01-24 15:22:44 +00:00
public init(from decoder: Decoder) throws {
let container = try decoder.container(keyedBy: CodingKeys.self)
2024-02-14 11:48:14 +00:00
id = try container.decode(String.self, forKey: .id)
username = try container.decode(String.self, forKey: .username)
displayName = try container.decodeIfPresent(String.self, forKey: .displayName)
avatar = try container.decode(URL.self, forKey: .avatar)
header = try container.decode(URL.self, forKey: .header)
acct = try container.decode(String.self, forKey: .acct)
note = try container.decode(HTMLString.self, forKey: .note)
createdAt = try container.decode(ServerDate.self, forKey: .createdAt)
followersCount = try container.decodeIfPresent(Int.self, forKey: .followersCount)
followingCount = try container.decodeIfPresent(Int.self, forKey: .followingCount)
statusesCount = try container.decodeIfPresent(Int.self, forKey: .statusesCount)
lastStatusAt = try container.decodeIfPresent(String.self, forKey: .lastStatusAt)
fields = try container.decode([Account.Field].self, forKey: .fields)
locked = try container.decode(Bool.self, forKey: .locked)
emojis = try container.decode([Emoji].self, forKey: .emojis)
url = try container.decodeIfPresent(URL.self, forKey: .url)
source = try container.decodeIfPresent(Account.Source.self, forKey: .source)
bot = try container.decode(Bool.self, forKey: .bot)
discoverable = try container.decodeIfPresent(Bool.self, forKey: .discoverable)
moved = try container.decodeIfPresent(Account.self, forKey: .moved)
2024-01-24 15:22:44 +00:00
if let displayName, !displayName.isEmpty {
2024-02-14 11:48:14 +00:00
cachedDisplayName = .init(stringValue: displayName)
2024-01-24 15:22:44 +00:00
} else {
2024-02-14 11:48:14 +00:00
cachedDisplayName = .init(stringValue: "@\(username)")
2024-01-24 15:22:44 +00:00
}
}
2023-02-18 06:26:48 +00:00
2022-12-17 12:37:46 +00:00
public static func placeholder() -> Account {
.init(id: UUID().uuidString,
username: "Username",
displayName: "John Mastodon",
2022-12-17 12:37:46 +00:00
avatar: URL(string: "https://files.mastodon.social/media_attachments/files/003/134/405/original/04060b07ddf7bb0b.png")!,
header: URL(string: "https://files.mastodon.social/media_attachments/files/003/134/405/original/04060b07ddf7bb0b.png")!,
acct: "johnm@example.com",
note: .init(stringValue: "Some content"),
2023-02-09 08:12:44 +00:00
createdAt: ServerDate(),
2022-12-17 12:37:46 +00:00
followersCount: 10,
followingCount: 10,
statusesCount: 10,
lastStatusAt: nil,
fields: [],
2022-12-21 16:39:48 +00:00
locked: false,
2023-01-04 17:37:58 +00:00
emojis: [],
2023-01-10 07:24:05 +00:00
url: nil,
source: nil,
bot: false,
discoverable: true)
2022-12-17 12:37:46 +00:00
}
2023-01-17 10:36:01 +00:00
2022-12-23 17:47:19 +00:00
public static func placeholders() -> [Account] {
[.placeholder(), .placeholder(), .placeholder(), .placeholder(), .placeholder(),
.placeholder(), .placeholder(), .placeholder(), .placeholder(), .placeholder()]
}
}
public struct FamiliarAccounts: Decodable {
public let id: String
public let accounts: [Account]
}
extension FamiliarAccounts: Sendable {}