No tienes acceso a esta clase

¡Continúa aprendiendo! Únete y comienza a potenciar tu carrera

Implementación de Abstract Factory en JS

14/27
Recursos

Aportes 10

Preguntas 2

Ordenar por:

¿Quieres ver más aportes, preguntas y respuestas de la comunidad?

En lo personal este patrón no me encanta. Factory ya usaba una capa de abstracción y este agrega otra capa (lo cuál lo hace complejo).
Además de eso, para agregar un producto nuevo (un coche en este caso), se necesitan agregar muchas cosas:

  • La creación del coche que siga el contrato de BaseCar (por cierto, no se agrego un BaseCar en el ejemplo de esta clase)
  • La creación de cada uno de los modelos de nuevo coche (Sedan y Hatchback en este caso)
  • Agregar un nuevo método en AbstractFactory para el nuevo producto
  • Agregar polimorfismo a cada subfactory del nuevo producto (SedanModelFactory & HatchbackModelFactory)
    .
    Son muchas cosas para agregar un nuevo producto. Aunque la buena noticia es que se siguen cumpliendo los principios de Responsabilidad Unica y de Open-Close

No logró pensar en donde podría aplicar yo este patrón, en algunos empleos lo piden, pero como se vio en el curso anterior quizá es una exageración el pedirlo.

Pero con este patrón si entendí algo, los desarrolladores de zomboid son expertos en POO, porque puedo ver como este patrón ayudo a plantear ciertas mecánicas de ese videojuego, por ejemplo el “nuevo” sistema de autos en zomboid está claramente basado en este tipo de factories y zomboid es un juego mucho más complejos a nivel de mecánicas que la mayoría de juegos del mismo tipo.

Muy interesante este patrón de diseño, creería que es un patrón que podemos utilizar cuándo tenemos lógicas de negocio complejas.

Comparto mi codigo hecho en TypeScript

// PASO 1
interface BaseCar {
    useGPS(): void
}

interface RhinoCar extends BaseCar {
}

interface MastodonCar extends BaseCar {
}

// PASO 2
class MastodonSedanCar implements MastodonCar {
    public useGPS(): void {
        console.log('[SEDAN] Mastodon GPS')
    }
}

class MastodonHatchbackCar implements MastodonCar {
    public useGPS(): void {
        console.log('[HATCHBACK] Mastodon GPS')
    }
}

class RhinoSedanCar implements RhinoCar {
    public useGPS(): void {
        console.log('[SEDAN] Rhino GPS')
    }
}

class RhinoHatchbackCar implements RhinoCar {
    public useGPS(): void {
        console.log('[HATCHBACK] Rhino GPS')
    }
}

// PASO 3
interface CarAbstractFactory {
    createMastodonCar(): MastodonCar
    createRhinoCar(): RhinoCar
}

// PASO 4
class SedanCarFactory implements CarAbstractFactory {
    public createMastodonCar(): MastodonCar {
        return new MastodonSedanCar()
    }

    public createRhinoCar(): RhinoCar {
        return new RhinoSedanCar()
    }
}

class HatchbackCarFactory implements CarAbstractFactory {
    public createMastodonCar(): MastodonCar {
        return new MastodonHatchbackCar()
    }

    public createRhinoCar(): RhinoCar {
        return new RhinoHatchbackCar()
    }
}

function appAbstractFactory(factory: CarAbstractFactory): void {
    const mastodon = factory.createMastodonCar()
    const rhino = factory.createRhinoCar()

    mastodon.useGPS()
    rhino.useGPS()
}

function createFactory(type: 'sedan' | 'hatchback'): CarAbstractFactory {
    const factories = {
        sedan: SedanCarFactory,
        hatchback: HatchbackCarFactory,
    }

    const Factory = new factories[type]
    return Factory
}

appAbstractFactory(createFactory('sedan'))
appAbstractFactory(createFactory('hatchback'))

Dejo mi codigo, a modo de experimento tengo algunas cosas distintas:

class NivusBase{
    model(){
    }
}

class TcrossBase{
    model(){
        throw Error("This method is not implemented");
    }
}

class NivusSedan extends NivusBase{
    model(){
        return "Nivus Senda 2023";
    }
}

class NivusHatback extends NivusBase{
    model(){
        return "Nivus Hatback 2023";
    }
}

class TcrossSedan extends TcrossBase{
    model(){
        return "Tcross Sedan 2023";
    }
}

class TcrossHatback extends TcrossBase{
    model(){
        return "Tcross Hatback 2023";
    }
}

class CarAbstractFactory {
    createNivus(){
        throw Error("This method is not implemented");

    }
    
    createTcross(){
        throw Error("This method is not implemented");

    }
}


class SedanCarFactory extends CarAbstractFactory{
    createNivus(){
        return new NivusSedan();

    }
    createTcross(){
        return new TcrossSedan();
    }

}

class HatbackCarFactory extends CarAbstractFactory{
    createNivus(){
        return new NivusHatback();

    }
    createTcross(){
        return new TcrossHatback();
    }
}

function appAbstractFactory(factory){
    return new factory()
}

carSedanFactory = appAbstractFactory(SedanCarFactory);
carHatbackFactory = appAbstractFactory(HatbackCarFactory);

console.log(carSedanFactory.createNivus().model());
console.log(carSedanFactory.createTcross().model());

console.log(carHatbackFactory.createNivus().model());
console.log(carHatbackFactory.createTcross().model());

En el paso 4 noté que faltó heredar de la clase CarAbstractFactory para cumplir con lo que nos dice este paso: Create concrete factories that implements/inherits from the abstract factory behaviour and implements all the products creation methods. ```js class SedanCarFactory extends CarAbstractFactory { /** * @override createMastodon() method * @returns MastodonSedanCar */ createMastodon() { return new MastodonSedanCar(); } /** * @override createRhino() method * @returns RhinoSedanCar */ createRhino() { return new RhinoSedanCar(); } } ```

Cada vez más preparados para ir a aplicar en Tesla 😎

como sacas los multiples cursores para editar varias lineas de codigo al tiempo ? s no tengo mouse :V
Un poco díficil de entender en la última parte, en particular en el siguiente fragmento de código: ```js function createFactory(type) { // .... const Factory = factories[type]; return new Factory(); } ```Creo que se debe especificar que la constante Factory, ahora contiene una referencia a la clase o función constructora que fue seleccionada en el paso anterior. Luego se crea una nueva instancia de esa clase o función constructora usando `new Factory()`.
El que no haya extendido las clases `HatchbackCarFactory` y `SedanCarFactory` a `CarAbstractFactory` es un error? Si no fuese un error, no coincidiria con el diagrama de la clase anterior.