SEO Y ANGULAR
Este proyecto consisiterá en crear un Server Side Rendering (SSR) y cómo implementarlo para que nuestra aplicación SPA con Angular pueda ser detectada por la web (SEO) haciendo uso de Angular Universal (@nguniversal/express-engine)
Si necesitas ayuda esta disponible el siguiente video explicativo: https://www.youtube.com/watch?v=J8PDfVY2FfI.
Peligro de SPA con el SEO
La gran ventaja de las aplicaciones SPA(Aplicaciones del lado cliente) es que trabajan en el lado del cliente. Por ejemplo una web creada en el framework de Angular se ejecuta en el cliente, es decir, en el navegador del usuario y no en un servidor remoto. Este tipo aplicaciones web muestran todas las pantallas en una misma página, sin recargar el navegador.
El problema surge con Google. Cuando se rastrea una web; los robots/rastreadores de motores de búsqueda de Google o Yahoo funcionan de forma similar al comando curl. ¿Por qué? Simple, iniciar el navegador y ejecutar JavaScript es una tarea costosa y, por lo tanto, no viable. No hay tiempo ni recursos para hacerlo cuando necesita buscar miles de páginas.
El ejemplo real
Creemos una aplicación angular y verifiquemos cómo la ven los robots: Ahora, en la otra ventana de terminal, ejecute el comando curl y echamos un vistazo a la salida: Como podemos observar, no renderiza correctamente la web y nuestra aplicación web con Angular no ha sido detectada correctamente, es decir, los motores de búsqueda consideran que no hay contenido.
La solución
La solución a este problema es usar @nguniversal/express-engine . Con este módulo podremos utilizar el Server Side Rendering para renderizar el contenido en el servidor y así servirla al usuario completa.
¿Que necesitamos? Para ello necesitamos tener instalado:
- Tener instalado Node y NPM.
- Tener instalado Angular CLI
¿Qué nos ofrece Angular Universal?
Es una tecnología que nos permitirá ejecutar nuestra aplicación Angular desde el servidor.
Genera páginas de aplicaciones estáticas en el servidor mediante el proceso denominado SSR (server side rendering o renderizado de lado del servidor) que nos permitirá cubrir las áreas oscuras que se dan en el desarrollo moderno:
- Facilitar la indexacion del SEO
- Mejorar el rendimiento de la aplicacion en dispositivos de baja potencia
- Mostrar la primera pagina rápidamente
La importancia de implementar SEO en un proyecto
Es una parte importantísima para cualquier negocio sea pequeño, mediano o grande. El objetivo del SEo es conseguir que visiten nuestra página web o la de nuestra empresa la mayor cantidad de gente posible y para ello se definen una serie de procedimiento y técnias que permitirán tener una mayor repercusión a nuestra web
Hay dos tipos:
- SEO on page: se trata de todo lo que puedes hacer respecto al código de nuestra web para que genere más tráfico y es lo que vamos a ver en esta sección
- TSEO off page: como su nombre indica es todo lo relacionado con tu negocio fuera de tu página, es decir, lo que corresponde a redes sociales, publicidad, etc.
Para obtener estos objetivos, en nuestra aplicación de angular vamos a implementar la siguiente solución:
En ella se observa: - El usuario solicita la página.
- La solicitud llega al servidor
- NodeJS genera HTML y lo envía al navegador
- El navegador muestra la vista desde el HTML e inmediatamente la muestra al usuario, simultáneamente se está ejecutando JavaScript
- Cuando JavaScript finaliza el arranque de la aplicación, cambia la vista representada en HTML con la aplicación angular
- El usuario ve una aplicación angular totalmente interactiva
Bueno. Conocemos la teoria. Vamos a practicar ahora.
Aplicando SSR con Angular Universal
Ahí es donde @nguniversal/express-engine entra en el juego. Escriba un comando simple:
ng add @nguniversal/express-engine
Hay que recordar que el CLI de Angular utilizar la directiva “ng add” del principio del uso de los schematicas para modificar nuestro código y adaptarlo a la nueva funcionalidad que queremos implementar.
Si hicieramos manualmente el proceso tendríamos que seguir los siguientes pasos, que como podéis ver son muchos:
- Instalar nuevas dependencias
- Editar el fichero main.ts
- Editar el fichero app.module.ts
- Editar el fichero angular.json
- Crear el fichero src/app/app.server.module.ts
- Crear el fichero src/main.server.ts
- Crear el fichero server.ts
- Crear el fichero tsconfig.server.json
- Crear el fichero webpack.server.config.js
- Editar el fichero angular.json
- Editar el fichero package.json
Ahora que ya tenemos nuestra aplicación adaptada al renderizado por el lado del servidor (SSR), con lo visto hasta ahora, nuestra aplicación estará más que cubierta en cuanto a ofrecer la mejor experiencia para usuarios al tiempo que conseguiremos enviar contenido indexable para robots… mejorando este punto negativo en las aplicaciones de tipo SPA.
Lanzar la aplicación
Para lanzar la aplicación se ejecutan los siguientes comandos:
npm run build:ssr
npm run serve:ssr
Y si ejecutamos la misma sentencia que antes nos encontramos con el suguiente código html:
curl localhost:4000
¿Qué pasa con window y localStorage?
NodeJS y los navegadores pueden ejecutarse en 99% de los casos con el mismo código. Pero hay algunas cosas que se pueden ejecutar solo en NodeJS o solo en el navegador. Ahora nos centraremos en resolver estas incidencias
Window: es el navegador que utiliza el cliente. Un rastreador no utiliza una ventana entonces, si por ejemplo queremos utilizar el siguiente código nos daria un error:
public ngOnInit (): void {
console.log (window.URL);
}
En mi caso, para ese problema he aplicado la siguiente solución:
import {Component, Inject, OnInit, PLATFORM_ID} from '@angular/core';
import {isPlatformBrowser} from '@angular/common';
@Component ( {
...
export class xxxxComponent implements OnInit {
isBrowser;
constructor(@Inject(PLATFORM_ID) private platformId: object) {
this.isBrowser = isPlatformBrowser(platformId);
}
ngOnInit() {
if (this.isBrowser) {
if (document.cookie.indexOf(this.cookie_name + '=1') >= 0) {
....
}
}
}
Es decir, con PLATFORM_ID puedo comprobar si hay o no una ventana solicitando la información. En caso afirmativo, genero el código necesario para que se muestre la lógica necesaria, en caso negativo, muestro la lógica deseada en ese caso.
Puesta en producción
En mi caso, he decidido utilizar pm2 para ejecutar el servidor, próximamente creare un proyecto explicando como llevar a cabo una puesta en marcha de un proyecto en angular de estas caracteristicas, pero mientras tanto dejo el siguiente comando:
sudo npm install -g pm2
Una vez instalado, tengo que copiar el directorio raiz (por ejemplo, utilizando el comando scp) creado por el comando:
npm run build:ssr
EL directorio raiz es por defector /dist pero depende de la configuración del proyecto. Una vez copiado el directorio, simplemente se genera un fichero con el siguiente código:
// generated by @nguniversal/express-engine
const port = process.env.PORT || 8590;
const server = require('./dist/server');
server.app.listen(port, () => {
console.log(`Listening on: http://localhost:${port}`);
});
Con este fichero creado y el entorno pm2 instalado se ejecuta el siguiente comando:
pm2 start node filename.js (en mi caso server.js)
Y ya tendremos en ejecutación en la url http://xxxx:8590 nuestro Server Side Rendering. Si por ejemplo estamos en un entorno apacher, si añadimos a nuestro archivo .conf del dominio las siguientes tres linea redireccionariamos las peticiones 80 al Server Side Rendering de la siguiente forma:
<VirtualHost www.example.com:80>
ProxyPreserveHost On
ProxyRequests Off
ServerName www.example.com
ServerAlias example.com
ProxyPass / http://localhost:8080/
ProxyPassReverse / http://localhost:8080/
</VirtualHost>
Es necesario tener instalado tanto el paquete proxy y proxy_http de apache y configurado.
sudo a2enmod proxy
sudo a2enmod proxy_http
Lecturas relacionadas de SEO tecnico
- Como usar Codex dentro de IntelliJ IDEA. Util cuando quieres que Codex inspeccione rutas, sitemap, catalogos y metadatos SEO antes de editar.
- SSR y SEO con ngx-highlightjs en Angular. Ejemplo practico para mejorar bloques de codigo sin perder calidad de renderizado en servidor.
- Ejemplo de routing en Angular. Complementa este articulo porque las rutas rastreables y enlaces reales forman parte del SEO tecnico.
- ngx-highlightjs en Angular Universal. Util si tus paginas tienen ejemplos de codigo y quieres que sigan siendo legibles para usuarios y bots.
- Migracion de Firebase en Angular. Conecta el trabajo SEO con analisis de bundle, imports modernos y rendimiento frontend.
- hCaptcha con Angular Universal. Caso relacionado donde las integraciones solo de navegador necesitan cuidado especial en SSR.
- JavaScript externo en Angular. Ayuda a revisar scripts que pueden afectar al renderizado, la indexacion y la estabilidad de pagina.
- PageRank y factores de ranking. Aporta contexto teorico sobre enlaces, autoridad y por que importa el enlazado interno.