Browser-sync: Replace localtunnel with ngrok

Created on 8 Jul 2014  Â·  25Comments  Â·  Source: BrowserSync/browser-sync

Through previous testing, ngrok appears to be a lot more reliable than localtunnel. Localtunnel even states that we should use ngrok instead.

Most helpful comment

This issue should reopen or localtunnel has to be removed as an option...

All 25 comments

We don't use that lib.

We use https://github.com/defunctzombie/localtunnel - which I've not had any problems with personally and seems to be well supported/maintained.

Is this a simple mix-up, or have you had problems with the the BrowserSync tunnel?

Both I think haha. Naturally I mixed up the two localtunnel repositories, however I am having some trouble with localtunnel on BrowserSync: getting a 502 error after a certain amount of time whilst running node-simplecrawler on the page. Nevermind this issue though.

@shakyShane localtunnel.me is down most of the time with 502 Bad Gateway error, I think it is a good idea to replace it with ngrok as asap, or browser-sync tunnel functionality won't be usable.

Please check this issue defunctzombie/localtunnel-server#13 on localtunnel.

@code-guru - yeah I agree, localtunnel has become unreliable.

I'm not able to install rc8, while I'm able to install rc7

npm ERR! [email protected] postinstall: `node ./postinstall.js`
npm ERR! Exit status 8
npm ERR! 
npm ERR! Failed at the [email protected] postinstall script.
npm ERR! This is most likely a problem with the ngrok package,
npm ERR! not with npm itself.
npm ERR! Tell the author that this fails on your system:
npm ERR!     node ./postinstall.js
npm ERR! You can get their info via:
npm ERR!     npm owner ls ngrok
npm ERR! There is likely additional logging output above.

npm ERR! System Linux 3.16.0-30-generic
npm ERR! command "/usr/bin/node" "/usr/bin/npm" "i"
npm ERR! cwd /home/testyo/repos/frontend-repo/code
npm ERR! node -v v0.10.36
npm ERR! npm -v 1.4.28
npm ERR! code ELIFECYCLE
npm ERR! not ok code 0

I don't know if I should report it here or not? The problem is probably that we're behind a proxy.

ngrok - Downloading newest binary...
|
events.js:72
        throw er; // Unhandled 'error' event
              ^
Error: CERT_UNTRUSTED
    at SecurePair.<anonymous> (tls.js:1381:32)
    at SecurePair.emit (events.js:92:17)
    at SecurePair.maybeInitFinished (tls.js:980:10)
    at CleartextStream.read [as _read] (tls.js:472:13)
    at CleartextStream.Readable.read (_stream_readable.js:341:10)
    at EncryptedStream.write [as _write] (tls.js:369:25)
    at doWrite (_stream_writable.js:226:10)
    at writeOrBuffer (_stream_writable.js:216:5)
    at EncryptedStream.Writable.write (_stream_writable.js:183:11)
    at write (_stream_readable.js:602:24)

Passing a plain string to tunnel now breaks with the following error:

 Expected Array or iterable object of [k, v] entries, or keyed object: %tunnelstring%

Anybody else running across this issue, try passing the following object to tunnel:

{ authtoken: "ngrok-key", subdomain: "subdomain" }

Heyo! Do you have plans to include the ngrok support again? I have some 502 errors with localtunnel.me. But only for some files which is really annoying:

screenshot from 2015-03-04 16 54 48

@Saschlong As you can probably tell from this thread, I did try to include ngrok - but downloading the binary (it's a Go project) was proving even more unreliable that localtunnel is. Ultimately I cannot compromise install for something not _essential_ to BrowserSync.

That being said, you can easily integrate ngrok manually

var ngrok = require('ngrok');
var browserSync = require('browser-sync')
browserSync({
    server: "./app"
}, function (err, bs) {
   ngrok.connect(bs.options.get('port'), function (err, url) {
      // https://757c1652.ngrok.com -> 127.0.0.1:8080  
   }); 
});

Ah, ok. That's a shame. But thanks a lot for the tut :-)

@shakyShane

I'm not following exactly where to use the code from your last post. I'm using the Grunt plugin for browsersync. Should I use your code in my page javascript or in my gruntfile.js?

Here is what I have in my grunfile.js:

browserSync: {
        dev: {
            bsFiles: {
                src : ['text/devTest/portionfix-test/display/control/styles/*.css', 'text/devTest/portionfix-test/display/control/js/*.js']
            },
            options: {
                watchTask: true,
                proxy: {
                    target: '127.0.0.1:8888',
                    scriptPath: function (relative) {
                        return relative;
                    }
                }
            }
        }
    }

Here is what I have in my HTML page before </body>:

<script type='text/javascript' id="__bs_script__">//<![CDATA[document.write("<script async src='http://127.0.0.1:8888/browser-sync/browser-sync-client.2.5.0.js'><\/script>".replace("HOST", location.hostname));//]]></script>

Hi @samxi - you've actually demonstrated a deficiency with the grunt plugin - specifically that you cannot provide a callback for when BrowserSync is ready... I'll add this to the list of improvements after which you'll be able to call:

browserSync: {
    dev: {
        bsFiles: {
            src : ['text/devTest/portionfix-test/display/control/styles/*.css', 'text/devTest/portionfix-test/display/control/js/*.js']
        },
        options: {
            watchTask: true,
            proxy: '127.0.0.1:8888',
            callbacks: {
                ready: function () {
                    ngrok.connect(bs.options.get('port'), function (err, url) {
                        // https://757c1652.ngrok.com -> 127.0.0.1:8080
                    });
                }
            }
        }
    }
}

Sweet, can't wait for this. If it changes the implementation at all, it might be worth mentioning there is an ngrok grunt plugin https://www.npmjs.com/package/grunt-ngrok

It wouldn't change the implementation at all - there are lots of use cases for the callback, not just the one we discussed here :)

Great! Looking forward to that implementation. I've previously used BrowserSync with my local IP but at my job I have issues using that so I've been using ngrok. Thanks for your quick reply and attention!

@samxi - worth noting if you're having issues with the IP address BrowserSync gives you, it may be because its selecting the incorrect one.

Check if your OS reports more than 1 with something like dev-ip

@samxi - my previous example will work with latest version, just run

npm rm grunt-browser-sync && npm install grunt-browser-sync

This will ensure you get the latest version

@shakyShane Sounds good. I'll give it a shot. Thanks!

@shakyShane

For clarity, I use a custom domain setup in ngrok to test local files on devices (http://sambbdev.ngrok.com). I am trying to get the browserSync grunt task to refresh that custom ngrok domain on devices.

I have run npm rm grunt-browser-sync && npm install grunt-browser-sync to get latest version.

My gruntfile.js now contains:

browserSync: {
        dev: {
            bsFiles: {
                src : ['text/devTest/portionfix-test/display/control/styles/*.css', 'text/devTest/portionfix-test/display/control/js/*.js']
            },
            options: {
                watchTask: true,
                proxy: '127.0.0.1:8888',
                callbacks: {
                    ready: function () {
                        ngrok.connect(bs.options.get('port'), function (err, url) {
                            // https://757c1652.ngrok.com -> 127.0.0.1:8080
                        });
                    }
                }
            }
        }
    }

I am getting this error: Fatal error: ngrok is not defined.

Should I be using:

var ngrok = require('ngrok');
var browserSync = require('browser-sync')
browserSync({
    server: "./app"
}, function (err, bs) {
   ngrok.connect(bs.options.get('port'), function (err, url) {
      // https://757c1652.ngrok.com -> 127.0.0.1:8080  
   }); 
});

I tried adding that in a script tag before </body> but that is not working either. Sorry if I am being daft.

first run npm install ngrok - then put var ngrok = require('ngrok'); at the top of your grunfile

If I run ngrok -authtoken ********************* -subdomain=acd 80 then the ngrok tunnel works at http://acd.ngrok.com as expected. When I follow the above instructions (get new version of BS, require ngrok in gruntfile) and add the following to my gruntfile, browserSync starts as usual with no problem, but I get Tunnel acd.ngrok.com not found at http://acd.ngrok.com.

I'm sure I'm missing something glaringly obvious here, and if so, any elucidation would be greatly appreciated! I'm not even sure what the expected behavior is. Should the ngrok details print to the terminal along side the [BS] Proxying: http... etc.? Thanks.

browserSync: {
        dev: {
          bsFiles: {
            src : ['dist/css/*.css', 'dist/js/*.js', '../craft/templates/*.html']
          },
          options: {
            proxy: 'truckinusa.dev',
            watchTask: true,
            callbacks: {
              ready: function () {
                ngrok.connect({
                  authtoken: '*************************',
                  subdomain: 'acd',
                  port: bs.options.get('port')
                }, function (err, url) {

                });
              }
            }
          }
        }
      }

@samxi — did you ever get this to work? I have just tried messing around with it again today and still am not able to get ngrok to run from the BS callback. I'd love to know if you had any luck with it.

@jimlakey – Unfortunately I was not able to get it working. I'm hoping to dig into it again soon to see if I can come up with a solution. If I do I'll post it here.

Is there any intent to implement this? I've had a lot of luck with ngrok at my workplace and zero luck with localtunnel.

This issue should reopen or localtunnel has to be removed as an option...

Was this page helpful?
0 / 5 - 0 ratings

Related issues

adjavaherian picture adjavaherian  Â·  4Comments

w88975 picture w88975  Â·  3Comments

npearson72 picture npearson72  Â·  3Comments

tonyoconnell picture tonyoconnell  Â·  3Comments

ericmorand picture ericmorand  Â·  3Comments