Come si può comprendere dal precedente articolo, ho lavorato su diversi progetti. I primi giorni in un nuovo team solitamente seguono uno schema simile: il backend si unisce a me e svolge delle operazioni magiche per l'installazione e il deployment dell'applicazione. Docker è indispensabile per i frontend developer, poiché il backend è spesso scritto in una vasta gamma di stack come PHP, Java, Python e C#, e il frontend non deve continuamente distrarre il backend per installare e avviare tutto. Ho visto solo un caso di integrazione Docker-Jenkins con deploy trasparente, log e test automatici integrati.
Sono state scritte molte articoli dettagliati su Docker. In questo articolo si parlerà del deployment di un'Applicazione a Pagina Unica utilizzando VueJS/Vue Router, con il backend sotto forma di RESTful API realizzato in NodeJS, e come database verrà utilizzato MongoDB. Docker Compose è usato per descrivere e avviare diversi container applicativi.
A cosa serve Docker
Docker consente di automatizzare il processo di deployment dell'applicazione. I developer non devono più installare manualmente i programmi o affrontare conflitti di versioni sui loro sistemi. È sufficiente installare Docker e digitare 1-2 comandi nel terminale. È più comodo farlo su Linux.
Iniziare
Installiamo and
Struttura delle cartelle
Creiamo 2 cartelle per le applicazioni client e server. Un file con estensione .yml è un file di configurazione Docker Compose, dove sono definiti e collegati i contenitori dell'applicazione.
Docker-compose.yml:
version: "3"
services:
mongo:
container_name: mongo
hostname: mongo
image: mongo
ports:
- "27017:27017"
server:
build: server/
#command: node ./server.js #qui puoi sovrascrivere CMD dal Dockerfile in /server
ports:
- "3000:3000"
links:
- mongo
client:
build: client/
#command: http-server ./dist #qui puoi sovrascrivere CMD dal Dockerfile in /client
network_mode: host
ports:
- "8089:8089"
depends_on:
- server
Creiamo 3 servizi in Docker: per NodeJS, MongoDB e per il frontend in Vue. Per collegare il client al server è stato aggiunto depends on server. Per collegare MongoDB all'API del server si utilizza links mongo. Server, client, mongo sono i nomi dei servizi.
Client in VueJS
Nella cartella /client l'applicazione è basata su VueJS. L'applicazione è stata creata utilizzando . Durante la costruzione dell'immagine, l'applicazione client viene compilata in un insieme di file statici nella cartella /dist. Nel Dockerfile è descritto un insieme di comandi per la costruzione dell'immagine:
FROM node:10
WORKDIR /client
COPY ./package*.json ./
RUN npm install
RUN npm install -g http-server
COPY . .
RUN npm run build
EXPOSE 8081
CMD ["npm", "test:dev"]
Si noti che il package.json viene copiato e installato separatamente dagli altri file del progetto. Questo è fatto per migliorare le prestazioni, in modo che il contenuto della cartella /node_modules sia memorizzato nella cache durante il rebuild. Ogni riga di comando viene memorizzata nella cache separatamente.
Alla fine, durante l'avvio del contenitore viene eseguita la comando npm run dev. Questo comando è descritto nel package.json:
"scripts": {
"test:dev": "http-server dist -p 8081 -c 1 --push-state"
}
Per eseguire i file dalla cartella /dist, viene installato globalmente http-server, e tra le dev-dependencies il pacchetto spa-http-server, affinché Vue Router funzioni correttamente. Il flag —push-state reindirizza a index.html. Il flag -c con valore 1 secondo è stato aggiunto per http-server non memorizzare nella cache gli script. Questo è un esempio di test; in un progetto reale è meglio utilizzare nginx.
Nel Vuex store creiamo il campo apiHost: 'http://localhost:3000', dove si specifica la porta dell'API NodeJS. La parte client è pronta. Ora tutte le richieste dal client al backend vanno su questo URL.
API del server NodeJS
Nella cartella /server creiamo server.js e Dockerfile:
FROM node:10
WORKDIR /server
COPY ./package*.json ./
RUN npm install
COPY . .
EXPOSE 3000
CMD ["node", "server.js"]
In server.js che si indica url per il database const url = 'mongodb://mongo:27017/';. Permettiamo richieste cross-domain dal client:
const clientUrl = 'http://localhost:8081';
const corsOptions = {
origin: clientUrl,
optionsSuccessStatus: 200, // alcuni browser legacy (IE11, vari SmartTV) non riescono a gestire 204
};
app.use(cors());
app.all('*', (req, res, next) => {
res.header('Access-Control-Allow-Origin', clientUrl);
res.header('Access-Control-Allow-Headers', 'X-Requested-With');
next();
});
app.get('/getProducts', cors(corsOptions), (req, res) => {
products.getContent
.then(data => res.json(data), err => res.json(err));
});
app.get('/getUsers', cors(corsOptions), (req, res) => {
db.getUsers()
.then(data => res.json(data), err => res.json(err));
});
Conclusione
Ora passiamo alla directory del progetto e avviamo docker-compose build per la costruzione delle immagini e docker-compose up per l'avvio dei container. Il comando solleverà 3 container: server, client, mongo. Per il server su NodeJS è possibile configurare il hot-reload, collegandolo alla cartella user. E il client in fase di sviluppo può essere avviato localmente con hot reload, lanciandolo separatamente server e mongo. Per avviare un servizio separato, basta specificarne il nome docker-compose up client. Non dimenticate di eseguire di tanto in tanto prune e la rimozione dei container (containers), delle reti (networks) e delle immagini (images) per liberare risorse.
Il codice completo può essere visualizzato . Il progetto è ancora in fase di sviluppo.
Fonte: habr.com
