Skip to content

Commit

Permalink
Temporarily disable 'context.access'
Browse files Browse the repository at this point in the history
  • Loading branch information
rbuckton committed Jan 18, 2023
1 parent 02e93fd commit 831a5b2
Show file tree
Hide file tree
Showing 100 changed files with 628 additions and 605 deletions.
205 changes: 152 additions & 53 deletions src/compiler/factory/emitHelpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ import {
isComputedPropertyName,
isIdentifier,
memoize,
ObjectLiteralElementLike,
PrivateIdentifier,
ScriptTarget,
setEmitFlags,
Expand Down Expand Up @@ -251,65 +250,165 @@ export function createEmitHelperFactory(context: TransformationContext): EmitHel
]);
}

function createESDecorateClassElementAccessGetMethod(elementName: ESDecorateName) {
const accessor = elementName.computed ?
factory.createElementAccessExpression(factory.createThis(), elementName.name) :
factory.createPropertyAccessExpression(factory.createThis(), elementName.name);

return factory.createMethodDeclaration(
/*modifiers*/ undefined,
/*asteriskToken*/ undefined,
"get",
/*questionToken*/ undefined,
/*typeParameters*/ undefined,
[],
/*type*/ undefined,
factory.createBlock([factory.createReturnStatement(accessor)])
);
}

function createESDecorateClassElementAccessSetMethod(elementName: ESDecorateName) {
const accessor = elementName.computed ?
factory.createElementAccessExpression(factory.createThis(), elementName.name) :
factory.createPropertyAccessExpression(factory.createThis(), elementName.name);

return factory.createMethodDeclaration(
/*modifiers*/ undefined,
/*asteriskToken*/ undefined,
"set",
/*questionToken*/ undefined,
/*typeParameters*/ undefined,
[factory.createParameterDeclaration(
/*modifiers*/ undefined,
/*dotDotDotToken*/ undefined,
factory.createIdentifier("value")
)],
/*type*/ undefined,
factory.createBlock([
factory.createExpressionStatement(
factory.createAssignment(
accessor,
factory.createIdentifier("value")
)
)
])
);
}

function createESDecorateClassElementAccessObject(name: ESDecorateName, access: ESDecorateClassElementAccess) {
const properties: ObjectLiteralElementLike[] = [];
if (access.get) properties.push(createESDecorateClassElementAccessGetMethod(name));
if (access.set) properties.push(createESDecorateClassElementAccessSetMethod(name));
return factory.createObjectLiteralExpression(properties);
}
// Per https://github.com/tc39/proposal-decorators/issues/494, we may need to change the emit for the `access` object
// so that it does not need to be used via `.call`. The following two sections represent the options presented in
// tc39/proposal-decorators#494
//
// === Current approach (`access.get.call(obj)`, `access.set.call(obj, value)`) ===
//
// function createESDecorateClassElementAccessGetMethod(elementName: ESDecorateName) {
// const accessor = elementName.computed ?
// factory.createElementAccessExpression(factory.createThis(), elementName.name) :
// factory.createPropertyAccessExpression(factory.createThis(), elementName.name);
//
// return factory.createMethodDeclaration(
// /*modifiers*/ undefined,
// /*asteriskToken*/ undefined,
// "get",
// /*questionToken*/ undefined,
// /*typeParameters*/ undefined,
// [],
// /*type*/ undefined,
// factory.createBlock([factory.createReturnStatement(accessor)])
// );
// }
//
// function createESDecorateClassElementAccessSetMethod(elementName: ESDecorateName) {
// const accessor = elementName.computed ?
// factory.createElementAccessExpression(factory.createThis(), elementName.name) :
// factory.createPropertyAccessExpression(factory.createThis(), elementName.name);
//
// return factory.createMethodDeclaration(
// /*modifiers*/ undefined,
// /*asteriskToken*/ undefined,
// "set",
// /*questionToken*/ undefined,
// /*typeParameters*/ undefined,
// [factory.createParameterDeclaration(
// /*modifiers*/ undefined,
// /*dotDotDotToken*/ undefined,
// factory.createIdentifier("value")
// )],
// /*type*/ undefined,
// factory.createBlock([
// factory.createExpressionStatement(
// factory.createAssignment(
// accessor,
// factory.createIdentifier("value")
// )
// )
// ])
// );
// }
//
// function createESDecorateClassElementAccessObject(name: ESDecorateName, access: ESDecorateClassElementAccess) {
// const properties: ObjectLiteralElementLike[] = [];
// if (access.get) properties.push(createESDecorateClassElementAccessGetMethod(name));
// if (access.set) properties.push(createESDecorateClassElementAccessSetMethod(name));
// return factory.createObjectLiteralExpression(properties);
// }
//
// === Suggested approach (`access.get(obj)`, `access.set(obj, value)`, `access.has(obj)`) ===
//
// function createESDecorateClassElementAccessGetMethod(elementName: ESDecorateName) {
// const accessor = elementName.computed ?
// factory.createElementAccessExpression(factory.createIdentifier("obj"), elementName.name) :
// factory.createPropertyAccessExpression(factory.createIdentifier("obj"), elementName.name);
//
// return factory.createMethodDeclaration(
// /*modifiers*/ undefined,
// /*asteriskToken*/ undefined,
// "get",
// /*questionToken*/ undefined,
// /*typeParameters*/ undefined,
// [factory.createParameterDeclaration(
// /*modifiers*/ undefined,
// /*dotDotDotToken*/ undefined,
// factory.createIdentifier("obj")
// )],
// /*type*/ undefined,
// factory.createBlock([factory.createReturnStatement(accessor)])
// );
// }
//
// function createESDecorateClassElementAccessSetMethod(elementName: ESDecorateName) {
// const accessor = elementName.computed ?
// factory.createElementAccessExpression(factory.createIdentifier("obj"), elementName.name) :
// factory.createPropertyAccessExpression(factory.createIdentifier("obj"), elementName.name);
//
// return factory.createMethodDeclaration(
// /*modifiers*/ undefined,
// /*asteriskToken*/ undefined,
// "set",
// /*questionToken*/ undefined,
// /*typeParameters*/ undefined,
// [factory.createParameterDeclaration(
// /*modifiers*/ undefined,
// /*dotDotDotToken*/ undefined,
// factory.createIdentifier("obj")
// ),
// factory.createParameterDeclaration(
// /*modifiers*/ undefined,
// /*dotDotDotToken*/ undefined,
// factory.createIdentifier("value")
// )],
// /*type*/ undefined,
// factory.createBlock([
// factory.createExpressionStatement(
// factory.createAssignment(
// accessor,
// factory.createIdentifier("value")
// )
// )
// ])
// );
// }
//
// function createESDecorateClassElementAccessHasMethod(elementName: ESDecorateName) {
// const propertyName =
// elementName.computed ? elementName.name :
// isIdentifier(elementName.name) ? factory.createStringLiteralFromNode(elementName.name) :
// elementName.name;
//
// return factory.createMethodDeclaration(
// /*modifiers*/ undefined,
// /*asteriskToken*/ undefined,
// "has",
// /*questionToken*/ undefined,
// /*typeParameters*/ undefined,
// [factory.createParameterDeclaration(
// /*modifiers*/ undefined,
// /*dotDotDotToken*/ undefined,
// factory.createIdentifier("obj")
// )],
// /*type*/ undefined,
// factory.createBlock([factory.createReturnStatement(
// factory.createBinaryExpression(
// propertyName,
// SyntaxKind.InKeyword,
// factory.createIdentifier("obj")
// )
// )])
// );
// }
//
// function createESDecorateClassElementAccessObject(name: ESDecorateName, access: ESDecorateClassElementAccess) {
// const properties: ObjectLiteralElementLike[] = [];
// if (access.get) properties.push(createESDecorateClassElementAccessGetMethod(name));
// if (access.set) properties.push(createESDecorateClassElementAccessSetMethod(name));
// property.push(createESDecorateClassElementAccessHasMethod(name));
// return factory.createObjectLiteralExpression(properties);
// }

function createESDecorateClassElementContextObject(contextIn: ESDecorateClassElementContext) {
return factory.createObjectLiteralExpression([
factory.createPropertyAssignment(factory.createIdentifier("kind"), factory.createStringLiteral(contextIn.kind)),
factory.createPropertyAssignment(factory.createIdentifier("name"), contextIn.name.computed ? contextIn.name.name : factory.createStringLiteralFromNode(contextIn.name.name)),
factory.createPropertyAssignment(factory.createIdentifier("static"), contextIn.static ? factory.createTrue() : factory.createFalse()),
factory.createPropertyAssignment(factory.createIdentifier("private"), contextIn.private ? factory.createTrue() : factory.createFalse()),
factory.createPropertyAssignment(factory.createIdentifier("access"), createESDecorateClassElementAccessObject(contextIn.name, contextIn.access))

// Disabled, pending resolution of https://github.com/tc39/proposal-decorators/issues/494
// factory.createPropertyAssignment(factory.createIdentifier("access"), createESDecorateClassElementAccessObject(contextIn.name, contextIn.access))
]);
}

Expand Down
123 changes: 64 additions & 59 deletions src/lib/decorators.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -72,16 +72,17 @@ interface ClassMethodDecoratorContext<
/** A value indicating whether the class member has a private name. */
readonly private: boolean;

/** An object that can be used to access the current value of the class member at runtime. */
readonly access: {
/**
* Gets the current value of the method from the provided receiver.
*
* @example
* let fn = context.access.get.call(instance);
*/
get(this: This): Value;
};
// NOTE: Disabled, pending the outcome of https://github.com/tc39/proposal-decorators/issues/494
// /** An object that can be used to access the current value of the class member at runtime. */
// readonly access: {
// /**
// * Gets the current value of the method from the provided receiver.
// *
// * @example
// * let fn = context.access.get.call(instance);
// */
// get(this: This): Value;
// };

/**
* Adds a callback to be invoked either before static initializers are run (when
Expand Down Expand Up @@ -132,16 +133,17 @@ interface ClassGetterDecoratorContext<
/** A value indicating whether the class member has a private name. */
readonly private: boolean;

/** An object that can be used to access the current value of the class member at runtime. */
readonly access: {
/**
* Invokes the getter on the provided receiver.
*
* @example
* let value = context.access.get.call(instance);
*/
get(this: This): Value;
};
// NOTE: Disabled, pending the outcome of https://github.com/tc39/proposal-decorators/issues/494
// /** An object that can be used to access the current value of the class member at runtime. */
// readonly access: {
// /**
// * Invokes the getter on the provided receiver.
// *
// * @example
// * let value = context.access.get.call(instance);
// */
// get(this: This): Value;
// };

/**
* Adds a callback to be invoked either before static initializers are run (when
Expand Down Expand Up @@ -173,16 +175,17 @@ interface ClassSetterDecoratorContext<
/** A value indicating whether the class member has a private name. */
readonly private: boolean;

// NOTE: Disabled, pending the outcome of https://github.com/tc39/proposal-decorators/issues/494
/** An object that can be used to access the current value of the class member at runtime. */
readonly access: {
/**
* Invokes the setter on the provided receiver.
*
* @example
* context.access.set.call(instance, value);
*/
set(this: This, value: Value): void;
};
// readonly access: {
// /**
// * Invokes the setter on the provided receiver.
// *
// * @example
// * context.access.set.call(instance, value);
// */
// set(this: This, value: Value): void;
// };

/**
* Adds a callback to be invoked either before static initializers are run (when
Expand Down Expand Up @@ -214,24 +217,25 @@ interface ClassAccessorDecoratorContext<
/** A value indicating whether the class member has a private name. */
readonly private: boolean;

/** An object that can be used to access the current value of the class member at runtime. */
readonly access: {
/**
* Invokes the getter on the provided receiver.
*
* @example
* let value = context.access.get.call(instance);
*/
get(this: This): Value;

/**
* Invokes the setter on the provided receiver.
*
* @example
* context.access.set.call(instance, value);
*/
set(this: This, value: Value): void;
};
// NOTE: Disabled, pending the outcome of https://github.com/tc39/proposal-decorators/issues/494
// /** An object that can be used to access the current value of the class member at runtime. */
// readonly access: {
// /**
// * Invokes the getter on the provided receiver.
// *
// * @example
// * let value = context.access.get.call(instance);
// */
// get(this: This): Value;

// /**
// * Invokes the setter on the provided receiver.
// *
// * @example
// * context.access.set.call(instance, value);
// */
// set(this: This, value: Value): void;
// };

/**
* Adds a callback to be invoked either before static initializers are run (when
Expand Down Expand Up @@ -310,18 +314,19 @@ interface ClassFieldDecoratorContext<
/** A value indicating whether the class member has a private name. */
readonly private: boolean;

/** An object that can be used to access the current value of the class member at runtime. */
readonly access: {
/**
* Gets the value of the field on the provided receiver.
*/
get(this: This): Value;

/**
* Sets the value of the field on the provided receiver.
*/
set(this: This, value: Value): void;
};
// NOTE: Disabled, pending the outcome of https://github.com/tc39/proposal-decorators/issues/494
// /** An object that can be used to access the current value of the class member at runtime. */
// readonly access: {
// /**
// * Gets the value of the field on the provided receiver.
// */
// get(this: This): Value;

// /**
// * Sets the value of the field on the provided receiver.
// */
// set(this: This, value: Value): void;
// };

/**
* Adds a callback to be invoked either before static initializers are run (when
Expand Down
Loading

0 comments on commit 831a5b2

Please sign in to comment.