Private class fields

This translation is incomplete. Please help translate this article from English

Las propiedades de la clase son públicas de forma predeterminada y se pueden examinar o modificar fuera de la clase. Sin embargo, existe una propuesta experimental  para permitir la definición de campos de clase privados utilizando un #prefijo hash .

Syntax

class ClassWithPrivateField {   
  #privateField
}

class ClassWithPrivateMethod {   
  #privateMethod() {     
    return 'hello world'
 }
}

class ClassWithPrivateStaticField {   
  static #PRIVATE_STATIC_FIELD
}

Campos estáticos privados 

Los campos privados son accesibles en el constructor de clases desde dentro de la propia declaración de clases.

La limitación de las variables estáticas que se llaman solo por métodos estáticos aún se mantiene

class ClassWithPrivateStaticField {
  static #PRIVATE_STATIC_FIELD

  static publicStaticMethod() {
    ClassWithPrivateStaticField.#PRIVATE_STATIC_FIELD = 42
    return ClassWithPrivateStaticField.#PRIVATE_STATIC_FIELD
  }
}

console.assert(ClassWithPrivateStaticField.publicStaticMethod() === 42)

Los campos estáticos privados se agregan al constructor de la clase en el momento de la evaluación de la clase.

Existe una restricción de procedencia en los campos estáticos privados. Solo la clase que define el campo estático privado puede acceder al campo.

Esto puede conducir a un comportamiento inesperado al usar this.

class BaseClassWithPrivateStaticField {
  static #PRIVATE_STATIC_FIELD

  static basePublicStaticMethod() {
    this.#PRIVATE_STATIC_FIELD = 42
    return this.#PRIVATE_STATIC_FIELD
  }
}

class SubClass extends BaseClassWithPrivateStaticField { }

let error = null

try {
  SubClass.basePublicStaticMethod()
} catch(e) { error = e}

console.assert(error instanceof TypeError)

Campos de instancia privados

Los campos de instancia privados se declaran con # nombres  (pronunciados " nombres hash "), que son identificadores con el prefijo #. El #es una parte del nombre propio. También se utiliza para la declaración y el acceso.

La encapsulación es impuesta por el lenguaje. Es un error de sintaxis referirse a #nombres que están fuera del alcance.

class ClassWithPrivateField {
  #privateField
  
  constructor() {
    this.#privateField = 42
    this.#randomField = 666 // Syntax error
  }
}

const instance = new ClassWithPrivateField()
instance.#privateField === 42 // Syntax error

Métodos privados

Métodos estáticos privados

Al igual que su equivalente público, los métodos estáticos privados se invocan en la propia clase, no en instancias de la clase. Al igual que los campos estáticos privados, solo se puede acceder a ellos desde dentro de la declaración de clase.

Los métodos estáticos privados pueden ser funciones generadoras, asíncronas y asíncronas.

class ClassWithPrivateStaticMethod {
    static #privateStaticMethod() {
        return 42
    }

    static publicStaticMethod1() {
        return ClassWithPrivateStaticMethod.#privateStaticMethod();
    }

    static publicStaticMethod2() {
        return this.#privateStaticMethod();
    }
}

console.assert(ClassWithPrivateStaticMethod.publicStaticMethod1() === 42);
console.assert(ClassWithPrivateStaticMethod.publicStaticMethod2() === 42);

Esto puede conducir a un comportamiento inesperado al usar this. En el siguiente ejemplo se thishace referencia a la Derivedclase (no a la Baseclase) cuando intentamos llamar Derived.publicStaticMethod2(), y por lo tanto exhibe la misma "restricción de procedencia" que se mencionó anteriormente:

class Base {
    static #privateStaticMethod() {
        return 42;
    }
    static publicStaticMethod1() {
        return Base.#privateStaticMethod();
    }
    static publicStaticMethod2() {
        return this.#privateStaticMethod();
    }
}

class Derived extends Base {}

console.log(Derived.publicStaticMethod1()); // 42
console.log(Derived.publicStaticMethod2()); // TypeError

Métodos de instancia privada

Los métodos de instancia privada son métodos disponibles en instancias de clase cuyo acceso está restringido de la misma manera que los campos de instancia privada.

class ClassWithPrivateMethod {
  #privateMethod() {
    return 'hello world'
  }

  getPrivateMessage() {
      return this.#privateMethod()
  }
}

const instance = new ClassWithPrivateMethod()
console.log(instance.getPrivateMessage())
// expected output: "hello worl​d"

Los métodos de instancia privada pueden ser funciones generadoras, asíncronas o asíncronas. Los getters y setters privados también son posibles:

class ClassWithPrivateAccessor {
  #message

  get #decoratedMessage() {
    return `✨${this.#message}✨`
  }
  set #decoratedMessage(msg) {
    this.#message = msg
  }

  constructor() {
    this.#decoratedMessage = 'hello world'
    console.log(this.#decoratedMessage)
  }
}

new ClassWithPrivateAccessor();
// expected output: "✨hello worl​d✨"

Specifications

Specification
Public and private instance fields
La definición de 'FieldDefinition' en esta especificación.

Browser compatibility

Update compatibility data on GitHub
DesktopMobileServer
ChromeEdgeFirefoxInternet ExplorerOperaSafariAndroid webviewChrome para AndroidFirefox para AndroidOpera para AndroidSafari en iOSSamsung InternetNode.js
Private class fieldsChrome Soporte completo 74Edge Soporte completo 79Firefox Sin soporte NoIE Sin soporte NoOpera Soporte completo 62Safari Soporte completo 14WebView Android Soporte completo 74Chrome Android Soporte completo 74Firefox Android Sin soporte NoOpera Android Soporte completo 53Safari iOS Soporte completo 14Samsung Internet Android Sin soporte Nonodejs Soporte completo 12.0.0

Leyenda

Soporte completo  
Soporte completo
Sin soporte  
Sin soporte

See also