en las versiones recientes de sinon no se usa
sinon.sandbox.create()
sinon.sandbox.restore()
esto se convierte a
sinon.createSandbox()
sinon.resetHistory()
Inicio del curso
¿Qué vamos a construir en el curso avanzado de Node.js?
Introducción a Node.js
Conoce qué es node.js
Características de la plataforma Node.js
¿Qué tipo de aplicaciones podemos desarrollar con Node.js?
Preparando el entorno de Desarrollo
Cómo instalar Node.js en macOS
Cómo instalar PostgreSQL y Redis en macOS
Cómo instalar Visual Studio Code en macOS
Cómo instalar Ansible en macOS
Arquitectura del Proyecto (Platziverse)
Arquitectura y Componentes del proyecto
Introducción a protocolos y patrones de aplicaciones en tiempo real
Cómo funciona el modelo Pub/Sub en MQTT y Web Sockets
Creando Módulo de Base de Datos (platziverse-db)
Estructura básica de un módulo de Node.js
Definición de entidades de base de datos
Implementación de modelos con sequelize
Implementación de un módulo básico de base de datos
Implementación de script de inicialización de base de datos
Creando una advertencia sobre el borrado de base de datos
Introducción a pruebas unitarias con Ava.js
Introducción a code coverage con nyc
Cómo hacer Mocks y Stubs con Sinon
Creación de fixtures y definición básica del servicio de Agent
Implementación de findbyId y pruebas en el servicio Agent
Implementación de createOrUpdate
Revisión del servicio Agent
Implementación del servicio Metric
Realizando un ejemplo con el módulo de base de datos
Reto: Cómo modificar el script de inicialización de la base de datos
Construyendo un servidor en tiempo real para Internet de las Cosas con Mosca/MQT
Definición de un Broker de Mensajería
Definición de los tipos de mensajes
Implementación del servidor MQTT
Cómo recibir mensajes
Cómo integrar el servidor MQTT con la base de datos
Cómo almacenar la información del agente y reportar el agente conectado
Cómo almacenar la información de las métricas
Probando el servidor MQTT (Ejemplo con mqtt client)
Construyendo el agente de monitoreo (platziverse-agent)
Cómo implementar un custom EventEmitter usando ES6 classes
Definiendo un timer de ejecución continua (setInterval)
Implementación del cliente MQTT
Implementación de métricas personalizadas
Probar agent (ejemplo)
Construyendo una API REST con Express (platziverse-api)
Implementación de un servidor básico con express
Definición de rutas del API
Implementación de manejo de errores con express
Pruebas básicas de Integración con Ava y supertest
Integración con el módulo de base de datos
Implementación de ruta del API
Pruebas de Integración con Ava, Supertest y Sinon
Asegurando nuestra API REST con JWT
Definición de JWT
Asegurando nuestra API con express-jwt
Modificando las pruebas de integracion
Implementando permisos con express-jwt-permissions
Creando un Dashboard Web en tiempo real con WebSockets (platziverse-web)
Implementación de un servidor web estático con express
Integrando socket.io con express
Integrando agente de monitoreo con socket.io
Implementación de rutas proxy con la API
Presentación de nuestro cliente frontend en Vue.js
Integración del cliente frontend con API (Metric)
Integración del cliente frontend con socket.io (Metric)
Integración del cliente frontend con API (Agent)
Integración del cliente frontend con socket.io (Agent)
Creando un Dashboard para la terminal en tiempo real con Blessed (platziverse-cl)
Implementación de un CLI Básico con Node
Introducción a Blessed / Blessed Contrib
Implementación del layout básico con Blessed Contrib
Integración con el agente de monitoreo 1
Integración con el agente de monitoreo 2
Integración con el agente de monitoreo 3
Depurando Aplicaciones Node.js
Utilizando longjohn para mejores stacktraces
Depurando en Desarrollo con node --inspect
Depurando en Desarrollo con Visual Studio Code
Preparando nuestra aplicación para producción
Preparando Proyecto para Producción 1
Preparando Proyecto para Producción 2
Creación de scripts para despliegue con Ansible
Probando el database rol con Vagrant
Creando scripts del rol de platziverse db y mqtt (script de automatización .yml)
Terminando los scripts faltantes
Creación de servidores en DigitalOcean
Desplegando nuestra aplicación a producción
Ejecutando los Scripts de Despliegue
Utilizando Aplicación en Producción y cierre del curso
Bonus: Utilizando platziverse-agent en BeagleBone Black y Raspberry PI
Implementación platziverse-agent con Johnny-Five
No tienes acceso a esta clase
¡Continúa aprendiendo! Únete y comienza a potenciar tu carrera
Vamos a crear unos servicios que van a utilizar unos modelos, y estos son los que se van a conectar a la base de datos. Sequelize se encarga de probar los modelos.
Aportes 17
Preguntas 10
en las versiones recientes de sinon no se usa
sinon.sandbox.create()
sinon.sandbox.restore()
esto se convierte a
sinon.createSandbox()
sinon.resetHistory()
Para versiones actuales de sinon me toco realizar los siguientes cambios:
let sanbox = null
test.beforeEach(async () => {
sanbox = sinon.createSandbox()
AgentStub = {
hasMany:sanbox.spy()
}
...
})
test.afterEach(() => {
sanbox && sanbox.restore()
})
asi es como cambia el código en las versiones actuales, se llama directamente createSandbox en lugar de sinon.sandbox
de igual manera con afterEach(), directamente es sandbox.restore() sin necesidad de llamar a sinon
test.beforeEach(async () => {
sandbox = sinon.createSandbox()
...
}
test.afterEach( () => {
sandbox && sandbox.restore()
})
Hola, para los que se atreven a realizar este excelente curso con un poco de desactualización como yo. En esta época ya existe un test runner llamado jest, mantenido por facebook que facilita un poco la construcción de las pruebas automatizadas. Para aquellos que quieran lanzarse con ello y no esten tan empapados, pueden ver el curso de Jest que está más adelante en la escuela de backend con JS o mirar mi implementación en mi repositorio.
Este test runner, no necesita la creación de un isolated env como lo es el sandbox ni un proxyquire. El realiza esa gestión internamente. Y para la restauración o limpieza de ese “sandbox”, jest ofrece la función clearAllMocks la cual puede ser llamada en los hooks muy similar a como se hace en esta clase.
Esas son algunas conclusiones que he sacado personalmente al hacer ese update de algunas dependencias como el test runner. Si alguien es más experto en el tema agradezco me corriga.
Por si alguien lo está haciendo con jest, este código me funciona
'use strict'
let config = {
logging: function(){},
}
let mockMetricModel = {
belongsTo: jest.fn(),
}
let mockAgentModel = null
let db = null
beforeEach(async () => {
mockAgentModel = {
hasMany: jest.fn(),
}
const setupDatabase = require('../../index')
jest.mock('../../models/agent', () => jest.fn(() => mockAgentModel))
jest.mock('../../models/metric', () => jest.fn(() => mockMetricModel))
db = await setupDatabase(config)
})
afterEach(() => {
jest.resetModules()
jest.clearAllMocks()
})
describe('Agent', () => {
test('The agent should exists', () => {
expect(db.Agent).toBeDefined()
})
test('setupAgentModel.hasMany should be called', () => {
expect(mockAgentModel.hasMany).toHaveBeenCalled()
})
test('setupMetricModel.belongsTo should be called', () => {
expect(mockMetricModel.belongsTo).toHaveBeenCalled()
})
test('setupAgentModel.hasMany should be called with mockMetricModel', () => {
expect(mockAgentModel.hasMany).toHaveBeenCalledWith(mockMetricModel)
})
test('setupMetricModel.belongsTo should be called with mockAgentModel', () => {
expect(mockMetricModel.belongsTo).toHaveBeenCalledWith(mockAgentModel)
})
})
Usamos los stubs para garantizar que se hacen llamadas a las funciones adecuadas, abstraiendo asi las llamadas de sequelize, las cuales como son de una libreria externa ya testeada no debemos preocuparnos por testearla.
Hola Para lo que estén viendo este video en 2021 hay dos pequeños cambios en sinon “sinon.createSandbox()” y “sinon.restore()”
test.beforeEach(async () => {
sandbox = sinon.createSandbox()
AgentStub = {
hasMany: sandbox.spy()
}
const setupDatabase = proxyquire('../', {
'./models/agent': () => AgentStub,
'./models/metric': () => MetricStub
})
db = await setupDatabase(config)
})
demasiada información en muy poco tiempo. me frustre 😞
Para correr test de forma serial en Jest hasta donde le entiendo a la doc se usa esto: https://jestjs.io/docs/api#testconcurrentname-fn-timeout
desde la versión 5, el objeto sinon es un sandbox por defecto
✌
Como serian las pruebas para la liberia request-promise-native usando sinon.?
Este seria mi implementacion pero no esta funcionando correctamente
const request = require(‘request-promise-native’)
let resolveStub = sandbox.stub(request, ‘Request’).withArgs(options).resolves(data)
Donde “options” son los datos del conexion a la API y “data” es el resultado esperado.
Estoy intentando conseguir hacer los “stubs” con Jest y no consigo hacerlos funcionar
Les dejo el codigo sin los stubs por si alguien sabe como implementarlo, Gracias!
import setupDatabase from '..';
const config = {
logging() {},
};
let db = null;
beforeEach(async () => {
db = await setupDatabase(config);
});
describe('Agent', () => {
test('Agent service should exist', () => {
expect(db.Agent).toBeTruthy();
});
test('Setup', () => {
// expect(MetricStub.belongsTo).toHaveBeenCalled();
// expect(Agent).toHaveBeenCalled();
});
});
Me parece interesante compartir esto que esta en la documentacion de AVA
Mocha requires you to use implicit globals like describe and it with the default interface (which most people use). It's not very opinionated and executes tests serially without process isolation, making it slow.
Proxyquire sobreescribe los modelos
Corro el comando npm i sinon --save-dev
y el comando npm i --save-dev proxyquire
y no se agregan a las dependencias de desarrollo. Alguien sabe porque?
{
"name": "platziverse-db",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "DEBUG=platziverse:* nyc --reporter=lcov ava tests/* --verbose",
"setup": "DEBUG=platziverse:* node setup.js",
"lint": "standard",
"lint-fix": "standard --fix"
},
"author": "",
"license": "ISC",
"devDependencies": {
"ava": "^3.8.2",
"nyc": "^15.0.1",
"sqlite3": "^4.2.0",
"standard": "^14.3.4"
},
"dependencies": {
"chalk": "^4.0.0",
"debug": "^4.1.1",
"defaults": "^1.0.3",
"inquirer": "^7.1.0",
"pg": "^8.2.0",
"pg-hstore": "^2.3.3",
"sequelize": "^5.21.9"
}
}
npm i proxyquire -D
Los aportes, preguntas y respuestas son vitales para aprender en comunidad. Regístrate o inicia sesión para participar.