Saturday, November 3, 2012

Module Caching in Node.js

There was an interesting question on stackoverflow about whether singletons can be implemented in Node.js  via modules: Singleton pattern in nodejs - is it needed?

Ignoring any discussion about the singleton as anti-patterns, the question comes down to how Node.js caches modules.

The Node.js docs for Module Caching & Module Caching Caveats state:
Modules are cached after the first time they are loaded. This means (among other things) that every call to require('foo') will get exactly the same object returned, if it would resolve to the same file. Multiple calls to require('foo') may not cause the module code to be executed multiple times. 
Modules are cached based on their resolved filename. Since modules may resolve to a different filename based on the location of the calling module (loading from node_modules folders), it is not a guarantee that require('foo') will always return the exact same object, if it would resolve to different files. 
"may not" and "not a guarantee" bother me -- under what circumstances will require('foo') not return the same object?

Turns out to be pretty simple: If the foo in require('foo') resolves to the same file in the filesystem (excluding hardlinked files), the same object is returned. If foo resolves to different files, in different directories, then each would be loaded/executed/cached individually.

Under the hood, fs.realpath is used to resolve the canonicalized absolute pathname to the file -- this means that symlinks to a file all resolve to the same file.

Monday, October 29, 2012

Google Analytics and development/staging/production servers

It's common (best practice, actually) to have multiple copies of a site for development, staging, production, etc. Ideally you want to use the same code on all the sites. This can lead to an analytics problem -- having data from the dev and staging sites pollute the production data. One approach to dealing with this is to add a filter to the analytics profile to remove any data coming from the staging or dev servers.

I've starting modifying my analytics code as follows:
if (!/staging|localhost/.test(window.location.hostname))
 _gaq.push(['_setAccount', 'UA-XXXXX-X']);

In brief, if we're on our staging server, don't set the web property ID . This results in the tracker using a default ID -- something like "UA-99999-9".

  • The analytics code functions normally, but any data is sent to the default web property ID. This is nice because it's possible to verify that the analytics code is working.
  • More Javascript (the hostname comparison) that runs on every page.
Note: I used to put the conditional on the _trackPageview call -- The problem with this is that other analytics code (like _trackEvent, etc) will still be sending data.

Saturday, October 27, 2012

Building a Raspberry Pi Cross Compiler: could not retrieve eglibc-2_16

tl;dr svn is required to fetch eglibc-2_16 when building a Raspberry Pi cross compiler with crosstool-NG

The Raspberry Pi is a great little device. While it's possible to do compiles on the platform, because of limited memory/CPU, for bigger binaries it's faster to work on my regular desktop box.

I'm using crosstool-NG to build a toolchain for cross compiling binaries for the Raspberry Pi.
Following along Chris Boot's steps from How to build a cross compiler for your Raspberry Pi, the final build failed during the "Retrieving needed toolchain components' tarballs" step with the error

ct-ng could not retrieve eglibc-2_16

Looks like the the eglibc folk don't provide tarball releases, so svn is required to fetch eglibc.
Installed Subversion, and had a successful build.

Just for the records, the final list of packages needed for building the cross compiler were:
sudo apt-get -y install libssl-dev openssh-server git-core pkg-config build-essential curl gcc g++
sudo apt-get -y install bison flex gperf libtool texinfo gawk automake libncurses5-dev
sudo apt-get -y install subversion

Update: If you're planning on cross compiling Node.js (build time: 10 minutes instead of 2 hours!), make sure to enable C++ from within ct-ng menuconfig (under C-compiler > Additional supported languages)

Saturday, September 15, 2012

Delta Printer Musings...

I've got a new printer in the works -- a Delta robot based on the Rostock by Johann Rocholl.

I wrote this post to help me get my mind around the differences between traditional 3D printers vs Delta robots, and the math involved in figuring out movement.

(tl;dr The resolution of a single arm on the Rostock printer I’m building varies from 11 to 60 steps/mm across the print bed)

What I find interesting is that with a Delta bot, the resolution changes depending on where you are on the print bed.

With printers that use a Cartesian coordinate linear motion system (i.e. X, Y, Z motors), the resolution of the printer is the same no matter where you’re printing. For example, my ORDish Bot printer has a resolution of approximately 53 steps/millimeter on both the X & Y axis, and 2015 steps/millimeter along the Z.
(Both X & Y axis use 20 tooth gears, 3mm pitch belts, and stepper motors with 200 steps/revolution in 1/16 microstepping mode. The Z axis uses 16 TPI threaded rod and the same motors.)

Looking at a single arm of a Delta Bot, one end of the arm moves up and down (attached to some form of linear motion element), and the other end moves horizontally (attached to a print head). This forms a right triangle, with the arm as the hypotenuse. The hypotenuse length is fixed, and the length of either side can be calculated from the other via the Pythagorean theorem.

The printer I’m currently building is based on Johann’s original Rostock dimensions, with an arm length of 250mm. Moving the print head across the platform (but keeping it on the platform) moves the other end of the arm up & down, at heights ranging from 165mm (print head is farthest from the linear motion element), 218mm (middle of platform), and 245mm (closest to linear motion element)

A little playing around with the Pythagorean theorem shows that a 1mm vertical movement at those points results in print head movements of 0.87mm, 1.76mm, & 4.69mm. Using the same pulley/belt/motor combo as my ORDish bot translates to resolutions of 60, 29, 11 steps/mm. The farther away the print head is from the linear motion  element, the higher the resolution.

This is just looking at one arm... When the print head is in an area of higher resolution of one arm, it’s at lower resolution of the other arms, and visa-versa.

If anybody has a good way of describing the resolution, please let me know.

All these numbers are approximate, and should be taken with a grain of salt...

Thursday, June 7, 2012

Node.js instead of make/Ant...

Interesting post on using Node.js as a build script, instead of make/Ant/...

Con: yet another way of doing builds...
Pro: It's Node.js!

I'm on the fence about this, but I think it's worth considering, depending on your environment.

Tuesday, May 29, 2012

Slic3r 0.8.1/0.8.2 is out!

Slic3r is one of several applications that takes a 3D model and converts it to a set of instruction for a 3D printer.

Slic3r 0.8.1 has been released at

Looks like some interesting new features
  • randomize starting points across layers -- preventing a bump when the starting/ending point is the same.
  • automatically adding perimeters as needed -- I've had problems with printing the tops of spheres.
  • improved surface quality

Looking forward to giving it a try!

Update: make that Slic3r 0.8.2

Saturday, May 19, 2012

3D Printer Trading Cards (From the Future!)

Mike's ORD-ish Bot
Shawn Wallace of Make Magazine put together these great 3D Printer Trading Cards!

Maker Faire 2012

Great first day at Maker Faire -- the ORDish bot is in a great location by one of the doors in the Expo hall. Lot's of people stopped by, and with luck I'll get my voice back by tomorrow ;)

Both MakerSlide and ORD Bot kits are availabile through Inventables:

Quick view of the ORDish Bot at Maker Faire 2012 before opening.

Tuesday, May 15, 2012


Most home Fused deposition modeling (FDM) printers are using Acrylonitrile Butadiene Styrene (ABS) or Polylactic acid(PLA).

ABS prints at around 225-250C, and requires a heated build platform for larger prints to avoid warping.

PLA prints at around 170-180C. Originally I thought I was going to be able to print straight onto an unheated glass bed, but found the prints coming off after a few mm had printed. Turns out that PLA sticks well to a layer blue painters tape over glass.

 One downside to PLA is that due to the lower melting point, for best results the prints have to be cooled between layers, otherwise the top surfaces of small objects can overheat and distort. With that in mind, I added a modified Ducted cooling fan that blows air over the printed surface. I tried a duct that surrounded the extruder, but wasn't happy with loosing visibility.

Saturday, May 12, 2012

Broken Glass Bed...

I've had good luck printing PLA onto painters tape on a glass bed -- some time in the future I'd like to upgrade to a heated bed.

I was printing a large rectangular piece (the base for a Las Vegas sign, scaled 150%), and it just didn't want to come off the glass.

Picked up two replacement beds from the local hardware store -- wanted to make sure to have a spare for Maker Faire!

Sunday, May 6, 2012

Z axis problems

Bad news - I upgraded the Z axis hoping to get rid of some periodic distortion, but my calibration prints look worse than before ;-(

After printing out a 20mm calibration cube that was only 16mm high, I realized that I'm loosing Z steps -- the  Pololu motor drivers have an adjustable current setting, and I'm guessing that while things worked before, it must have been right on the border. Moving the additional mass of the bigger ACME screws caused the drivers to overheat and miss steps.

Adding a fan blowing over the RAMPS board seems to work for now.

Saturday, April 28, 2012

New Z axis

Upgraded the Z axis to ACME lead screws and added supports for the top of the rods. I wasn't happy with a  periodic distortion along Z in prints, and I could see that one of the threaded rods had a small amount of wobble.

Monday, March 5, 2012

Not a blob of plastic!

Printed a Squirrel from Thingiverse!
Still have a lot of tuning to do, but it's cool to have something come out of the printer that doesn't look like a Lovecraftian elder god trying to sneak back into our dimension ;)

Not an amorphous blob of plastic

Friday, February 10, 2012

Starting the build...

Pretty much the intent is to roughly follow Bard Dring's initial ORD Bot design, but with a larger build platform.
I've been receiving packages from all over this week: MakerSlideUltiMachineMakerGearMisumiMcMasterCarSDP-SI, and a couple of eBay vendors.

Parts, parts, parts...

Wednesday, February 1, 2012

RangeError: Maximum call stack size exceeded

One difficulty in node.js occurs with the asynchronous processing of a large amount of sequential data.
For example, in Stack Overflow: Is there really a Node.js maximum execution call limit? a large amount of data is being processed through DB calls via recursive callbacks. Eventually a Maximum call stack size exceeded error is generated.
It's possible to simplify the code through modules like Step or Flow-JS, but these still use the call stack to keep things in sync.

An interesting approach that doesn't build up the call stack is to avoid recursion and use setTimeout with a timeout value of 0 to schedule the callback call. See

Tuesday, January 24, 2012

Cloud9 IDE now supports Node 0.6!

Node v0.5 got rid of require.paths, which was used in Cloud9. It's been possible to work around this, but a pain.
It looks like multiple versions of Node are supported, allowing backward compatability in your code