And a few less-featureful templating-frameworks in 140 bytes or less: http://www.140byt.es/keywords/template
Notably, the examples found at https://gist.github.com/964762#file_test.js has the closest parity.
Edit: On second thought, I think the previous gist can reach parity with just a helper function for iterating and escaping:
function engine(a,b){return function(c,d){return a.replace(/#{([^}]*)}/g,function(a,e){return Function("x","with(x)return "+e).call(c,d||b||{})})}}
function iterator(o, k, f){
var i, v = [];
for(i in o[k]){
v = v.concat(f(o, k, i));
}
return v.join('');
}
function print_kv(o, k, i){
return [" ", i, ":", o[k][i]];
}
hello = engine("Hello,#{iterator(this, 'users', print_user)}!")
// We don't have to pass iterator, on the next line, but it should demonstrate
// how we context can be overwritten
hello({users: {a: 1, b: 2, c:3}}, {iterator: iterator, print_user: print_kv})
// Or don't pass print_user
print_user = print_kv
hello({users: {a: 1, b: 2, c:3}})
// "Hello, a:1 b:2 c:3!"
// Overload it!
hello({users: {a: 1, b: 2, c:3}}, {print_user: function(o, k, i){return " "+i}})
// "Hello, a b c!"