Monday, July 21, 2014

Recursively npm uninstall all modules

How to recursively do a npm uninstall on all modules? 

I came across a problem where we updated our version of nodejs, then the suggestion was to remove all of the installed node modules of your project after upgrading and before doing a "npm install". I looked at the web and it seemed it is not supported by npm yet (at the time of this writing). Doing manual npm uninstall of all of our modules is a very daunting task.

So I created a powershell script to recursively loop all of the folders inside the node_module and execute a "npm uninstall" passing the folder name as parameter.

Here is the code.
$arr = Get-ChildItem .\node_modules| Where-Object {$_.PSIsContainer} | Foreach-Object {$_.Name}; for($i = 0; $i -le $arr.count -1; $i++) { if($arr[$i] -ne ".bin") { Invoke-Command -Script {npm uninstall $arr[$i]}}}
It first get all of the folder names under node_modules and store it in the $arr variable, then invoke-command on all items in the array.

So just open your powershell terminal and paste this code in your project folder. Please note that I have a condition to test if the $arr[$i] is not equal to ".bin", this is because my node_modules has this folder name which is not a node package - this was generated by our grunt task.

 Hope this helps!

Monday, July 7, 2014

NodeJs: Call API through proxy

How to call an API inside NodeJs through a proxy?

I came across a problem where our box (vagrant box) was configured in a way that we could not call any site (website or API) directly, we have to use our proxy.

So the solution I found was to use a tunnel npm module.

Below is a mocha test I created to test calling an API through a proxy:
var tunnel = require('tunnel');
var https = require('https');
var url = require('url');

describe('call api through proxy', function () {
    it('should be able to access http', function (done) {
        var inputToken = 'YOUR_INPUT_TOKEN'; // this should be from config/redis
        var accessToken = 'ACCESS_TOKEN';

        var urlParsed = url.parse(process.env.https_proxy); // get the proxy

// declare the tunnel
        var tunnelingAgent = tunnel.httpsOverHttp({
            proxy: {
                host: urlParsed.hostname,
                port: urlParsed.port
            }
        });

// FB option
        var options = {
            host: "graph.facebook.com",
            port: 443,
            path: '/debug_token?input_token=' + inputToken + '&access_token=' + accessToken,
            agent: tunnelingAgent,

        };
        var reqGet = https.get(options, function (res) {
            var chunk = '';
            res.on('data', function (d) {
                console.info('GET result:\n');
                chunk += d;
                process.stdout.write(d);
            });
            res.on('end', function () {
                var fbResponse = JSON.parse(chunk);
                console.log("Got response: ", fbResponse);
                done();
            });
        });

        reqGet.end();
        reqGet.on('error', function (e) {
            console.error(e);
        });
    });
});

Hope this helps!