0.1.2 #9

Merged
Thilawyn merged 8 commits from next into master 2024-01-27 23:40:19 +01:00
2 changed files with 82 additions and 2 deletions
Showing only changes of commit 69ecd95cbb - Show all commits

View File

@@ -21,7 +21,7 @@ export type Trait<
"@thilawyn/thilatrait/Trait" "@thilawyn/thilatrait/Trait"
> >
export type TraitApplierTag = "@thilawyn/thilatrait/Trait" export type TraitApplierTag = "@thilawyn/thilatrait/Parent"
/** /**
* Represents the function signature for applying a trait to a parent class. * Represents the function signature for applying a trait to a parent class.
@@ -154,6 +154,30 @@ export function extendsAndExpresses<
extend: C, extend: C,
...traits: Traits ...traits: Traits
) { ) {
// Combine all static members of the traits
type AllStaticMembers = UnionToIntersection<TraitClass<Traits[number]>>
// Combine all instance members of the traits
type AllInstanceMembers = UnionToIntersection<TraitInstance<Traits[number]>>
// Extract common keys from all traits
type CommonKeys = keyof AllStaticMembers & keyof AllInstanceMembers
// Exclude common keys from the static members of the last trait
type StaticMembersWithoutCommon = Omit<AllStaticMembers, CommonKeys>
// Exclude common keys from the instance members of the last trait
type InstanceMembersWithoutCommon = Omit<AllInstanceMembers, CommonKeys>
// Combine the instance members of the base class and the last trait
type CombinedInstanceMembers = InstanceType<C> & InstanceMembersWithoutCommon
// Combine the static members of the base class and the last trait
type CombinedStaticMembers = StaticMembers<C> & StaticMembersWithoutCommon
// Combine the instance and static members
type CombinedMembers = CombinedInstanceMembers & CombinedStaticMembers
return traits.reduce( return traits.reduce(
(previous, trait) => trait(previous), (previous, trait) => trait(previous),
extend as Opaque<C, TraitApplierTag>, extend as Opaque<C, TraitApplierTag>,

View File

@@ -1,4 +1,5 @@
import { expresses, extendsAndExpresses, trait } from "." import { AbstractClass, Class, Simplify } from "type-fest"
import { TraitInstance, expresses, extendsAndExpresses, trait } from "."
const Identifiable = <ID>() => const Identifiable = <ID>() =>
@@ -68,3 +69,58 @@ class User extends UserProto {
const user1 = new User(1n) const user1 = new User(1n)
console.log(user1) console.log(user1)
console.log(user1.equals(user1)) console.log(user1.equals(user1))
abstract class TestTrait1 {
abstract variable: number
abstract member: {
issou: string
}
}
abstract class TestTrait2 {
abstract lol: BigInt
abstract member: {
issou: "gneugneu",
adolf: string
}
}
type StaticMembers<C> = {
[Key in keyof C as Key extends "prototype" ? never : Key]: C[Key]
}
type CommonKeys<A, B> = Extract<keyof A, keyof B>
type Extend2<Self, Parent> = (
Pick<Self, CommonKeys<Self, Parent>> extends Pick<Parent, CommonKeys<Self, Parent>>
? Omit<Parent, CommonKeys<Self, Parent>> & Self
: never
)
type ExtendN<Classes extends any[]> = (
Classes extends [infer Parent, infer Self, ...infer Rest]
? Extend2<Self, Parent> & ExtendN<Rest>
: Classes extends [infer Self, ...infer Others]
? Self
: "Empty array"
)
// type ExtendClass<
// Self extends AbstractClass<any>,
// Parent extends AbstractClass<any>,
// > = (
// )
type Test = Simplify<StaticMembers<typeof TestTrait2>>
type MixedStaticTestTraits = ExtendN<[
StaticMembers<typeof TestTrait2>,
StaticMembers<typeof TestTrait1>,
]>
type MixedTestTraitsProto = Class<
Extend2<TestTrait2, TestTrait1>,
any[]
> & Extend2<StaticMembers<typeof TestTrait2>, StaticMembers<typeof TestTrait1>>