Skip to content
Mariano Botta edited this page Apr 26, 2021 · 5 revisions

Guía de desarrollo Andes/Angular

Primeros pasos

  • Linteo 4 espacios.
  • VsCode Ide desarrollo.
  • Tslint extension.
  • Configuración VSCode:
{ 
    "files.exclude": {
        "**/.git": true,
        "**/.DS_Store": true,
        "**/*.js": {
            "when": "$(basename).ts"
        },
        "**/*.js.map": {
            "when": "$(basename)"
        }
    },
    "editor.formatOnSave": true,
    "html.format.wrapAttributes": "aligned-multiple",
    "tslint.autoFixOnSave": true,
    "html.format.enable": true,
    "html.format.wrapLineLength": 120
}
  • Nomenclatura de archivos: Kebab Case (nombre-de-archivo.component.ts)

Angular no detecta cambios

Algunos sistemas operativos tienen restricción en la cantidad de archivos para monitorizar, por eso hay que cambiar la cantidad de watches permitidas:

echo fs.inotify.max_user_watches=524288 | sudo tee /etc/sysctl.d/40-max-user-watches.conf && sudo sysctl --system

Estructuración de modulos

Todo desarollo nuevo debe comenzar en la carpeta apps, con la palabra clave del modulo como nombre de carpeta raíz. Dentro deberá contener el archivo del modulo y el de ruteos:

  1. nombre-modulo.module.ts
  2. nombre-modulo.routing.ts

Estructura de carpeta (algunas son opcionales):

  • components
  • directives
  • models
  • interfaces
  • pipes
  • services
  • views

Components

Son las componentes compartidas por dos o más vistas; o aquellas que se exportan para ser usadas por otros modulos.

El nombre de la clase debe finalizar con la palabra Component, y su selector arrancar con el prefijo del nombre del modulo (u abreviación). Es necesario para esto modificar el tslint.json

Las componentes solo deben tener accesos a los servicios y no más de algunos metodos para el manejo de elementos visuales. Todos los llamados a la API deben ocurrir los servicios.

Views

Las vistas son las componentes que se usan como raíz de una ruta. Arrancan con plex-layout y son las únicas que deben usarlo. Presentan muy poco código, solo son contenedores de componetes visuales y orquetadores de las mismas. De esta forma introducir un cambio de layout es muy rápido.

Dentro de cada vista puede haber una o más subcarpeta, dónde cada cual es una subcomponente de esta vista. Son componentes exclusivas de la vista.

Services

Los servicios se deben separar en dos o más. Por un lado, las llamadas HTTP básicas (o puras) en un servicio separado que debe ser nombrado con el sufijo .http.ts. Esto permite separar la lógica de la aplicación de los request HTTP. Pudiendo ser reutilizables desde otros modulos. Cada recurso de la API debe tener su servicio exclusivo con sus endpoints

Por otro lado, puede haber servicios generares, que son compartidos por varias vistas y/o componente que ya presenta cierta lógica de negocio

Por otro lado, cada vista puede tener un servicio para sincronizar cada llamada.

Interfaces

Cada llamada a la API debe tener sus interfaz de respuesta, que puede ser independiente a la interfaz de los modelos. Algunas interfaces pueden estar adentro de una componente si se usan para tipar metodos o variables internas.

Modelos

La idea de los modelos es agrupar funcionalidades de un recurso en una clase, cuando llega la respuesta HTTP, se instancia ese modelo y se pueden precalcular ciertas variables. Estor permite encapsular cierta lógica del recurso en un solo lugar. Evitando diferentes tipos de accesos.

Template HTML

Primero en principal el identado de los tags HTML, el contenido de un tag debe ir en una nueva línea. Mejora la lectura del código y también evita las posibilidades de trabajos de mergeos. Así podemos trabajar más de una persona en el mismo archivo.

<plex-copy> 
    {{ prestacion.paciente.documento | number }}
</plex-copy>
  • ngIf: Dentro del if solo se puede poner una condición. Nada de concatenar and con diferentes variables. Si este es el caso se debe llevar a un virtual a la componentes Se recomiendo precalcular el valor en el OnInit o OnChanges, pudiendo así desarrollar mejor la lógica del elemento.
<plex-button type="success" *ngIf="canDelete">
    Borrar
</plex-button>
export class MiComponent {

    ngOnInit() {
        const tengoPermiso = this.auth.check('mi:permiso');
        const agendaDisponible = this.agenda.estado === 'disponible'
        this.canDelete = tengoPermiso && agendaDisponible;  
    }

}

(*) Notar el uso de dos variables para mejorar la comprensión del código.

  • ngFor: Interar sobre una variable de tipo array, con nombre descriptivo, tanto el array como el item que itera. Angular tiene variable de contexto como index, even, odd, first y last.
<div *ngFor="let prestacion of prestaciones; let i = index; let esPar = odd">
    {{ esPar ? 'Soy par' : 'No soy par' }}
</div>
  • [class.mi_clase]: Directiva de Angular para asignar una clase CSS a un componente si se cumple o no la condición.
<div [class.selected]="prestacion.id === idSelected">
    Contenido de la prestacion.
</div>
  • Eventos (click): Un evento emitido por una componente solo debe contener una llamada a un método. No concatenar sentencias ni asignar variables desde este lugar.
<plex-button type="success" (click)="OnDelete()">
    Borrar
</plex-button>

División en componentes

La primera división importante es separar la vista de los elementos visuales del recurso:

  • mpi/paciente-buscador-view
    • mpi-paciente-buscador-component
    • mpi-paciente-listado-component
    • mpi-paciente-detalle-component
  • mpi/paciente-abm-view
    • mpi-paciente-abm-component
    • mpi-paciente-contacto-component
    • mpi-paciente-detalle-component
    • mpi-paciente-numero-carpeta-component

(*) Los nombres son meramente iliustrativos.

El segundo punto importante es cuando tenemos un *ngFor. En la mayoría de los casos amerita crear una nueva componente, salvo que el contenido del for sea muy pequeño.

Un hecho importante que marca esto, es que no se pueden crear virtuals para un item dentro de un for, así que ese es un buen indicio de que necesitamos otra componente.

Separar el item del listado, mejora la legibilidad del código, evita condiciones muy complejas, se puede aprovecha los virtuals, los metodos no quedan hiper-parametrizados y los archivos son más pequeños mejorando la posibilidad de trabajo en paralelo.