Skip to content

Instantly share code, notes, and snippets.

@getify
Forked from JedWatson/async.js
Last active January 3, 2016 18:29

Revisions

  1. getify revised this gist Jan 19, 2014. 1 changed file with 44 additions and 47 deletions.
    91 changes: 44 additions & 47 deletions async.js
    Original file line number Diff line number Diff line change
    @@ -9,62 +9,59 @@
    // uuid = require('node-uuid')
    // redis.client = require('node-redis').createClient()

    var transform = function(contents, done) {
    var transform = function( contents, done ) {

    // generate a new auth id for the user and store it in redis with a ttl of 1 hour

    var authExpiry = 60 * 60 * 1000, // 1 hour
    authId = uuid.v4(), // unique request to ID the user
    authKey = 'file:auth:' + authId;

    redis.client.set(authKey, JSON.stringify({
    redis.client.set( authKey, JSON.stringify( {
    userId: req.user.id
    }));
    redis.client.expire(authKey, authExpiry);

    // function to send the secure file paths back to the user

    var sendContents = function(err, files) {
    if (err) return handleError(err);
    contents.files = files;
    done(contents);
    }
    } ) );
    redis.client.expire( authKey, authExpiry );

    // loop through the files array, caching each in redis (if it doens't exist)
    // and turning the file path into {authId}/{fileId}

    // async.map executes in parallel, see https://github.com/caolan/async#map
    // async.mapLimit and async.mapSeries are also available.

    async.map(contents.files, function(file, next) {

    // fileIds are cached in redis with the file path as the key
    var lookupKey = 'file:path:' + file.path;

    redis.client.get(lookupKey, function(err, fileId) {

    // bail if there was an error
    if (err) return next(err);

    if (fileId) {
    // if we found a fileId, it is already in the cache.
    // convert it to a string and use it.
    fileId = fileId.toString();
    } else {
    // if we didn't, create a new id and cache the file details
    fileId = uuid.v4();
    redis.client.set('file:id:' + fileId, JSON.stringify(file));
    redis.client.set(lookupKey, fileId);
    }

    // rewrite the path of the file to {authId}/{fileId}
    file.path = authId + '/' + fileId;

    // continue
    next(false, file);

    });

    }, sendContents);


    ASQ()
    .gate.apply(
    null,
    // create an array of segments for the parallel gate()
    contents.files.map(function( file ){
    return function __segment__( done ) {
    // fileIds are cached in redis with the file path as the key
    var lookupKey = 'file:path:' + file.path;
    var sq = ASQ();

    redis.client.get( lookupKey, sq.errfcb() );

    sq.val(function( fileId ){
    if (fileId) {
    // if we found a fileId, it is already in the cache.
    // convert it to a string and use it.
    fileId = fileId.toString();
    } else {
    // if we didn't, create a new id and cache the file details
    fileId = uuid.v4();
    redis.client.set( 'file:id:' + fileId, JSON.stringify(file) );
    redis.client.set( lookupKey, fileId );
    }

    // rewrite the path of the file to {authId}/{fileId}
    file.path = authId + '/' + fileId;

    return file;
    })
    .pipe( done );
    };
    })
    )
    .val(function(){
    // `arguments` is an array of all the `file` objects
    contents.files = [].slice.call( arguments );
    done( contents ); // NOTE: not asynquence's `done` :)
    })
    .or( handleError );
    }
  2. @JedWatson JedWatson revised this gist Jan 19, 2014. 1 changed file with 3 additions and 0 deletions.
    3 changes: 3 additions & 0 deletions async.js
    Original file line number Diff line number Diff line change
    @@ -33,6 +33,9 @@ var transform = function(contents, done) {
    // loop through the files array, caching each in redis (if it doens't exist)
    // and turning the file path into {authId}/{fileId}

    // async.map executes in parallel, see https://github.com/caolan/async#map
    // async.mapLimit and async.mapSeries are also available.

    async.map(contents.files, function(file, next) {

    // fileIds are cached in redis with the file path as the key
  3. @JedWatson JedWatson created this gist Jan 19, 2014.
    67 changes: 67 additions & 0 deletions async.js
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,67 @@
    // This function takes a contents object with a files array.
    // The goal is to cache each file details in redis then replace
    // the file's path with a secure, obscured url.

    // Finally the contents object is returned with the updated array
    // in place of the old one.

    // async = require('async')
    // uuid = require('node-uuid')
    // redis.client = require('node-redis').createClient()

    var transform = function(contents, done) {

    // generate a new auth id for the user and store it in redis with a ttl of 1 hour

    var authExpiry = 60 * 60 * 1000, // 1 hour
    authId = uuid.v4(), // unique request to ID the user
    authKey = 'file:auth:' + authId;

    redis.client.set(authKey, JSON.stringify({
    userId: req.user.id
    }));
    redis.client.expire(authKey, authExpiry);

    // function to send the secure file paths back to the user

    var sendContents = function(err, files) {
    if (err) return handleError(err);
    contents.files = files;
    done(contents);
    }

    // loop through the files array, caching each in redis (if it doens't exist)
    // and turning the file path into {authId}/{fileId}

    async.map(contents.files, function(file, next) {

    // fileIds are cached in redis with the file path as the key
    var lookupKey = 'file:path:' + file.path;

    redis.client.get(lookupKey, function(err, fileId) {

    // bail if there was an error
    if (err) return next(err);

    if (fileId) {
    // if we found a fileId, it is already in the cache.
    // convert it to a string and use it.
    fileId = fileId.toString();
    } else {
    // if we didn't, create a new id and cache the file details
    fileId = uuid.v4();
    redis.client.set('file:id:' + fileId, JSON.stringify(file));
    redis.client.set(lookupKey, fileId);
    }

    // rewrite the path of the file to {authId}/{fileId}
    file.path = authId + '/' + fileId;

    // continue
    next(false, file);

    });

    }, sendContents);

    }