feat(model): ✨ add service
model
This commit is contained in:
parent
f7f3b48ad1
commit
2ca1ceda60
122
src/models/src/service.ts
Normal file
122
src/models/src/service.ts
Normal file
|
@ -0,0 +1,122 @@
|
|||
import { ToJson } from '@/types.ts'
|
||||
import { Group } from '@models/group.ts'
|
||||
import { Ressource } from '@models/ressource.ts'
|
||||
import { Ref } from '@/src/models/utils/ref.ts'
|
||||
|
||||
export class Service extends Ressource {
|
||||
static fromJSON(
|
||||
{ groups, url, avatar, ...json }: ToJson<Service>,
|
||||
): Service {
|
||||
return new Service({
|
||||
groups: groups.map((group) => Ref.fromString<Group>(group)),
|
||||
url: new URL(url),
|
||||
avatar: new URL(avatar),
|
||||
...json,
|
||||
})
|
||||
}
|
||||
|
||||
static create(
|
||||
{ category, url, groups, avatar, name }: Pick<
|
||||
Service,
|
||||
'category' | 'url' | 'groups' | 'avatar' | 'name'
|
||||
>,
|
||||
): Service {
|
||||
const { uuid, createdAt, updatedAt } = super.create({ name })
|
||||
return new Service({
|
||||
uuid,
|
||||
createdAt,
|
||||
updatedAt,
|
||||
name,
|
||||
category,
|
||||
url,
|
||||
groups,
|
||||
avatar,
|
||||
})
|
||||
}
|
||||
|
||||
#category: 'bin' | 'web' | 'fs' | 'git'
|
||||
#url: URL
|
||||
#groups: readonly Ref<Group>[]
|
||||
#avatar: URL
|
||||
|
||||
private constructor({
|
||||
category,
|
||||
url,
|
||||
groups,
|
||||
avatar,
|
||||
...ressource
|
||||
}: Pick<
|
||||
Service,
|
||||
| 'uuid'
|
||||
| 'createdAt'
|
||||
| 'updatedAt'
|
||||
| 'name'
|
||||
| 'category'
|
||||
| 'url'
|
||||
| 'groups'
|
||||
| 'avatar'
|
||||
>) {
|
||||
super(ressource)
|
||||
|
||||
if (!['bin', 'web', 'fs', 'git'].includes(category)) {
|
||||
throw new TypeError(
|
||||
`category is "${category}" but ('bin' | 'web' | 'fs' | 'git') is required`,
|
||||
)
|
||||
}
|
||||
this.#category = category
|
||||
this.#url = url
|
||||
this.#groups = Object.freeze(groups)
|
||||
this.#avatar = avatar
|
||||
}
|
||||
|
||||
get type(): 'service' {
|
||||
return 'service'
|
||||
}
|
||||
|
||||
get category() {
|
||||
return this.#category
|
||||
}
|
||||
|
||||
get url() {
|
||||
return new URL(this.#url)
|
||||
}
|
||||
|
||||
get groups() {
|
||||
return Object.freeze(this.#groups)
|
||||
}
|
||||
|
||||
get avatar() {
|
||||
return new URL(this.#avatar)
|
||||
}
|
||||
|
||||
update(
|
||||
props: Partial<Omit<Service, 'type' | 'uuid' | 'createdAt'>>,
|
||||
): Service {
|
||||
const { updatedAt } = super.update(props)
|
||||
const service = new Service({ ...this, ...props, updatedAt })
|
||||
return service
|
||||
}
|
||||
|
||||
toJSON() {
|
||||
return {
|
||||
...super.toJSON(),
|
||||
type: this.type,
|
||||
category: this.category,
|
||||
url: this.url.toJSON(),
|
||||
groups: this.groups.map((group) => group.toJSON()),
|
||||
avatar: this.avatar.toJSON(),
|
||||
} as const
|
||||
}
|
||||
|
||||
toString(): string {
|
||||
return `Service (${JSON.stringify(this)})`
|
||||
}
|
||||
}
|
||||
|
||||
export interface Service extends Ressource {
|
||||
type: 'service'
|
||||
category: 'bin' | 'web' | 'fs' | 'git'
|
||||
url: URL
|
||||
groups: readonly Ref<Group>[]
|
||||
avatar: URL
|
||||
}
|
Loading…
Reference in a new issue