Blog

  • He’s Alive!

    Restarting this blog after a short hiatus of just 10 years. Not that I didn’t write anything in that time. I just didn’t publish it.

    For now I’m reviewing the old posts, translating some to enlish, deleting those of them that were not relevant even 10 or 12 years ago and shaping up this WP instance.

  • Programando una extensión de Google Chrome

    Escribir una extensión para cualquier aplicación que lo soporte suele ser tan complicado como detallada sea la documentación que ofrece. En el caso que nos ocupa, Google Chrome, la documentación es bastante completa aunque haya que navegar por distintos negociados de la web de desarrolladores de Chrome para encontrar todas las piezas. Y una de las partes difíciles de encontrar es cómo depurar nuestra extensión. Usando como base la que se encuentra aquí vamos a entender un poco mejor como funcionan las extensiones para Google Chrome. (more…)

  • De la diferencia entre censura y autodefensa

    Esta entrada ha estado macerando en el disco duro durante un buen tiempo. Cubre un tema que no me gusta y que me convierte, a mis tiernos ojos, en algo que tampoco me gusta: un censurador. La excusa, nosotros contra ellos.

    Ellos son, esta vez, las empresas. Centrémonos en una empresa periodística. Transparente en casi todos sus aspectos. Con buen contenido, casi siempre. Esos “casis” aparecen por todas partes, en todos los aspectos de nuestras vidas. Pero esta empresa concreta se metió en un jardín: hazte socio y no verás publicidad. Casi. En su afán por conseguir contenido han perdido el control sobre lo que publican. O esa es la impresión que dan. (more…)

  • Be careful what and how you “optimize”

    Sometimes we tend to over-engineer our code. Just because we think it will look smarter, or run faster, or be more canon-compliant. Let’s take, for example, this function that gets a value from the server and translates it into a class name to apply to an element.

    angular.module('widgetTransactionsFilters', [])
           .filter('transactionType', function() {
    	return function(input) {
    		var strClass = 'type-0';
    
    		switch(input) {
    			case 'Payment Credit Card':
    				strClass = 'type-1';
    				break;
    			case 'Cash Withdrawl':
    				strClass = 'type-2';
    				break;
    			case 'Bill Payment':
    				strClass = 'type-3';
    				break;
    			case 'Salary':
    				strClass = 'type-4';
    				break;
    			case 'Online Transfer':
    				strClass = 'type-5';
    				break;
    		}
    		return strClass;
    	};
    });

    it’s not the most elegant filter, but hey, it’s mine! As they say, devil will find code for idle hands to refactor. In this case, I decided, don’t ask me why, to change the switch for an array lookup. To make it less legible, mainly. To make any changes to the filter slightly difficult? Who knows. In any case, this was the second version.

    angular.module('widgetTransactionsFilters', [])
           .filter('transactionType', function() {
    	return function(input) {	
    		return 'type-' + 
    				(['Payment Credit Card',
    				'Cash Withdrawl',
    				'Bill Payment',
    				'Salary',
    				'Online Transfer'].indexOf(input) + 1);
    	};
    });

    Despite my feeble attempts at AngularJS I know some things about JS. One of these things is that most of the array methods are not very optimized. So maybe it’s time to check which version is faster. Or less slow. Fortunately there’s an online tool that can help us to quickly solve this questions: jsperf.com.

    Using jsperf.com. you can create a set of tests that will be run in a loop for some time. The speed of the test will be determined by the number of loops executed in that time. Additionally you can run the same tests using different browsers in different platforms. This is specially useful when you’re optimizing your code for an hybrid app where you know the browser and the platform.

    You can code your setup, and add a number of tests. This is the setup:

    <script>
      Benchmark.prototype.setup = function() {
        function bySwitch(input) {
            var strClass = 'type-0';
        
            switch(input) {
                    case 'Payment Credit Card':
                            strClass = 'type-1';
                            break;
                    case 'Cash Withdrawal':
                            strClass = 'type-2';
                            break;
                    case 'Bill Payment':
                            strClass = 'type-3';
                            break;
                    case 'Salary':
                            strClass = 'type-4';
                            break;
                    case 'Online Transfer':
                            strClass = 'type-5';
                            break;
            }
            return strClass;
        }
        
        function byArray(input) {   
            return 'type-' + 
                            (['Payment Credit Card',
                            'Cash Withdrawal',
                            'Bill Payment',
                            'Salary',
                            'Online Transfer'].indexOf(input) + 1);
        }
      };
    </script>

    And these are the tests, along with the results.

    performance1

    As you can see, the array lookup is way more slow than the old fashioned switch. Not surprises here, people. The only surprise can be the huge difference of performance between Chrome Canary and WebKit when you perform the same test in both browsers.

    performance2

    Corollary: be careful when you start refactoring and always test the performance of your code.

    UPDATE: Vyacheslav Egorov, aka @mraleph, noticed this post and thankfully redirected me to this excellent presentation on how to avoid benchmarking pitfalls due to the JIT optimization. Basically “optimizer eats µbenchmarks for breakfast”.

    performance3

    I’ve modified the first function to force the switch input NOT to be treated by the compiler as a constant, by changing it from switch(input) to switch(input.toString()). And here are the updated results.

    performance4

    The difference is still there, both between browsers and ways to test for the string. But the number of iterations for each test shows that all (or most) of the code in each of my tests is being executed. Or so I hope. BTW, the benchmark is located here. Feel free to use and abuse it.

    So, the bottom line is: 1. don’t trust blindly in microbenchmarks, 2. don’t assume anything about the language and 3. run, don’t walk, to see mraleph’s presentation.

  • The toString conundrum

    Last week, in the course of a technical job interview I was asked this question:

        How to make
    
          console.log(test.plus(6).minus(4))
    
        return
    
          9.

    The first part, chaining functions, is trivial. As you (should) know, you just need to return the object in each chainable method.

    function Counter (numInitial) {
          this.counter = numInitial;
    
          this.plus = function (howmuch) {
                this.counter += howmuch;
                return this;
          };
    
          this.minus = function (howmuch) {
                this.counter -= howmuch;
                return this;
          };
    };

    To test this class in your browser you just need to instantiate it like this and then call the required methods:

    test = new Counter(7)
    > Counter {counter: 7, plus: function, minus: function, toString: function}
    
    console.log(test.plus(6).minus(4))
    > Counter {counter: 9, plus: function, minus: function, toString: function}

    Of course, the result is not the expected. The tester is asking for the code to return “9”, not the object. Fortunately, there are two methods in the Function() that we can override. These methods are used internally whenever JavaScript need to make a comparison, returning the native value of the Function().

    // automatically called to return a String representation of our class
    
    Counter.prototype.toString = function () {
          return this.counter;
    };

    Of course, you can define this method inside the original definition of the class. I’m just writing this way for you to copy and paste step by step in your browser’s console.

    In any case, by overriding the toString method in our class we should get “9”, since console.log() is returning an String. But it doesn’t. It seems that console.log don’t use .toString or .valueOf in FireFox or Chrome. You should thinks of this as a bug, but if you think of it, the function of the console is to give us accurate information of the objects and variables we pass to it. Converting them would, most of the time, not desirable.

    The way to really show that our code is working is to force it to return an String, by converting it before passing it to console.log().

    // before overriding toString
    
    console.log(test.plus(6).minus(4) + '')
    > [object Object]
    
    // after overriding toString
    
    console.log(test.plus(6).minus(4) + '')
    > 9