Socket
Socket
Sign inDemoInstall

grunt-s3

Package Overview
Dependencies
Maintainers
1
Versions
14
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

grunt-s3 - npm Package Compare versions

Comparing version 0.2.0-alpha to 0.2.0-alpha.1

10

Gruntfile.js

@@ -1,7 +0,7 @@

var path = require("path");
var path = require('path');
module.exports = function(grunt) {
module.exports = function (grunt) {
grunt.initConfig({
jshint : ['tasks/**/*.js'],
jshint: ['tasks/**/*.js'],
nodeunit: {

@@ -30,4 +30,4 @@ all: ['test/upload.js', 'test/download.js', 'test/s3Task.js']

upload: [{
src: path.join(process.cwd(), "test", "files", "**", "*.txt"),
rel: path.join(process.cwd(), "test", "files")
src: path.join(process.cwd(), 'test', 'files', '**', '*.txt'),
rel: path.join(process.cwd(), 'test', 'files')
}]

@@ -34,0 +34,0 @@ }

@@ -1,5 +0,5 @@

{
{
"name": "grunt-s3",
"description": "A grunt task to automate moving files to/from Amazon S3.",
"version": "0.2.0-alpha",
"version": "0.2.0-alpha.1",
"author": "Aaron Forsander (https://github.com/pifantastic)",

@@ -37,3 +37,4 @@ "homepage": "https://github.com/pifantastic/grunt-s3",

"knox": "0.6.x",
"mime": "~1.2.5"
"mime": "~1.2.5",
"temporary": "0.0.5"
},

@@ -40,0 +41,0 @@ "devDependencies": {

@@ -154,3 +154,3 @@ [![Build Status](https://secure.travis-ci.org/pifantastic/grunt-s3.png?branch=master)](https://travis-ci.org/pifantastic/grunt-s3)

grunt.initConfig({
aws: '<json:grunt-aws.json>',
aws: grunt.file.readJSON('grunt-aws.json'),
s3: {

@@ -177,4 +177,10 @@ key: '<%= aws.key %>',

### grunt.helper('s3.put', src, dest, options)
Helpers have been removed from Grunt 0.4 to access these methods directly. You can now require the s3 library files directly like so:
`var s3 = require('grunt-s3').helpers;`
Make sure you explicitly pass the options into the method. If you've used `grunt.initConfig()` you can use `grunt.config.get('s3')` to access them.
### s3.upload(src, dest, options)
Upload a file to s3. Returns a Promises/J-style Deferred object.

@@ -198,3 +204,3 @@

### grunt.helper('s3.pull', src, dest, options)
### s3.download(src, dest, options)
Download a file from s3. Returns a Promises/J-style Deferred object.

@@ -214,3 +220,3 @@

### grunt.helper('s3.delete', src, options)
### s3.delete(src, options)

@@ -232,3 +238,3 @@ Delete a file from s3. Returns a Promises/J-style Deferred object.

```javascript
var upload = grunt.helper('s3.put', 'dist/my-app-1.0.0.tar.gz', 'archive/my-app-1.0.0.tar.gz');
var upload = s3.upload('dist/my-app-1.0.0.tar.gz', 'archive/my-app-1.0.0.tar.gz');

@@ -246,6 +252,6 @@ upload

var download = grunt.helper('s3.pull', 'dist/my-app-0.9.9.tar.gz', 'local/my-app-0.9.9.tar.gz');
var download = s3.download('dist/my-app-0.9.9.tar.gz', 'local/my-app-0.9.9.tar.gz');
download.done(function() {
grunt.helper('s3.delete', 'dist/my-app-0.9.9.tar.gz');
s3.delete('dist/my-app-0.9.9.tar.gz');
});

@@ -252,0 +258,0 @@

@@ -20,2 +20,3 @@ /*jshint esnext:true*/

const deferred = require('underscore.deferred');
var Tempfile = require('temporary/lib/file');

@@ -49,4 +50,4 @@ // Local

exports.init = function (grunt) {
var async = grunt.util.async,
_ = grunt.util._;
var async = grunt.util.async;
var _ = grunt.util._;

@@ -155,5 +156,4 @@ _.mixin(deferred);

if (options.gzip && gzipExclude.indexOf(path.extname(src)) === -1) {
headers['Content-Encoding'] = 'gzip';
headers['Content-Type'] = mime.lookup(src);
headers['Content-Type'] = headers['Content-Type'] || mime.lookup(src);

@@ -165,11 +165,5 @@ var charset = mime.charsets.lookup(headers['Content-Type'], null);

// Determine a unique temp file name.
var tmp = src + '.gz';
var incr = 0;
while (existsSync(tmp)) {
tmp = src + '.' + (incr++) + '.gz';
}
var tmp = new Tempfile();
var input = fs.createReadStream(src);
var output = fs.createWriteStream(tmp);
var output = fs.createWriteStream(tmp.path);

@@ -183,6 +177,6 @@ // Gzip the file and upload when done.

// Update the src to point to the newly created .gz file.
src = tmp;
src = tmp.path;
upload(function (err, msg) {
// Clean up the temp file.
fs.unlinkSync(tmp);
tmp.unlinkSync();

@@ -314,3 +308,3 @@ if (err) {

'Content-Length': 0,
'x-amz-copy-source' : src
'x-amz-copy-source': src
};

@@ -317,0 +311,0 @@

@@ -1,147 +0,148 @@

var path = require("path");
var path = require('path');
var grunt = require("grunt"),
_ = grunt.util._,
async = grunt.util.async;
var grunt = require('grunt');
var _ = grunt.util._;
var async = grunt.util.async;
var S3Task = function(origTask, s3) {
this._origTask = origTask;
this.s3 = s3;
var S3Task = function (origTask, s3) {
this._origTask = origTask;
this.s3 = s3;
};
S3Task.prototype = {
run: function() {
var self = this,
s3 = this.s3;
run: function () {
var self = this;
var s3 = this.s3;
var done = this._origTask.async();
var config = this.getConfig();
var transfers = [];
var done = this._origTask.async();
if (config.debug) {
grunt.log.writeln('Running in debug mode, no transfers will be made'.yellow);
grunt.log.writeln();
}
var config = this.getConfig();
config.upload.forEach(function (upload) {
var uploadFiles = self._parseUploadFiles(upload, config);
var transfers = [];
uploadFiles.forEach(function (uploadFile) {
transfers.push(s3.upload.bind(s3, uploadFile.file, uploadFile.dest, uploadFile.upload));
});
});
if (config.debug) {
grunt.log.writeln("Running in debug mode, no transfers will be made".yellow);
grunt.log.writeln();
}
config.download.forEach(function (download) {
transfers.push(s3.download.bind(s3,download.src, download.dest, download));
});
config.upload.forEach(function(upload) {
var uploadFiles = self._parseUploadFiles(upload, config);
config.del.forEach(function (del) {
transfers.push(s3.del.bind(s3,del.src, del));
});
uploadFiles.forEach(function(uploadFile) {
transfers.push(s3.upload.bind(s3, uploadFile.file, uploadFile.dest, uploadFile.upload));
});
});
config.copy.forEach(function (copy) {
transfers.push(s3.copy.bind(s3,copy.src, copy.dest, copy));
});
config.download.forEach(function(download) {
transfers.push(s3.download.bind(s3,download.src, download.dest, download));
});
var total = transfers.length;
var errors = 0;
config.del.forEach(function(del) {
transfers.push(s3.del.bind(s3,del.src, del));
});
var eachTransfer = config.maxOperations > 0 ?
async.forEachLimit.bind(async,transfers,config.maxOperations) :
async.forEach.bind(async,transfers);
config.copy.forEach(function(copy) {
transfers.push(s3.copy.bind(s3,copy.src, copy.dest, copy));
});
eachTransfer(function (transferFn, completed){
var transfer = transferFn();
var total = transfers.length;
var errors = 0;
transfer.done(function (msg) {
grunt.log.ok(msg);
completed();
});
var eachTransfer = config.maxOperations > 0 ?
async.forEachLimit.bind(async,transfers,config.maxOperations)
: async.forEach.bind(async,transfers);
transfer.fail(function (msg) {
grunt.log.error(msg);
++errors;
completed();
});
eachTransfer(function(transferFn, completed){
var transfer = transferFn();
}, function () {
done(!errors);
});
},
transfer.done(function(msg) {
grunt.log.ok(msg);
completed();
});
_parseUploadFiles: function (upload, config) {
// Expand list of files to upload.
var files = grunt.file.expand({ filter: 'isFile' }, upload.src);
var destPath = grunt.template.process(upload.dest || '');
transfer.fail(function(msg) {
grunt.log.error(msg);
++errors;
completed();
});
return _.map(files, function (file) {
file = path.resolve(file);
upload.src = path.resolve(grunt.template.process(upload.src));
},function(){
// we're all done.
done(!errors);
});
},
// Put the key, secret and bucket information into the upload for knox
_.extend(upload, config);
_parseUploadFiles: function(upload, config) {
// Expand list of files to upload.
var files = grunt.file.expand({ filter: "isFile" }, upload.src),
destPath = grunt.template.process(upload.dest || "");
// If there is only 1 file and it matches the original file wildcard,
// we know this is a single file transfer. Otherwise, we need to build
// the destination.
var dest;
if (files.length === 1 && file === upload.src) {
dest = destPath;
}
else {
if (upload.rel) {
dest = path.join(destPath, path.relative(grunt.file.expand({ filter: "isDirectory" }, upload.rel)[0], file));
}
else {
dest = path.join(destPath, path.basename(file));
}
}
return _.map(files, function(file) {
file = path.resolve(file);
upload.src = path.resolve(grunt.template.process(upload.src));
if (config.encodePaths === true) {
dest = encodeURIComponent(dest);
}
// Put the key, secret and bucket information into the upload for knox
_.extend(upload, config);
dest = dest.replace(/\\/g, '/');
// If there is only 1 file and it matches the original file wildcard,
// we know this is a single file transfer. Otherwise, we need to build
// the destination.
var dest;
if (files.length === 1 && file === upload.src) {
dest = destPath;
}
else {
if (upload.rel) {
dest = path.join(destPath, path.relative(grunt.file.expand({ filter: "isDirectory" }, upload.rel)[0], file));
}
else {
dest = path.join(destPath, path.basename(file));
}
}
return {
file: file,
dest: dest,
upload: upload
};
});
},
if(config.encodePaths === true) {
dest = encodeURIComponent(dest);
}
/**
* Return the config, allow for arbitrary options that don't originate
* from grunt.
*
* @param {Object=} optOptions optionally define an options object.
* @param {Object=} optData optionally define file actions,
* will ignore defaults.
* @return {Object} A normalized configuration.
*/
getConfig: function (optOptions, optData) {
// Grab the options for this task.
var opts = optOptions || this._origTask.options();
return {file: file, dest: dest, upload: upload};
});
},
var defaultOpts = {
key: process.env.AWS_ACCESS_KEY_ID,
secret: process.env.AWS_SECRET_ACCESS_KEY,
debug: false,
maxOperations: 0,
encodePaths: false
};
/**
* Return the config, allow for arbitrary options that don't originate
* from grunt.
*
* @param {Object=} optOptions optionally define an options object.
* @param {Object=} optData optionally define file actions,
* will ignore defaults.
* @return {Object} A normalized configuration.
*/
getConfig: function(optOptions, optData) {
// Grab the options for this task
// Grab the actions to perform from the task data, default to empty arrays
var fileActions = optData || this._origTask.data;
var defaultFileActions = {
upload: [],
download: [],
del: [],
copy: []
};
var opts = optOptions || this._origTask.options();
var defaultOpts = {
key : process.env.AWS_ACCESS_KEY_ID,
secret : process.env.AWS_SECRET_ACCESS_KEY,
debug: false,
maxOperations: 0,
encodePaths: false
};
// Grab the actions to perform from the task data, default to empty arrays
var fileActions = optData || this._origTask.data;
var defaultFileActions = {
upload: [],
download: [],
del: [],
copy: []
};
// Combine the options and fileActions as the config
return _.extend({}, defaultOpts, defaultFileActions, opts, fileActions);
}
// Combine the options and fileActions as the config
return _.extend({}, defaultOpts, defaultFileActions, opts, fileActions);
}
};
module.exports = S3Task;

@@ -14,9 +14,9 @@ /*jshint esnext:true*/

module.exports = function (grunt) {
var s3 = require('./lib/s3');
var s3 = require('./lib/s3');
const S3Task = require('./lib/S3Task');
var exportFn = function (grunt) {
var S3Task = require('./lib/S3Task');
// if grunt is not provided, then expose internal API
if ('object' !== typeof(grunt)) {
// If grunt is not provided, then expose internal API.
if (typeof grunt !== 'object') {
return {

@@ -41,1 +41,7 @@ s3: s3,

};
exportFn.init = function (grunt) {
return s3.init(grunt);
};
module.exports = exportFn;
var path = require('path');
var grunt = require('grunt');
var s3 = require('../tasks/lib/s3').init(grunt);
var S3Task = require("../tasks/lib/S3Task");
var S3Task = require('../tasks/lib/S3Task');
var deferred = require('underscore.deferred');

@@ -11,102 +11,96 @@

var s3Config = grunt.config("s3"),
config = _.extend({}, s3Config.options, s3Config.test_S3Task.options);
var s3Config = grunt.config('s3');
var config = _.extend({}, s3Config.options, s3Config.test_S3Task.options);
var makeMockTask = function(taskDef) {
// A fake grunt task
// TODO: Figure out if grunt has a way to mock this.
var mockTask = {
_asyncCalls: 0,
async: function() {
this._asyncCalls++;
return function(result) {
taskDef.resolve(result);
};
},
options: function(defaults) {
return _.defaults({}, config, defaults);
},
data: s3Config.test_S3Task
};
var makeMockTask = function (taskDef) {
// A fake grunt task
// TODO: Figure out if grunt has a way to mock this.
var mockTask = {
_asyncCalls: 0,
async: function () {
this._asyncCalls++;
return function (result) {
taskDef.resolve(result);
};
},
options: function (defaults) {
return _.defaults({}, config, defaults);
},
data: s3Config.test_S3Task
};
// Remove the options from the data.
mockTask.data.options = null;
// Remove the options from the data.
mockTask.data.options = null;
return mockTask;
}
return mockTask;
};
module.exports = {
"run": function(test) {
var taskDef = new _.Deferred(),
asyncCalls = 0;
run: function (test) {
var taskDef = new _.Deferred();
var asyncCalls = 0;
var mockTask = makeMockTask(taskDef);
var task = new S3Task(mockTask, s3);
// Some vars to hold upload information
var uploadOrig = s3.upload,
uploadFiles = [],
uploadCalls = 0;
var uploadOrig = s3.upload;
var uploadFiles = [];
var uploadCalls = 0;
// Fake the upload functionality; it's tested elsewhere
s3.upload = function(file, dest, opts) {
uploadCalls++;
// Fake the upload functionality; it's tested elsewhere.
s3.upload = function (file, dest, opts) {
uploadCalls++;
var def = new _.Deferred();
var def = new _.Deferred();
uploadFiles.push(dest);
uploadFiles.push(dest);
setTimeout(function() {
def.resolve();
}, 10);
setTimeout(function () {
def.resolve();
}, 10);
return def.promise();
return def.promise();
};
// Wait for the run() call to complete then test activity
// Wait for the run() call to complete then test activity.
taskDef.then(function(result) {
test.equal(mockTask._asyncCalls, 1, "1 async() call");
test.equal(uploadFiles.length, 5, "5 uploaded files");
test.equal(uploadFiles[0], "a.txt", "Correct rel path on uploaded file 1");
test.equal(uploadFiles[4], "subdir/d.txt", "Correct rel path for subdir file");
test.equal(mockTask._asyncCalls, 1, '1 async() call');
test.equal(uploadFiles.length, 5, '5 uploaded files');
test.equal(uploadFiles[0], 'a.txt', 'Correct rel path on uploaded file 1');
test.equal(uploadFiles[4], 'subdir/d.txt', 'Correct rel path for subdir file');
test.ok(result, 'Completed');
}, function (err) {
test.ok(false, "Error'd");
})
.always(function () {
s3.upload = uploadOrig;
test.done();
});
test.ok(result, "Completed");
}, function(err) {
test.ok(false, "Error'd");
})
.always(function() {
s3.upload = uploadOrig;
test.done();
});
task.run();
},
"_parseUploadFiles": function(test) {
_parseUploadFiles: function (test) {
var mockTask = makeMockTask();
var task = new S3Task(mockTask, s3);
var config = task.getConfig();
test.equal(config.upload.length, 1, "Has upload to parse");
test.equal(config.upload.length, 1, 'Has upload to parse');
var uploadFiles = task._parseUploadFiles(config.upload[0], config);
test.equal(uploadFiles.length, 5, "Has 5 files to be uploaded");
test.equal(uploadFiles.length, 5, 'Has 5 files to be uploaded');
// File paths in root
test.equal(uploadFiles[0].file, path.join(process.cwd(), "test", "files", "a.txt"));
test.equal(uploadFiles[1].file, path.join(process.cwd(), "test", "files", "b.txt"));
test.equal(uploadFiles[0].file, path.join(process.cwd(), 'test', 'files', 'a.txt'));
test.equal(uploadFiles[1].file, path.join(process.cwd(), 'test', 'files', 'b.txt'));
// File paths in subdir
test.equal(uploadFiles[3].file, path.join(process.cwd(), "test", "files", "subdir", "c.txt"));
test.equal(uploadFiles[4].file, path.join(process.cwd(), "test", "files", "subdir", "d.txt"));
test.equal(uploadFiles[3].file, path.join(process.cwd(), 'test', 'files', 'subdir', 'c.txt'));
test.equal(uploadFiles[4].file, path.join(process.cwd(), 'test', 'files', 'subdir', 'd.txt'));
// Destinations don't have full path, but have subdir
test.equal(uploadFiles[0].dest, "a.txt");
test.equal(uploadFiles[1].dest, "b.txt");
test.equal(uploadFiles[3].dest, path.join("subdir", "c.txt"));
test.equal(uploadFiles[4].dest, path.join("subdir", "d.txt"));
test.equal(uploadFiles[0].dest, 'a.txt');
test.equal(uploadFiles[1].dest, 'b.txt');
test.equal(uploadFiles[3].dest, path.join('subdir', 'c.txt'));
test.equal(uploadFiles[4].dest, path.join('subdir', 'd.txt'));

@@ -116,4 +110,3 @@ test.done();

"getConfig": function (test) {
getConfig: function (test) {
// A fake grunt task

@@ -124,29 +117,28 @@ // TODO: Figure out if grunt has a way to mock this.

var oldVal = {
key: process.env.AWS_ACCESS_KEY_ID,
secret: process.env.AWS_SECRET_ACCESS_KEY
key: process.env.AWS_ACCESS_KEY_ID,
secret: process.env.AWS_SECRET_ACCESS_KEY
};
// Making sure we choose the options over the process key
process.env.AWS_ACCESS_KEY_ID = "testid";
process.env.AWS_SECRET_ACCESS_KEY = "secret";
process.env.AWS_ACCESS_KEY_ID = 'testid';
process.env.AWS_SECRET_ACCESS_KEY = 'secret';
var task = new S3Task(mockTask, s3);
var config = task.getConfig();
// Test the custom things first
test.equal(config.key, s3Config.options.key, "Key");
test.equal(config.secret, s3Config.options.secret, "Secret");
test.equal(config.debug, false, "Debug");
test.equal(config.key, s3Config.options.key, 'Key');
test.equal(config.secret, s3Config.options.secret, 'Secret');
test.equal(config.debug, false, 'Debug');
// Test the data actions
test.equal(config.upload.length, 1, "Upload length");
test.equal(config.upload.length, 1, 'Upload length');
// Testing things that are only in the default options.
test.equal(config.bucket, s3Config.options.bucket, "Bucket");
test.equal(config.endpoint, s3Config.options.endpoint, "Endpoint");
test.equal(config.bucket, s3Config.options.bucket, 'Bucket');
test.equal(config.endpoint, s3Config.options.endpoint, 'Endpoint');
// Newly added options
test.equal(config.maxOperations, 0, "Defaults max operations to 0");
test.equal(config.encodePaths, false, "Defaults encodePaths to false");
test.equal(config.maxOperations, 0, 'Defaults max operations to 0');
test.equal(config.encodePaths, false, 'Defaults encodePaths to false');

@@ -153,0 +145,0 @@ // Be a good citizen and reset these.

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc