Skip to content
This repository has been archived by the owner on Nov 23, 2022. It is now read-only.

Commit

Permalink
Add way to deploy projects from image and image tar file
Browse files Browse the repository at this point in the history
  • Loading branch information
yamalight committed Feb 11, 2019
1 parent 3583f61 commit 084b14a
Show file tree
Hide file tree
Showing 6 changed files with 106 additions and 1 deletion.
46 changes: 46 additions & 0 deletions src/docker/templates/image.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
// npm packages
const fs = require('fs');
const path = require('path');

// template name
exports.name = 'image';

// function to check if the template fits this recipe
exports.checkTemplate = async ({config}) => {
// if project has image field defined in config
try {
return config.image && config.image.length;
} catch (e) {
return false;
}
};

// function to execute current template
exports.executeTemplate = async ({config, username, tempDockerDir, folder, resultStream, util, docker}) => {
// build docker image
try {
const {image, imageFile} = config;
util.writeStatus(resultStream, {message: `Deploying project from image: ${image}..`, level: 'info'});

// import from tar if needed
if (imageFile && imageFile.length) {
util.writeStatus(resultStream, {message: `Importing image from file: ${imageFile}..`, level: 'info'});
// get packed stream
const tarStream = fs.createReadStream(path.join(tempDockerDir, folder, imageFile));
const importRes = await docker.daemon.loadImage(tarStream, {tag: image});
util.logger.debug('Import result:', importRes);
}

// start image
const container = await docker.start({image, username, folder, resultStream});
util.logger.debug(container);

// return new deployments
util.writeStatus(resultStream, {message: 'Deployment success!', deployments: [container], level: 'info'});
resultStream.end('');
} catch (e) {
util.logger.debug('build failed!', e);
util.writeStatus(resultStream, {message: e.error, error: e.error, log: e.log, level: 'error'});
resultStream.end('');
}
};
3 changes: 2 additions & 1 deletion src/docker/templates/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ const path = require('path');
const {extensionsFolder} = require('../../config');

// hard-coded templates
const imageTemplate = require('./image');
const composeTemplate = require('./compose');
const dockerfileTemplate = require('./dockerfile');
const nodeTemplate = require('./node');
Expand All @@ -23,5 +24,5 @@ module.exports = () => {
return require(templatePath);
});

return [composeTemplate, dockerfileTemplate, nodeTemplate, nginxTemplate].concat(userTemplates);
return [imageTemplate, composeTemplate, dockerfileTemplate, nodeTemplate, nginxTemplate].concat(userTemplates);
};
47 changes: 47 additions & 0 deletions test/deploy.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ const docker = require('../src/docker/docker');
const {initNetwork} = require('../src/docker/network');

// create tar streams
const streamDockerImage = tar.pack(path.join(__dirname, 'fixtures', 'docker-image-project'));
const streamDocker = tar.pack(path.join(__dirname, 'fixtures', 'docker-project'));
const streamNode = tar.pack(path.join(__dirname, 'fixtures', 'node-project'));
const streamNodeLock = tar.pack(path.join(__dirname, 'fixtures', 'node-lock-project'));
Expand Down Expand Up @@ -111,6 +112,52 @@ test('Should deploy simple docker project', async done => {
done();
});

test('Should deploy simple project from image and image tar', async done => {
const options = Object.assign(optionsBase, {
payload: streamDockerImage,
});

const response = await fastify.inject(options);
// parse result into lines
const result = response.payload
.split('\n')
.filter(l => l && l.length)
.map(line => JSON.parse(line));

// find deployments
const completeDeployments = result.find(it => it.deployments && it.deployments.length).deployments;

// check response
expect(response.statusCode).toEqual(200);
expect(completeDeployments.length).toEqual(1);
expect(completeDeployments[0].Name.startsWith('/exo-test-image-')).toBeTruthy();

// check docker services
const allContainers = await docker.listContainers();
const containerInfo = allContainers.find(c => c.Names.includes(completeDeployments[0].Name));
const name = completeDeployments[0].Name.slice(1);

expect(containerInfo).toBeDefined();
expect(containerInfo.Labels['exoframe.deployment']).toEqual(name);
expect(containerInfo.Labels['exoframe.user']).toEqual('admin');
expect(containerInfo.Labels['exoframe.project']).toEqual('test-image-project');
expect(containerInfo.Labels['traefik.backend']).toEqual(`${name}.test`);
expect(containerInfo.Labels['traefik.docker.network']).toEqual('exoframe');
expect(containerInfo.Labels['traefik.enable']).toEqual('true');
expect(containerInfo.NetworkSettings.Networks.exoframe).toBeDefined();

const containerData = docker.getContainer(containerInfo.Id);
const container = await containerData.inspect();
expect(container.NetworkSettings.Networks.exoframe.Aliases.includes('testimage')).toBeTruthy();
expect(container.HostConfig.RestartPolicy).toMatchObject({Name: 'no', MaximumRetryCount: 0});

// cleanup
const instance = docker.getContainer(containerInfo.Id);
await instance.remove({force: true});

done();
});

test('Should deploy simple node project', async done => {
const options = Object.assign(optionsBase, {
payload: streamNode,
Expand Down
3 changes: 3 additions & 0 deletions test/fixtures/docker-image-project/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
FROM busybox

CMD ["sleep", "300"]
8 changes: 8 additions & 0 deletions test/fixtures/docker-image-project/exoframe.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"name": "test-docker-image-deploy",
"hostname": "testimage",
"project": "test-image-project",
"restart": "no",
"image": "exo-test-image",
"imageFile": "image.tar"
}
Binary file added test/fixtures/docker-image-project/image.tar
Binary file not shown.

0 comments on commit 084b14a

Please sign in to comment.