Thursday, January 26, 2012

HTML5 Canvas Performance Tips


Here are some things we learned when building the i.TV grid with HTML5 Canvas, which was a fun experiment, but probably a terrible idea. You can decide if it was a good idea here: http://i.tv/guide.

1. Close your paths! (Avoid memory leaks)
2. Don't draw when you don't need to! (Improve FPS)
3. Profile! Profile! Profile!
4. Keep your canvas as small as possible. (Decrease memory use and improve FPS)
5. Check out requestAnimationFrame for animations. (Optimize FPS)
6. Mobile browsers don't do well with canvas animations (5 FPS FTW!)
7. Native scrolling > JS Scrolling!
8. DOM = slow, Canvas may be slower.

Here are some other techniques I've heard an help as well:
9. Typed arrays http://hacks.mozilla.org/2011/12/faster-canvas-pixel-manipulation-with-typed-arrays/
10. Consider variable re-use to prevent garbage collection. (Smoother animation)

Here are some other general tips for dealing with Canvas:
11. Make sure to handle touch events for mobile
12. Test your offset code in multiple browsers as it can get a little hairy

Friday, January 20, 2012

LESS is awesome

Lately we started using LESS for some of our web apps at i.TV. I just wanted to iterate some of the benefits and a few of the downsides.  Initially we were using connect-less to compile our less dynamically when the app is started. We still use this for our development environment but now we use lessc in our build scripts to compile it before hand. It's a little more stable that way.

AWESOME BITS

  1. We can use constants for z-indexes to prevent the endless desire of devs to make them higher forever. z-index: @z-modal > z-index: 999999999
  2. Separate .less files for each UI widget makes for awesome code organization. This is HUGE!
  3. Makes CSS3 browser prefixes a little more manageable.
  4. Using variables for color names makes it a lot easier to make sure you're on the same page with a designer.
  5. CSS code re-use FTW!
  6. Mixins are okay.
NOT-SO AWESOME BITS
  1. Weird issue with using the @arguments variable where there are commas. (See: https://github.com/cloudhead/less.js/issues/301)
  2. connect-less initially had some trouble including files with includes inside them, but I think it's fixed now.
  3. It would be really nice to be able to just include a full directory instead of manually including all x number of files (within the widgets directory for example) manually.
  4. LESS doesn't encouraged any specific structure or good patterns, which is fine, but you sometimes get really excited about using the nesting feature, because it seems so convenient and clean, but it can actually can make your code less re-usable if you don't do it right.

NodeUp 11 Commentary


Yesterday, I listened to the nodeup podcast (http://nodeup.com/eleven) about databases and node.js. It was pretty epic. I wanted to write up my thoughts and summarize it as best as I could. There are some great things going on in the node.js and database worlds and I have my opinions about them too. Here we go...

1) Postgres

People like Postgres if they need relational database. This is because the community is really cool and they add lots of features (every feature!) There's even a JSON-store feature Postgres is working on. Yammer is the only known (big) company to be using Postgres with node in production, but the node-postgres library is supposedly pretty decent.

2) Database people hate MongoDB, developers love it

Supposedly, 10Gen is the hermit of the database world. They don't hang out with other database people, but what they do is listen to customers/end-users more than database engineers, so it's very developer friendly, but database people think it's technically inferior (??). People say "Mongo loses data", presumably because journaling used to be off by default, but Mongoose has become the de-factor ORM of simple node websites and MongoDB with node is obviously really popular. For the record I LOVE MONGODB.

3) Redis

Redis has a lot in common with node. It's single threaded and fast, but it doesn't scale horizontally very well. It's also really really fast and has really good node support. There actually aren't a lot of good use cases for Redis, because it doesn't scale up super well. Because it's in memory it's going to be faster than most other databases. DShaw wrote a redistore for socket.io, but it's unclear how well it can scale, pretty darn well though, apparently. It does have a pubsub feaure that can be subscribed to with a regex (?), which people think is really cool.

4) CouchDB

So the node community has been huge on CouchDB for a long time. Isaac S. uses it for NPM and a lot of people use it for other things. Pros: HTTP Interface super easy to use, map reduces are incremental and therefore super fast. Cons: It scales terribly. Imagine 1,000,000 users each with their own DB doing master->master replication. It will blow up. A ton of data or a huge number of users don't make a good fit for couchDB. That being said, if you have less users and less data (say in the thousands of things) and want to experiment with master->master replication for example from a mobile app to the web it could be really cool. Again, it can actually be really slow.

5) Riak

Riak does map reduces really really slowly. They were joking that they should be called "work orders" instead of jobs. Someone, maybe it was Voxer? is using them heavily in production and converted their super slow couchDB instance to Riak and they found that it worked way better. Riak is a huge key/value store than is highly available and easy to scale horizontally. It's pretty simple and doesn't have a lot of fancy features, but it works well if you're trying to keep it simple. It has an HTTP interface (like couchDB). If you're trying to be fancy and do a lot of complex map reduces your life will suck and it would be faster to use carrier pigeons.

6) The future

A lot of people are excited about building databases in Javascript. Isaac S. noted some technical limitations of JavaScript, but everyone else was arguing that there are limitations in any langauge and the ones JavaScript has (not good with large numbers, etc), may prove solvable or less important. It seems the idea is that building databases isn't that hard and people (with some helpful tools) will likely continue to build custom databases for their own needs. Awesome.

Thursday, January 19, 2012

Mongo Map Reduce Vs. Query

Just had something come up today where I had to take a bunch of users from an existing collection and put some of their data in a new collection with new IDs. Here are two approaches that do the same thing, with wildly different speeds.


Map reduce is way faster than looping over a really fast query for this kind of work!

Tuesday, January 17, 2012

File upload with express.js


Uploading files with express.js is insanely simple!

FYI, there's something special called req.files when you upload multipart forms. In this case I upload the file with a form field with the name of "file".



I found this stuff out here:
https://groups.google.com/forum/#!topic/express-js/vDmtdWMx5tY


Monday, January 16, 2012

Installing node.js on Linode (Ubuntu 10.04)

Never really used Ubuntu for a server before.

Here's I was able to get it setup to run node.js and mongoDB.

Node:

apt-get update
apt-get install build-essential
apt-get install openssl
apt-get install libssl-dev 
cd /root
mkdir builds
cd builds
wget http://nodejs.org/dist/v0.6.7/node-v0.6.7.tar.gz
tar xzvf node-v0.6.7.tar.gz
cd node-v0.6.7
./configure
make
make install

Mongo:

Follow these instructions:
http://www.mkyong.com/mongodb/how-to-install-mongodb-on-ubuntu/



cat 'deb http://downloads-distro.mongodb.org/repo/ubuntu-upstart dist 10gen' >> /etc/apt/sources.list
sudo apt-get update
sudo apt-key adv --keyserver keyserver.ubuntu.com --recv 7F0CEB10
sudo apt-get install mongodb-10gen