diff --git a/src/docker.js b/src/docker.js index da451ced3..611dbcd5b 100644 --- a/src/docker.js +++ b/src/docker.js @@ -118,36 +118,60 @@ function ping(callback) { }); } +function getRegistryConfig(image, callback) { + const parts = image.split('/'); + if (parts.length === 2) return callback(null, null); // public docker registry + + settings.getRegistryConfig(function (error, registryConfig) { + if (error) return callback(error); + + // https://github.com/apocas/dockerode#pull-from-private-repos + const auth = { + username: registryConfig.username, + password: registryConfig.password, + auth: registryConfig.auth || '', // the auth token at login time + email: registryConfig.email || '', + serveraddress: registryConfig.serverAddress + }; + + callback(null, auth); + }); +} + function pullImage(manifest, callback) { var docker = exports.connection; - // Use docker CLI here to support downloading of private repos. for dockerode, we have to use - // https://github.com/apocas/dockerode#pull-from-private-repos - docker.pull(manifest.dockerImage, function (error, stream) { - if (error) return callback(new BoxError(BoxError.DOCKER_ERROR, 'Unable to pull image. Please check the network or if the image needs authentication. statusCode: ' + error.statusCode)); + getRegistryConfig(manifest.dockerImage, function (error, authConfig) { + if (error) return callback(error); - // https://github.com/dotcloud/docker/issues/1074 says each status message - // is emitted as a chunk - stream.on('data', function (chunk) { - var data = safe.JSON.parse(chunk) || { }; - debug('pullImage %s: %j', manifest.id, data); + debug(`pullImage: will pull ${manifest.dockerImage}. auth: ${authConfig ? 'yes' : 'no'}`); - // The data.status here is useless because this is per layer as opposed to per image - if (!data.status && data.error) { - debug('pullImage error %s: %s', manifest.id, data.errorDetail.message); - } - }); + docker.pull(manifest.dockerImage, { authconfig: authConfig }, function (error, stream) { + if (error) return callback(new BoxError(BoxError.DOCKER_ERROR, 'Unable to pull image. Please check the network or if the image needs authentication. statusCode: ' + error.statusCode)); - stream.on('end', function () { - debug('downloaded image %s of %s successfully', manifest.dockerImage, manifest.id); + // https://github.com/dotcloud/docker/issues/1074 says each status message + // is emitted as a chunk + stream.on('data', function (chunk) { + var data = safe.JSON.parse(chunk) || { }; + debug('pullImage %s: %j', manifest.id, data); - callback(null); - }); + // The data.status here is useless because this is per layer as opposed to per image + if (!data.status && data.error) { + debug('pullImage error %s: %s', manifest.id, data.errorDetail.message); + } + }); - stream.on('error', function (error) { - debug('error pulling image %s of %s: %j', manifest.dockerImage, manifest.id, error); + stream.on('end', function () { + debug('downloaded image %s of %s successfully', manifest.dockerImage, manifest.id); - callback(new BoxError(BoxError.DOCKER_ERROR, error.message)); + callback(null); + }); + + stream.on('error', function (error) { + debug('error pulling image %s of %s: %j', manifest.dockerImage, manifest.id, error); + + callback(new BoxError(BoxError.DOCKER_ERROR, error.message)); + }); }); }); }