Skip to content

Commit

Permalink
Build parent images checking the Dockerfile directive. Fixes makeusab…
Browse files Browse the repository at this point in the history
  • Loading branch information
anthony-o committed Aug 20, 2014
1 parent c8ecc7d commit 60fe93d
Showing 1 changed file with 54 additions and 26 deletions.
80 changes: 54 additions & 26 deletions lib/decking.js
Original file line number Diff line number Diff line change
Expand Up @@ -169,44 +169,72 @@ Decking.prototype._build = function(image, done) {
}

var targetPath = target + "/Dockerfile";
this.logger.log("Building image " + image + " from " + targetPath);

// @TODO for now, always assume we want to build from a Dockerfile
// @TODO need a lot of careful validation here
var readStream = fs.createReadStream(targetPath);
var writeStream = fs.createWriteStream("./Dockerfile");
var self = this;
var buildDep = false;

// ensure we don't try and create the tarball until the local Dockerfile exists
writeStream.on("close", function() {
var options = {t: image};
if(self.hasArg("--no-cache")) {
self.logger.log("Not using image cache");
options.nocache = true;
if(self.hasArg("--no-dependencies")) {
self.logger.log("Not building dependencies");
} else {
// Detecting local dependency
var dockerfileContent = fs.readFileSync(targetPath);
var fromRe = /^\s*from\s*(\S*)/i;
var fromMatch = fromRe.exec(dockerfileContent);
if (fromMatch) {
var dependency = fromMatch[1];
if (this.config.images[dependency]) {
// the dependency is declared in the local images, let's build that one first
buildDep = true;
self.logger.log("Found dependency : " + dependency);
self._build(dependency, function(err) {
if (err) return done(err);
continueFn();
});
}
}
}

self.logger.log("Uploading compressed context...");
if (!buildDep) continueFn();

// @TODO allow user to specifiy --exclude params to avoid unnecessarily huge tarballs
var tar = child_process.spawn("tar", ["-c", "-", "./"]);
function continueFn() {
self.logger.log("Building image " + image + " from " + targetPath);

return self.docker.buildImage(tar.stdout, options, function(err, res) {
fs.unlink("./Dockerfile", function(err) {
if(err) return self.logger.log("[WARN] Could not remove Dockerfile");
});
if(err) return done(err);
if(res.headers["content-type"] === "application/json") {
res.pipe(JSONStream.parse("stream")).pipe(process.stdout);
} else {
// we don't need an if/else but let's keep it for clarity; it'd be too easy to
// skim-read the code and misinterpret the first pipe otherwise
res.pipe(process.stdout);
var readStream = fs.createReadStream(targetPath);
var writeStream = fs.createWriteStream("./Dockerfile");

// ensure we don't try and create the tarball until the local Dockerfile exists
writeStream.on("close", function() {
var options = {t: image};
if(self.hasArg("--no-cache")) {
self.logger.log("Not using image cache");
options.nocache = true;
}
return res.on("end", done);

self.logger.log("Uploading compressed context...");

// @TODO allow user to specifiy --exclude params to avoid unnecessarily huge tarballs
var tar = child_process.spawn("tar", ["-c", "-", "./"]);

return self.docker.buildImage(tar.stdout, options, function(err, res) {
fs.unlink("./Dockerfile", function(err) {
if(err) return self.logger.log("[WARN] Could not remove Dockerfile");
});
if(err) return done(err);
if(res.headers["content-type"] === "application/json") {
res.pipe(JSONStream.parse("stream")).pipe(process.stdout);
} else {
// we don't need an if/else but let's keep it for clarity; it'd be too easy to
// skim-read the code and misinterpret the first pipe otherwise
res.pipe(process.stdout);
}
return res.on("end", done);
});
});
});

readStream.pipe(writeStream);
readStream.pipe(writeStream);
}
};

// ----------
Expand Down

0 comments on commit 60fe93d

Please sign in to comment.