Tuan Anh

container nerd. k8s || GTFO

Awesome maching learning

A curated list of awesome machine learning frameworks, libraries and software (by language). Inspired by awesome-php. Other awesome lists can be found in the awesome-awesomeness list.

Stumble upon this list when I was looking for some Julia’s libraries.

link bài gốc

Deferred font loading and using localStorage as cache

The idea is to lazy-load web fonts once everything else loaded completely, store them in localStorage to be used for subsequent pages. A cookie is used as a flag to check if the fonts are cached in localStorage.

There are something to note:

  • If visitors disable cookie, this method will backfire as the webfont will be reloaded everytime visitors go to a different page.

  • localStorage is slower than browser cache (So i heard).

  • A browser that supports localStorage is required, which mean IE8+, Firefox, Opera and Chrome.

  • On first load, the page will be flashed a bit after finish loading web fonts. This happened because the web fonts finish loading and are re-applied onto the page. Because of this particular reason, I refuse to use this method to lazy-load web fonts. I just hate it seeing it flashed. I’m a sucker for this kind of detail.

  (function () {
    "use strict";
    // once cached, the css file is stored on the client forever unless
    // the URL below is changed. Any change will invalidate the cache
    var css_href = './index_files/web-fonts.css';
    // a simple event handler wrapper
    function on(el, ev, callback) {
      if (el.addEventListener) {
        el.addEventListener(ev, callback, false);
      } else if (el.attachEvent) {
        el.attachEvent("on" + ev, callback);
      }
    }
    
    // if we have the fonts in localStorage or if we've cached them using the native batrowser cache
    if ((window.localStorage && localStorage.font_css_cache) || document.cookie.indexOf('font_css_cache') > -1){
      // just use the cached version
      injectFontsStylesheet();
    } else {
     // otherwise, don't block the loading of the page; wait until it's done.
      on(window, "load", injectFontsStylesheet);
    }
    
    // quick way to determine whether a css file has been cached locally
    function fileIsCached(href) {
      return window.localStorage && localStorage.font_css_cache && (localStorage.font_css_cache_file === href);
    }

    // time to get the actual css file
    function injectFontsStylesheet() {
     // if this is an older browser
      if (!window.localStorage || !window.XMLHttpRequest) {
        var stylesheet = document.createElement('link');
        stylesheet.href = css_href;
        stylesheet.rel = 'stylesheet';
        stylesheet.type = 'text/css';
        document.getElementsByTagName('head')[0].appendChild(stylesheet);
        // just use the native browser cache
        // this requires a good expires header on the server
        document.cookie = "font_css_cache";
      
      // if this isn't an old browser
      } else {
         // use the cached version if we already have it
        if (fileIsCached(css_href)) {
          injectRawStyle(localStorage.font_css_cache);
        // otherwise, load it with ajax
        } else {
          var xhr = new XMLHttpRequest();
          xhr.open("GET", css_href, true);
          // cater for IE8 which does not support addEventListener or attachEvent on XMLHttpRequest
          xhr.onreadystatechange = function () {
            if (xhr.readyState === 4) {
              // once we have the content, quickly inject the css rules
              injectRawStyle(xhr.responseText);
              // and cache the text content for further use
              // notice that this overwrites anything that might have already been previously cached
              localStorage.font_css_cache = xhr.responseText;
              localStorage.font_css_cache_file = css_href;
            }
          };
          xhr.send();
        }
      }
    }

    // this is the simple utitily that injects the cached or loaded css text
    function injectRawStyle(text) {
      var style = document.createElement('style');
      // cater for IE8 which doesn't support style.innerHTML
      style.setAttribute("type", "text/css");
      if (style.styleSheet) {
          style.styleSheet.cssText = text;
      } else {
          style.innerHTML = text;
      }
      document.getElementsByTagName('head')[0].appendChild(style);
    }

  }());

I did not write this code. This bit was taken from Smashing Magazine - source.


nodejs: callback vs promise

http://www.slideshare.net/wookieb/callbacks-promises-generators-asynchronous-javascript

The problem

Consider the code snippet below:

var x = doSomething();
typeof x === 'undefined'; // true

The second statement will not wait for the first one to complete, hence result in true in the second statement.

When it comes to dealing with asynchronous in nodejs, we usually come down to 2 most popular options: callback and promise.

Callback

Callback is widely used but when we need 3 or more operations going in sequence, things are going to get ugly. Consider the following code snippet.

var doSomething = function(arg1, arg2, cb_fn) {
  var sum = arg1 + arg2;
  cb_fn(sum);
};

// usage
doSomething(10,20, console.log);

That is just one function with callback. Imagine this with 4 levels of callback. Welcome to CALLBACK HELL!!

var func_1 = function(cb) {
  func_2(function(err, result) {
    if (err) { cb(err); return; }

    func_3(result, function(err, result) {
      if (err) { cb(error); return; }

      // WE NEED TO GO DEEPER
    });
  });
}

Promise

What is a promise?

The core idea behind promises is that a promise represents the result of an asynchronous operation. A promise is in one of three different states:

  • pending - The initial state of a promise.
  • fulfilled - The state of a promise representing a successful operation.
  • rejected - The state of a promise representing a failed operation.

Once a promise is fulfilled or rejected, it is immutable (i.e. it can never change again).

The most complete library for promise on Nodejs is Q.


How to fix `Logon failed for login 'username' due to trigger execution` error with mssql

I recently tumbled upon an error when trying to connect to SQL Server in nodejs using mssql package.

Logon failed for login 'username' due to trigger execution

I have no problem connecting to a dev db server of mine, probably due to I don’t have any restriction/security setup on it. I only got this when connecting to a production server.

Problem lies in the default driver tedious used by mssql. Changing to tds fixes the problem.

I don’t actually understand the problem behind this so if anyone knows, please help explain it to me.


How to setup Sublime-IJulia with Sublime Text

I love Sublime Text. I prefer to do all of my development in Sublime Text if possible, especially when Julia Studio or Juno don’t offer much addtional features.

The instructions on GitHub repo is a bit confusing so I decided to rewrite it steps by steps how to set Sublime-IJulia up on OS X. I can’t say for other OS though.

I suppose that you have already had homebrew and julia installed (v0.3.3 as of this post) and add julia to PATH variable.

Install zeromq and ipython

From terminal app, install python and zeromq

# instaling requirements
brew install python zeromq
pip install ipython

After that, launch julia console and install ZMQ and IJulia packages. ZMQ and IJulia should be added and builded successfully.

Pkg.add("ZMQ")
Pkg.add("IJulia")

Install Sublime-IJulia

Now head to Sublime Text and install Sublime-IJulia by pressing Ctrl+Cmd+P and type Install Package, search for Sublime-IJulia.

Follow the instruction from step 7 of this GitHub repo. There are a few things to note though:

  • Change zeromq dylib path because of the version difference.

  • If you got Kernel died error message, try using absolute path for julia even though you already have it in $PATH variable.

That’s it. Follow the instructions carefully and it will work as expected.


A conversation with stranger

Stranger: So you’ve been living here for nine years? How come you don’t speak Thai?

me: Well… (chuckle)

Stranger: What do you do for a living?

me: I’m a programmer. I write softwares.

Stranger: Aha. So you’re a nerd? You don’t feel the need to talk to people.

me: Well…yes.


Social sharing button without embedding sharing script crap

Found this collection share url structure from various social networks on Github.

Example, for Twitter:

https://twitter.com/share?url={url}&text={title}&via={via}&hashtags={hashtags}

social sharing buttons

Use this along with font-awesome icons and we have some nice social sharing buttons without tracking scripts or slowing down your website one bit.


When static website isn't fast enough

I have recently taken a look at my website loading speed again.

A bit about my website, as of currently:

  • I hosted my website on a smallest, cheapest VPS plan at RamNode ($15 per year, massive plan) which shares the physical machine with a numerous other people.

  • This website is powered by jekyll - a static site generator.

  • The website is using a custom theme, based on Bootstrap. I loaded two addtional fonts from Google Fonts (Ubuntu and Merriweather) for heading and paragraph.

  • I have Jquery and Bootstrap script on my page for some fancy stuff I might need later, along with Google Analytics script (async).

Testing

As for the testing setup, I will compare the loading speed of two posts with text only.

  Gtmetrix Webpagetest
Total load time 2.8s 2s
Size 247KB 221KB
Number of request 14 17
Location Canada US
PageSpeed 98 96
YSlow 96 -

2-3 seconds to load isn’t too bad itself but it’s definitely not good enough for me. My idea number would be something less than 1 second. I know that custom fonts come with the trade of loading speed but I would expect it to load faster than this, especially when they’re served by Google.

Stuff I have already tried:

  • Combine CSS into a single file, minified and served by CloudFlare.

  • Images are optimized with ImageOptim for optimal size.

  • Defer/async script when possible. Loading JS script right before </body> tag.

Webpagetest gives my website A for everything except: First Byte Time (B) and Cache static content (C). Let’s break it down.

First Byte Time

  • 845 ms First Byte Time
  • 717 ms Target First Byte Time

Apparently, the VPS my website is on is slow (which is expected). I can’t do much to enhance this either.

Cache static content

Webpagetest also complains about there’s no max-age or expires set in header on fonts.googleapi.com. I have no idea why Google didn’t set max-age or expires for this. Maybe someone with better understanding about this can help explaining to me.

As much as I would like to make my website load faster (I’m sucker for this kind of stuff), I either have to upgrade the VPS plan ($$$) or go with web safe fonts (Ewwwww!).

I guess I would have to settle with this for now. Hopefully, you don’t find this website too slow.


New theme

My blog is now using customized Shiori theme - a Bootstrap-based theme for jekyll by Elle Kasai.

The switching process is painless. I just have to copy my data over from old jekyll instance, tweak here and there a bit and git push. BAMM! The blog now has a shiny new modern look :)

new theme


BAT script to execute commands on remote Unix machine with PuTTY

putty -i private_key.ppk [email protected] -m local_script.bat

In the example above, I use public key authentication to authenticate and then execute the commands inside local_script.bat on the remote machine. Alternatively, you can use plink which is basically putty without the GUI part. All other options are basically the same.

You can also use password for authentication, just replace -i option with -pw and your password.