diff --git a/generators/lib/core_extensions.rb b/generators/lib/core_extensions.rb
index 4b3dceb51a731031e2287ffed9971ce2b75b9065..62711dc1e842c46ec07896c6021154e0cfeb09f1 100755
--- a/generators/lib/core_extensions.rb
+++ b/generators/lib/core_extensions.rb
@@ -91,4 +91,22 @@ class Hash
     result
   end
   
-end
\ No newline at end of file
+end
+
+
+# for versions of ruby < 1.8.7
+module Enumerable
+  def index_by
+    inject({}) do |accum, elem|
+      accum[yield(elem)] = elem
+      accum
+    end
+  end
+
+  def group_by #:yield:
+    #h = k = e = nil
+    r = Hash.new
+    each{ |e| (r[yield(e)] ||= []) << e }
+    r
+  end  
+end
diff --git a/generators/lib/g5k_generator.rb b/generators/lib/g5k_generator.rb
index dceaff19a8e8feeaab34e507500a1ed75f94db05..eac651126c4e69926b4b5dff99c1401cb5600987 100755
--- a/generators/lib/g5k_generator.rb
+++ b/generators/lib/g5k_generator.rb
@@ -63,27 +63,65 @@ class ReferenceGenerator
     Resolv.getaddress(network_address)
   end
   
-  %w{site cluster environment node service}.each do |method|
-    define_method(method) do |uid, *options, &block|
-      key = method.pluralize.to_sym
-      uid = uid.to_s
-      options = options.first || Hash.new
-      old_context = @context
-      @context[key] ||= G5K::Folder.new
-      if options.has_key? :refer_to
-        @context[key] << G5K::Link.new(uid, options[:refer_to])
-      else    
-        # if the same object already exists, we return it for completion/modification
-        if (same_trees = @context[key].select{|tree| tree[:uid] == uid}).size > 0
-          @context = same_trees.first
-        else
-          @context[key] << G5K::Tree.new.replace({:uid => uid, :type => method})
-          @context = @context[key].last
-        end
-        block.call(uid) if block
+  # This doesn't work with Ruby < 1.8.7. Replaced by a call to build_context (see below).
+  #
+  # %w{site cluster environment node service}.each do |method|
+  #   define_method(method) do |uid, *options, &block|
+  #     key = method.pluralize.to_sym
+  #     uid = uid.to_s
+  #     options = options.first || Hash.new
+  #     old_context = @context
+  #     @context[key] ||= G5K::Folder.new
+  #     if options.has_key? :refer_to
+  #       @context[key] << G5K::Link.new(uid, options[:refer_to])
+  #     else    
+  #       # if the same object already exists, we return it for completion/modification
+  #       if (same_trees = @context[key].select{|tree| tree[:uid] == uid}).size > 0
+  #         @context = same_trees.first
+  #       else
+  #         @context[key] << G5K::Tree.new.replace({:uid => uid, :type => method})
+  #         @context = @context[key].last
+  #       end
+  #       block.call(uid) if block
+  #     end
+  #     @context = old_context
+  #   end
+  # end
+  
+  def site(uid, *options, &block)
+    build_context(:sites, uid, *options, &block)
+  end
+  def cluster(uid, *options, &block)
+    build_context(:clusters, uid, *options, &block)
+  end
+  def environment(uid, *options, &block)
+    build_context(:environments, uid, *options, &block)
+  end
+  def node(uid, *options, &block)
+    build_context(:nodes, uid, *options, &block)
+  end
+  def service(uid, *options, &block)
+    build_context(:services, uid, *options, &block)
+  end
+  def build_context(key, uid, *options, &block)
+    type = key.to_s.chop
+    uid = uid.to_s
+    options = options.first || Hash.new
+    old_context = @context
+    @context[key] ||= G5K::Folder.new
+    if options.has_key? :refer_to
+      @context[key] << G5K::Link.new(uid, options[:refer_to])
+    else    
+      # if the same object already exists, we return it for completion/modification
+      if (same_trees = @context[key].select{|tree| tree[:uid] == uid}).size > 0
+        @context = same_trees.first
+      else
+        @context[key] << G5K::Tree.new.replace({:uid => uid, :type => type})
+        @context = @context[key].last
       end
-      @context = old_context
+      block.call(uid) if block
     end
+    @context = old_context
   end
   
   # Initializes a new generator that will generates data files in a hierachical way.