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. Continue reading
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. Continue reading
No es agencia para viejunos
Hace unas semanas me di de alta en una empresa de alquiler de coches joven, moderna y dinámica. La idea es estupenda. Sobre el papel. Como siempre, es la implementación la que importa. Concretamente, la implementación del proceso de reserva. Para empezar reconozco que no soy el público objetivo de este servicio: no tengo coche y no se ni quiero saber de coches.
La primera experiencia, añadir mi número de tarjeta de crédito ya fue sospechosa: encontrarte en mitad del proceso con páginas en aleman no es algo que inspire confianza. Que te hagan un cargo sin avisar previamente tampoco. O tal vez sí avisan, pero es que el alemán no es lo mío.
El problema serio llegó a la hora de hacer la primera reserva. Entro en la página y selecciono el modelo de Reserva Básica. Es una empresa moderna, hay tres formas de hacer una reserva. Cada proceso completamente distinto del otro y con sus propios WTF. Lo que podría entenderse como testing A/B¿/C?, pero mal hecho. Me pregunto, de hecho, si realmente analizan los resultados de esta especie de test.
Así que estoy en una pantalla básica, para un usuario básico. Pero este usuario básico no tiene memoria, así que no queda otra que abrir otra ventana para ver la correspondencia entre los chupinombres que la empresa asigna a sus categorías y los modelos reales. Y la información es parca: foto de catálogo y modelo de coche. Cuando me dicen que el modelo es un Kya Ceed me quedo exactamente igual que al principio. En las páginas de alquiler “viejunas” dan información sobre los vehículos que alquilan. Así, cuando necesito ir a un centro comercial o irme con tres amigotes a montar una exposición se si la capacidad del maletero será suficiente.
Entre la mala experiencia de sufrir una página mal diseñada –si no permites que la reserva sea de menos de 60 minutos no dejes que el usuario elija ese intervalo de tiempo, procura que la información relevante esté siempre visible, no la escondas en tooltips y si usas un diseño responsive comprueba que realmente funciona en todos los anchos– y que no me apetecía ponerme a buscar catálogos de coches por internet, opté por usar una agencia de alquiler tradicional. El coste en dinero es superior pero todo el proceso fue rápido e indoloro así que, sumándolo todo, no hay tanta diferencia de coste.
Seguro que alguna de las “pegas” se solucionarían en reservas posteriores, una vez conoces los modelos de coches. Pero lo de tener que hacer experimentos porque una empresa, joven y dinámica, no quiere o no sabe proporcionar al cliente toda la información que pueda necesitar en el momento en que la necesita me cuesta tiempo y dinero. Lo mismo que tener que sortear las idiosincracias de la web de reservas. Ahora estoy en la fase de encontrar la forma de darme de baja de la moderna empresa de alquiler. Pensada para gente joven y que sabe de coches. No soy el público objetivo: yo sólo quiero alquilar un coche, muy de tarde en tarde, sin pegarme con el proceso.
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.
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.
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”.
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.
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.
On AngularJS considered as one big fat Trojan Horse
A couple of weeks ago I was thinking about the relationship between AngularJS and this company that buys or starts projects and later sink them just because. No, no that company, the other one: Google. While perusing thru job boards AngularJS was appearing as a MUST in the same way (and intent) as .net appears for backend products. And then Google announced their real strategy.
Because, while there other JavaScript libraries out there that do two-way binding, template support and so on, there’s only one with a plan behind. Four years ago Google added AngularJS to its properties portfolio by adding their creators to its engineers portfolio. Just another JavaScript lib in a company where its main JavaScript apps are written in Java. A company that launched (and soon recanted) Dart, another scripting language, as the JavaScript replacement. Thanks to its initial simplicity AngularJS gained some traction. Add behind some marketing muscle and you have a winner.
Then Google announced their plans for AngularJS 2. A total rewrite (they should learn from Netscape) in ATScript. Not in JavaScript. Don’t worry: ATScript compiles to ECMAScript… and Dart. But, of course, there will not be an update path for all the code working in AngularJS right now. They’re just keeping the name. And maybe the logo.
Now I’m gonna dive into prediction territory. Let’s not forget that the business of Google is not in the development tools but in the advertisement. Everything and everyone in the company works for the ads division, directly or not. And one of the hidden but huge costs behind it are the fees payed to Firefox and Apple so they put Google in their respective navigators search box. Chrome on the other hand, been a Google property, adds no cost beyond the engineering resources destined to code it. As well as the Chrome OS, and the Chrome Notebooks.
I say that Google will announce in a months that Chrome will run native ATScript code. And, being a business movement as well as a typed language, quicker than JavaScript. Just another little push to those developers reluctant to embrace the jump from AngularJS to AngularJS 2. The bait: you can code in our language, run it at full speed in our browsers, and still compile it into JavaScript for those other losers still making us pay big bucks to Firefox or Apple.
On the other hand, we have another explanation for the switch to ATScript: the same way Apple has introduced Swift for iOS and MacOS development, maybe Google will introduce Dart (with AngularJS 2 to sweeten the deal) for Android (and Chrome OS) development. But this is just some wild fantasizing.