@@ -33,42 +33,45 @@ declare global {
3333/**
3434 * Converts property values to and from attribute values.
3535 */
36- export interface ComplexAttributeConverter < Type = any , TypeHint = any > {
36+ export interface ComplexAttributeConverter < Type = unknown , TypeHint = unknown > {
3737 /**
3838 * Function called to convert an attribute value to a property
3939 * value.
4040 */
41- fromAttribute ?( value : string , type ?: TypeHint ) : Type ;
41+ fromAttribute ?( value : string | null , type ?: TypeHint ) : Type ;
4242
4343 /**
4444 * Function called to convert a property value to an attribute
4545 * value.
46+ *
47+ * It returns unknown instead of string, to be compatible with
48+ * https://github.com/WICG/trusted-types (and similar efforts).
4649 */
47- toAttribute ?( value : Type , type ?: TypeHint ) : string | null ;
50+ toAttribute ?( value : Type , type ?: TypeHint ) : unknown ;
4851}
4952
50- type AttributeConverter < Type = any , TypeHint = any > =
53+ type AttributeConverter < Type = unknown , TypeHint = unknown > =
5154 ComplexAttributeConverter < Type > | ( ( value : string , type ?: TypeHint ) => Type ) ;
5255
5356/**
5457 * Defines options for a property accessor.
5558 */
56- export interface PropertyDeclaration < Type = any , TypeHint = any > {
59+ export interface PropertyDeclaration < Type = unknown , TypeHint = unknown > {
5760 /**
5861 * Indicates how and whether the property becomes an observed attribute.
5962 * If the value is `false`, the property is not added to `observedAttributes`.
6063 * If true or absent, the lowercased property name is observed (e.g. `fooBar`
6164 * becomes `foobar`). If a string, the string value is observed (e.g
6265 * `attribute: 'foo-bar'`).
6366 */
64- attribute ?: boolean | string ;
67+ readonly attribute ?: boolean | string ;
6568
6669 /**
6770 * Indicates the type of the property. This is used only as a hint for the
6871 * `converter` to determine how to convert the attribute
6972 * to/from a property.
7073 */
71- type ?: TypeHint ;
74+ readonly type ?: TypeHint ;
7275
7376 /**
7477 * Indicates how to convert the attribute to/from a property. If this value
@@ -82,7 +85,7 @@ export interface PropertyDeclaration<Type = any, TypeHint = any> {
8285 * the property is never updated again as a result of the attribute changing,
8386 * and vice versa.
8487 */
85- converter ?: AttributeConverter < Type , TypeHint > ;
88+ readonly converter ?: AttributeConverter < Type , TypeHint > ;
8689
8790 /**
8891 * Indicates if the property should reflect to an attribute.
@@ -91,7 +94,7 @@ export interface PropertyDeclaration<Type = any, TypeHint = any> {
9194 * property option and the value of the property converted using the rules
9295 * from the `converter` property option.
9396 */
94- reflect ?: boolean ;
97+ readonly reflect ?: boolean ;
9598
9699 /**
97100 * A function that indicates if a property should be considered changed when
@@ -108,7 +111,7 @@ export interface PropertyDeclaration<Type = any, TypeHint = any> {
108111 * `this.requestUpdate(propertyName, oldValue)` to request an update when
109112 * the property changes.
110113 */
111- noAccessor ?: boolean ;
114+ readonly noAccessor ?: boolean ;
112115}
113116
114117/**
@@ -117,7 +120,7 @@ export interface PropertyDeclaration<Type = any, TypeHint = any> {
117120 * PropertyDeclaration options.
118121 */
119122export interface PropertyDeclarations {
120- [ key : string ] : PropertyDeclaration ;
123+ readonly [ key : string ] : PropertyDeclaration ;
121124}
122125
123126type PropertyDeclarationMap = Map < PropertyKey , PropertyDeclaration > ;
@@ -128,7 +131,7 @@ export type PropertyValues = Map<PropertyKey, unknown>;
128131
129132export const defaultConverter : ComplexAttributeConverter = {
130133
131- toAttribute ( value : any , type ?: any ) {
134+ toAttribute ( value : unknown , type ?: unknown ) : unknown {
132135 switch ( type ) {
133136 case Boolean :
134137 return value ? '' : null ;
@@ -141,15 +144,15 @@ export const defaultConverter: ComplexAttributeConverter = {
141144 return value ;
142145 } ,
143146
144- fromAttribute ( value : any , type ?: any ) {
147+ fromAttribute ( value : string | null , type ?: unknown ) {
145148 switch ( type ) {
146149 case Boolean :
147150 return value !== null ;
148151 case Number :
149152 return value === null ? null : Number ( value ) ;
150153 case Object :
151154 case Array :
152- return JSON . parse ( value ) ;
155+ return JSON . parse ( value ! ) ;
153156 }
154157 return value ;
155158 }
@@ -256,10 +259,12 @@ export abstract class UpdatingElement extends HTMLElement {
256259 JSCompiler_renameProperty ( '_classProperties' , this ) ) ) {
257260 this . _classProperties = new Map ( ) ;
258261 // NOTE: Workaround IE11 not supporting Map constructor argument.
259- const superProperties = Object . getPrototypeOf ( this ) . _classProperties ;
262+ const superProperties : PropertyDeclarationMap =
263+ Object . getPrototypeOf ( this ) . _classProperties ;
260264 if ( superProperties !== undefined ) {
261265 superProperties . forEach (
262- ( v : any , k : PropertyKey ) => this . _classProperties ! . set ( k , v ) ) ;
266+ ( v : PropertyDeclaration , k : PropertyKey ) =>
267+ this . _classProperties ! . set ( k , v ) ) ;
263268 }
264269 }
265270 }
@@ -289,11 +294,15 @@ export abstract class UpdatingElement extends HTMLElement {
289294 }
290295 const key = typeof name === 'symbol' ? Symbol ( ) : `__${ name } ` ;
291296 Object . defineProperty ( this . prototype , name , {
297+ // tslint:disable-next-line:no-any no symbol in index
292298 get ( ) : any {
299+ // tslint:disable-next-line:no-any no symbol in index
293300 return ( this as any ) [ key ] ;
294301 } ,
295- set ( this : UpdatingElement , value : any ) {
302+ set ( this : UpdatingElement , value : unknown ) {
303+ // tslint:disable-next-line:no-any no symbol in index
296304 const oldValue = ( this as any ) [ name ] ;
305+ // tslint:disable-next-line:no-any no symbol in index
297306 ( this as any ) [ key ] = value ;
298307 this . requestUpdate ( name , oldValue ) ;
299308 } ,
@@ -338,6 +347,7 @@ export abstract class UpdatingElement extends HTMLElement {
338347 for ( const p of propKeys ) {
339348 // note, use of `any` is due to TypeSript lack of support for symbol in
340349 // index types
350+ // tslint:disable-next-line:no-any no symbol in index
341351 this . createProperty ( p , ( props as any ) [ p ] ) ;
342352 }
343353 }
@@ -375,7 +385,7 @@ export abstract class UpdatingElement extends HTMLElement {
375385 * @nocollapse
376386 */
377387 private static _propertyValueFromAttribute (
378- value : string , options : PropertyDeclaration ) {
388+ value : string | null , options : PropertyDeclaration ) {
379389 const type = options . type ;
380390 const converter = options . converter || defaultConverter ;
381391 const fromAttribute =
@@ -468,6 +478,7 @@ export abstract class UpdatingElement extends HTMLElement {
468478 private _applyInstanceProperties ( ) {
469479 // Use forEach so this works even if for/of loops are compiled to for loops
470480 // expecting arrays
481+ // tslint:disable-next-line:no-any
471482 this . _instanceProperties ! . forEach ( ( v , p ) => ( this as any ) [ p ] = v ) ;
472483 this . _instanceProperties = undefined ;
473484 }
@@ -497,7 +508,7 @@ export abstract class UpdatingElement extends HTMLElement {
497508 /**
498509 * Synchronizes property values when attributes change.
499510 */
500- attributeChangedCallback ( name : string , old : string , value : string ) {
511+ attributeChangedCallback ( name : string , old : string | null , value : string | null ) {
501512 if ( old !== value ) {
502513 this . _attributeToProperty ( name , value ) ;
503514 }
@@ -526,14 +537,14 @@ export abstract class UpdatingElement extends HTMLElement {
526537 if ( attrValue == null ) {
527538 this . removeAttribute ( attr ) ;
528539 } else {
529- this . setAttribute ( attr , attrValue ) ;
540+ this . setAttribute ( attr , attrValue as string ) ;
530541 }
531542 // mark state not reflecting
532543 this . _updateState = this . _updateState & ~ STATE_IS_REFLECTING_TO_ATTRIBUTE ;
533544 }
534545 }
535546
536- private _attributeToProperty ( name : string , value : string ) {
547+ private _attributeToProperty ( name : string , value : string | null ) {
537548 // Use tracking info to avoid deserializing attribute value if it was
538549 // just set from a property setter.
539550 if ( this . _updateState & STATE_IS_REFLECTING_TO_ATTRIBUTE ) {
@@ -547,7 +558,8 @@ export abstract class UpdatingElement extends HTMLElement {
547558 // mark state reflecting
548559 this . _updateState = this . _updateState | STATE_IS_REFLECTING_TO_PROPERTY ;
549560 this [ propName as keyof this] =
550- ctor . _propertyValueFromAttribute ( value , options ) ;
561+ // tslint:disable-next-line:no-any
562+ ctor . _propertyValueFromAttribute ( value , options ) as any ;
551563 // mark state not reflecting
552564 this . _updateState = this . _updateState & ~ STATE_IS_REFLECTING_TO_PROPERTY ;
553565 }
@@ -566,7 +578,7 @@ export abstract class UpdatingElement extends HTMLElement {
566578 * @param oldValue {any} (optional) old value of requesting property
567579 * @returns {Promise } A Promise that is resolved when the update completes.
568580 */
569- requestUpdate ( name ?: PropertyKey , oldValue ?: any ) {
581+ requestUpdate ( name ?: PropertyKey , oldValue ?: unknown ) {
570582 let shouldRequestUpdate = true ;
571583 // if we have a property key, perform property update steps.
572584 if ( name !== undefined && ! this . _changedProperties . has ( name ) ) {
0 commit comments