Permalink
Browse files

v0.0.1

  • Loading branch information...
0 parents commit 000a220e35571c5f28074240c759db9f7f2d50ea @tih-ra committed Nov 28, 2011
Showing with 366 additions and 0 deletions.
  1. +1 −0 .gitignore
  2. +98 −0 README.md
  3. +1 −0 index.js
  4. +245 −0 lib/alleup.js
  5. +21 −0 package.json
@@ -0,0 +1 @@
+.DS_Store
@@ -0,0 +1,98 @@
+Alleup
+=============
+
+Flexible way to resize and upload images to Amazon S3 or file system storages for Node.js. Possible to add different versions of the same file in cropped or resized variant.
+
+## Installation
+ $ npm install alleup
+
+## Quick Start
+
+1. **You need to create alleup configuration file with image variants and your storages**
+Example:
+ ```javascript
+ {
+ "variants": {
+ "resize": {
+ "mini" : "300x200",
+ "preview": "800x600"
+ },
+ "crop": {
+ "thumb": "200x200"
+ }
+ },
+
+ "storage": {
+ "aws": {
+ "key" : "AWS_KEY",
+ "secret" : "AWS_SECRET",
+ "bucket" : "AWS_BUCKET"
+ },
+ "dir": {
+ "path" : "./public/images/"
+ }
+ }
+ }
+
+2. **Now you can use Alleup**
+
+ ```javascript
+ var Alleup = require('alleup');
+ var alleup = new Alleup({storage : "aws", config_file: "path_to_alleup_config.json"})
+
+You can use `storage: 'aws'` for store files on Amazon S3 or `storage: 'dir'` for store files in filesystem
+
+**Upload example**
+ ```javascript
+ app.post('/upload', function(req, res) {
+ alleup.upload(req, res, function(err, file, res){
+
+ console.log("FILE UPLOADED: " + file);
+ // THIS YOU CAN SAVE FILE TO DATABASE FOR EXAMPLE
+ res.end();
+ });
+ });
+
+**Get file url example**
+ ```javascript
+ alleup.url(file, variant)
+`file` - The name of the file you uploaded, saved for example in database (`345621345.jpg`), `variant` - one of your image variants names from alleup_congig.json
+
+**Remove uploaded file example**
+ ```javascript
+ app.get('/delete', function(req, res) {
+ alleup.remove('1322506647.jpg', function(err) {
+ // THIS YOU CAN DELETE FILE FROM DATABASE FOR EXAMPLE
+ res.end();
+ });
+ };
+
+### Contribution
+Pull requests are welcome!!!
+### License
+(The MIT License)
+
+Copyright (c) 2011 Andriy Bazyuta <andriy.bazyuta@gmail.com>
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+'Software'), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+---
+### Author
+Andriy Bazyuta
@@ -0,0 +1 @@
+module.exports = require('./lib/alleup');
@@ -0,0 +1,245 @@
+var formidable = require('formidable'),
+ util = require('util'),
+ im = require('imagemagick'),
+ fs = require('fs'),
+ path = require('path'),
+ knox = require('knox');
+
+var config_file = './alleup.json',
+ config = {},
+ s3client = undefined,
+ uploaddir = undefined,
+ storage_type = undefined;
+
+
+var Alleup = exports = module.exports = function Alleup(options) {
+ config_file = (typeof options['config_file'] === 'undefined') ? config_file : options['config_file'];
+ storage_type = options['storage'];
+
+ this.loadConfig(config_file);
+
+ if ( typeof (config['storage']['aws'] || config['storage']['dir']) == 'undefined' )
+ throw new TypeError("No storage defined in alleup config");
+
+ for(storage in config['storage']) {
+ eval('this.' + storage + 'Setup')(config['storage'][storage]);
+ }
+
+
+};
+
+
+Alleup.prototype = {
+
+ url: function(file, version) {
+ var _file = this.genFileName( file, version );
+
+ return eval('this.' + storage_type + 'Url')(_file);
+ },
+
+ dirUrl: function(file) {
+ return uploaddir + file;
+ },
+
+ awsUrl: function(file) {
+ return s3client.url( file );
+ },
+
+
+ genFileName: function(file, version) {
+ return version + '_' + file;
+ },
+
+ remove: function(file, callback) {
+ var _resize = config['variants']['resize'];
+ var _crop = config['variants']['crop'];
+
+ for(version in _resize) {
+ eval('this.' + storage_type + 'Remove')( this.genFileName( file, version ), function(err) {
+ callback(err);
+ });
+ };
+
+ for(version in _crop) {
+ eval('this.' + storage_type + 'Remove')( this.genFileName( file, version ), function(err) {
+ callback(err);
+ });
+ };
+ return callback(null);
+ },
+
+ awsRemove: function(file, callback) {
+ s3client.deleteFile(file, function(err, res){
+ callback(err);
+ });
+ },
+
+ dirRemove: function(file, callback){
+ fs.unlink(uploaddir + file, function(err){
+ return callback(err);
+ });
+
+ },
+
+ upload: function(req, res, callback) {
+ var _this = this;
+ var form = new formidable.IncomingForm(),
+ files = [],
+ fields = [],
+ new_file = undefined;
+
+ //form.uploadDir = './tmp';
+
+ form
+ .on('field', function(field, value) {
+ fields.push([field, value]);
+ })
+ .on('file', function(field, file) {
+ files.push([field, file]);
+ new_file = file;
+
+ })
+ .on('end', function() {
+
+ //res.writeHead(200, {'content-type': 'text/plain'});
+ //res.write('received fields:\n\n '+util.inspect(fields));
+ //res.write('\n\n');
+ //res.end('received files:\n\n '+util.inspect(files));
+
+ _this.makeVariants(new_file, function(err, file){
+ callback(err, file, res);
+ });
+ });
+ form.parse(req);
+ },
+
+ awsSetup: function(options) {
+
+ s3client = knox.createClient({
+ key: options['key']
+ , secret: options['secret']
+ , bucket: options['bucket']
+ });
+ },
+
+ dirSetup: function(options) {
+
+ uploaddir = options['path'];
+ },
+
+
+ makeVariants: function(file, callback) {
+
+ var _this = this;
+
+ var _resize = config['variants']['resize'];
+ var _crop = config['variants']['crop'];
+ var new_file = Math.round(new Date().getTime()/1000.0);
+ var ext = this.setExtension(file['type']);
+ new_file += ext;
+
+ var i = 0;
+ for(prefix in _resize) {
+ i++;
+ this.imAction('im.resize', file, this.genFileName( new_file, prefix ) , _resize[prefix], function(err){
+
+ if (i == Object.keys(config.variants.resize).length ) {
+ i = 0;
+ for(prefix in _crop) {
+ i++;
+ var _callback = _this.imAction('im.crop', file, _this.genFileName( new_file, prefix ) , _crop[prefix], function(err){
+ if (i == Object.keys(config.variants.crop).length )
+ fs.unlink(file['path']);
+ callback(err, new_file);
+ });
+ };
+ };
+
+
+ });
+ };
+
+ },
+
+ pushToS3: function(sfile, dfile, content_type, callback) {
+
+ fs.readFile(sfile, function(err, buf){
+ var req = s3client.put(dfile, {
+ 'Content-Length': buf.length
+ , 'Content-Type': content_type
+ });
+ req.on('response', function(res){
+ if (200 == res.statusCode) {
+ fs.unlink(sfile);
+ callback(err);
+ }
+ });
+ req.end(buf);
+
+ });
+ },
+
+ loadConfig: function(resource) {
+ if (path.existsSync(resource)) {
+ try {
+ config = JSON.parse(fs.readFileSync(resource));
+ } catch (err) {
+ throw new Error("Could not parse JSON config at "+path.resolve(resource));
+ }
+ }
+ },
+
+ imAction: function(action, file, prefix, size, callback) {
+ var _this = this;
+
+
+ var dfile = prefix;
+ var tfile = (storage_type == 'dir') ? uploaddir + dfile : file['path'] + prefix;
+
+ eval(action)( this.imOptions(file, tfile, size), function(err, stdout, stderr){
+ if (storage_type == 'aws') {
+
+ _this.pushToS3(tfile, dfile, file['type'], function(err){
+ return callback(err);
+ });
+
+ } else {
+ return callback(err);
+ }
+ });
+
+ },
+
+ setExtension: function(content_type) {
+
+ switch(content_type) {
+ case 'image/jpeg':
+ var ext = '.jpg'
+ break;
+ case 'image/png':
+ var ext = '.png'
+ break;
+ case 'image/gif':
+ var ext = '.gif'
+ break;
+ };
+
+ return ext;
+
+ },
+
+ imOptions: function(file, tfile, size) {
+ var _size = size.split('x');
+ return options = {
+ srcPath: file['path'],
+ dstPath: tfile,
+ width: _size[0],
+ height: _size[1],
+ quality: 1
+ };
+ }
+
+
+
+
+};
@@ -0,0 +1,21 @@
+{
+ "author": "Andriy Bazuta <andriy.bazyuta@gmail.com> (http://andriy.bazyuta.me)",
+ "name": "alleup",
+ "description": "Flexible way to resize and upload images to Amazon S3 or file system storages",
+ "version": "0.0.1",
+ "keywords": ["upload", "image", "imagemagick", "amazon", "aws", "s3", "resize", "file"],
+ "homepage": "http://todo",
+ "repository": {
+ "type": "git",
+ "url": "git://todo"
+ },
+ "engines": {
+ "node": "~0.4.11"
+ },
+ "dependencies": {
+ "formidable": "~1.0.7",
+ "imagemagick": "~0.1.2",
+ "knox": "~0.0.9"
+ },
+ "devDependencies": {}
+}

0 comments on commit 000a220

Please sign in to comment.