Skip to content

Commit

Permalink
class-factory: Use symbols for unique property names (#270)
Browse files Browse the repository at this point in the history
  • Loading branch information
yotamN authored Apr 14, 2023
1 parent 09c77f4 commit 2731043
Showing 1 changed file with 199 additions and 30 deletions.
229 changes: 199 additions & 30 deletions lib/class-factory.js
Original file line number Diff line number Diff line change
Expand Up @@ -186,39 +186,94 @@ class ClassFactory {
_make (name, getClassHandle, env) {
const C = makeClassWrapperConstructor();
const proto = Object.create(Wrapper.prototype, {
$n: {
[Symbol.for('n')]: {
value: name
},
$C: {
$n: {
get () {
return this[Symbol.for('n')];
}
},
[Symbol.for('C')]: {
value: C
},
$w: {
$C: {
get () {
return this[Symbol.for('C')];
}
},
[Symbol.for('w')]: {
value: null,
writable: true
},
$_s: {
$w: {
get () {
return this[Symbol.for('w')];
},
set (val) {
this[Symbol.for('w')] = val;
}
},
[Symbol.for('_s')]: {
writable: true
},
$c: {
$_s: {
get () {
return this[Symbol.for('_s')];
},
set (val) {
this[Symbol.for('_s')] = val;
}
},
[Symbol.for('c')]: {
value: [null]
},
$m: {
$c: {
get () {
return this[Symbol.for('c')];
}
},
[Symbol.for('m')]: {
value: new Map()
},
$l: {
$m: {
get () {
return this[Symbol.for('m')];
}
},
[Symbol.for('l')]: {
value: null,
writable: true
},
$gch: {
$l: {
get () {
return this[Symbol.for('l')];
},
set (val) {
this[Symbol.for('l')] = val;
}
},
[Symbol.for('gch')]: {
value: getClassHandle
},
$f: {
$gch: {
get () {
return this[Symbol.for('gch')];
}
},
[Symbol.for('f')]: {
value: this
},
$f: {
get () {
return this[Symbol.for('f')];
}
}
});
C.prototype = proto;

const classWrapper = new C(null);
proto[Symbol.for('w')] = classWrapper;
proto.$w = classWrapper;

const h = classWrapper.$borrowClassHandle(env);
Expand Down Expand Up @@ -809,14 +864,20 @@ wrapperHandler = {
};

Object.defineProperties(Wrapper.prototype, {
$new: {
enumerable: true,
[Symbol.for('new')]: {
enumerable: false,
get () {
return this.$getCtor('allocAndInit');
}
},
$alloc: {
$new: {
enumerable: true,
get () {
return this[Symbol.for('new')];
}
},
[Symbol.for('alloc')]: {
enumerable: false,
value () {
const env = vm.getEnv();
const h = this.$borrowClassHandle(env);
Expand All @@ -829,14 +890,26 @@ Object.defineProperties(Wrapper.prototype, {
}
}
},
$init: {
$alloc: {
enumerable: true,
get () {
return this[Symbol.for('$alloc')];
}
},
[Symbol.for('init')]: {
enumerable: false,
get () {
return this.$getCtor('initOnly');
}
},
$dispose: {
$init: {
enumerable: true,
get () {
return this[Symbol.for('init')];
}
},
[Symbol.for('dispose')]: {
enumerable: false,
value () {
const ref = this.$r;
if (ref !== null) {
Expand All @@ -849,14 +922,26 @@ Object.defineProperties(Wrapper.prototype, {
}
}
},
$clone: {
$dispose: {
enumerable: true,
get () {
return this[Symbol.for('dispose')];
}
},
[Symbol.for('clone')]: {
enumerable: false,
value (env) {
const C = this.$C;
return new C(this.$h, this.$t, env);
}
},
class: {
enumerable: true,
$clone: {
value (env) {
return this[Symbol.for('clone')](env);
}
},
[Symbol.for('class')]: {
enumerable: false,
get () {
const env = vm.getEnv();
const h = this.$borrowClassHandle(env);
Expand All @@ -868,8 +953,14 @@ Object.defineProperties(Wrapper.prototype, {
}
}
},
$className: {
class: {
enumerable: true,
get () {
return this[Symbol.for('class')];
}
},
[Symbol.for('className')]: {
enumerable: false,
get () {
const handle = this.$h;
if (handle === null) {
Expand All @@ -879,22 +970,41 @@ Object.defineProperties(Wrapper.prototype, {
return vm.getEnv().getObjectClassName(handle);
}
},
$ownMembers: {
$className: {
enumerable: true,
get () {
return this[Symbol.for('className')];
}
},
[Symbol.for('ownMembers')]: {
enumerable: false,
get () {
const model = this.$l;
return model.list();
}
},
$super: {
$ownMembers: {
enumerable: true,
get () {
return this[Symbol.for('ownMembers')];
}
},
[Symbol.for('super')]: {
enumerable: false,
get () {
const env = vm.getEnv();
const C = this.$s.$C;
return new C(this.$h, STRATEGY_DIRECT, env);
}
},
$s: {
$super: {
enumerable: true,
get () {
return this[Symbol.for('super')];
}
},
[Symbol.for('s')]: {
enumerable: false,
get () {
const proto = Object.getPrototypeOf(this);

Expand Down Expand Up @@ -934,13 +1044,25 @@ Object.defineProperties(Wrapper.prototype, {
return superWrapper;
}
},
$isSameObject: {
$s: {
get () {
return this[Symbol.for('s')];
}
},
[Symbol.for('isSameObject')]: {
enumerable: false,
value (obj) {
const env = vm.getEnv();
return env.isSameObject(obj.$h, this.$h);
}
},
$getCtor: {
$isSameObject: {
value (obj) {
return this[Symbol.for('isSameObject')](obj);
}
},
[Symbol.for('getCtor')]: {
enumerable: false,
value (type) {
const slot = this.$c;

Expand All @@ -959,7 +1081,13 @@ Object.defineProperties(Wrapper.prototype, {
return ctor[type];
}
},
$borrowClassHandle: {
$getCtor: {
value (type) {
return this[Symbol.for('getCtor')](type);
}
},
[Symbol.for('borrowClassHandle')]: {
enumerable: false,
value (env) {
const className = this.$n;
const classHandles = this.$f._classHandles;
Expand All @@ -973,7 +1101,13 @@ Object.defineProperties(Wrapper.prototype, {
return handle.ref();
}
},
$copyClassHandle: {
$borrowClassHandle: {
value (env) {
return this[Symbol.for('borrowClassHandle')](env);
}
},
[Symbol.for('copyClassHandle')]: {
enumerable: false,
value (env) {
const h = this.$borrowClassHandle(env);
try {
Expand All @@ -983,7 +1117,13 @@ Object.defineProperties(Wrapper.prototype, {
}
}
},
$getHandle: {
$copyClassHandle: {
value (env) {
return this[Symbol.for('copyClassHandle')](env);
}
},
[Symbol.for('getHandle')]: {
enumerable: false,
value (env) {
const handle = this.$h;

Expand All @@ -996,7 +1136,13 @@ Object.defineProperties(Wrapper.prototype, {
return handle;
}
},
$list: {
$getHandle: {
value (env) {
return this[Symbol.for('getHandle')](env);
}
},
[Symbol.for('list')]: {
enumerable: false,
value () {
const superWrapper = this.$s;
const superMembers = (superWrapper !== null) ? superWrapper.$list() : [];
Expand All @@ -1005,7 +1151,13 @@ Object.defineProperties(Wrapper.prototype, {
return Array.from(new Set(superMembers.concat(model.list())));
}
},
$has: {
$list: {
get () {
return this[Symbol.for('list')];
}
},
[Symbol.for('has')]: {
enumerable: false,
value (member) {
const members = this.$m;
if (members.has(member)) {
Expand All @@ -1025,7 +1177,13 @@ Object.defineProperties(Wrapper.prototype, {
return false;
}
},
$find: {
$has: {
value (member) {
return this[Symbol.for('has')](member);
}
},
[Symbol.for('find')]: {
enumerable: false,
value (member) {
const members = this.$m;

Expand Down Expand Up @@ -1056,7 +1214,13 @@ Object.defineProperties(Wrapper.prototype, {
return null;
}
},
toJSON: {
$find: {
value (member) {
return this[Symbol.for('find')](member);
}
},
[Symbol.for('toJSON')]: {
enumerable: false,
value () {
const wrapperName = this.$n;

Expand All @@ -1072,6 +1236,11 @@ Object.defineProperties(Wrapper.prototype, {

return `<instance: ${wrapperName}, $className: ${actualName}>`;
}
},
toJSON: {
get () {
return this[Symbol.for('toJSON')];
}
}
});

Expand Down

0 comments on commit 2731043

Please sign in to comment.