diff --git a/Gemfile b/Gemfile
new file mode 100644
index 0000000000000000000000000000000000000000..b80e2bb0415643de56a5ee56e2f068cee4e9fdc9
--- /dev/null
+++ b/Gemfile
@@ -0,0 +1,3 @@
+source :rubygems
+
+gem 'json_pure', '~> 1.5'
diff --git a/Gemfile.lock b/Gemfile.lock
new file mode 100644
index 0000000000000000000000000000000000000000..817082ac31c0080750e3e3d3b34fa5ee1d499fd2
--- /dev/null
+++ b/Gemfile.lock
@@ -0,0 +1,10 @@
+GEM
+  remote: http://rubygems.org/
+  specs:
+    json_pure (1.5.1)
+
+PLATFORMS
+  ruby
+
+DEPENDENCIES
+  json_pure (~> 1.5)
diff --git a/README.wiki b/README.wiki
index 5f009003db75879097c08006605729774461e1c1..e60fc793bd784f027726cc10db00c32d4f96f424 100755
--- a/README.wiki
+++ b/README.wiki
@@ -8,7 +8,7 @@ The reference data is stored in a Git repository as JSON files, organized into h
 
 == Requirements ==
 * Ruby >= 1.8.6
-* JSON (<code>apt-get install libjson-ruby</code> or <code>gem install json</code>)
+* Bundler (<code>gem install bundler</code>)
 * Git
 * g5kadmin account
 
@@ -46,7 +46,11 @@ Finally, these changes are automatically replicated every minute to each API REP
 == Getting started ==
 First, clone the remote MASTER REPOSITORY if it is not already done:
 
-  g5kadmin@host:/somewhere/reference-repository$ git clone ssh://g5kadmin@git.grid5000.fr/srv/git/repos/reference-repository.git
+  g5kadmin@host:/somewhere$ git clone ssh://g5kadmin@git.grid5000.fr/srv/git/repos/reference-repository.git
+
+From the newly created reference-repository folder, run the following command to install the required dependencies:
+
+  g5kadmin@host:/somewhere/reference-repository$ bundle install
 
 Right now, the easiest way to get started is to look at some existing input files in the "generators/input" directory. There you can see how you can define sites, clusters, nodes and environments programmatically. 
 Then you may create a new input file or change an existing one and run it in simulation mode:
diff --git a/generators/grid5000 b/generators/grid5000
index bcc8e9ceaae66dfcbfd964b616c8c347923298be..cf6c23255c891fedab65507fca1cecd2653545f7 100755
--- a/generators/grid5000
+++ b/generators/grid5000
@@ -1,7 +1,24 @@
 #!/usr/bin/env ruby
 
-require 'pp'
 require 'rubygems'
+
+# Set up gems listed in the Gemfile.
+gemfile = File.expand_path('../../Gemfile', __FILE__)
+begin
+  ENV['BUNDLE_GEMFILE'] = gemfile
+  require 'bundler'
+  Bundler.setup
+rescue LoadError => e
+  STDERR.puts e.message
+  STDERR.puts "Try installing bundler: `gem install bundler`"
+  exit!
+rescue Bundler::GemNotFound => e
+  STDERR.puts e.message
+  STDERR.puts "Try running `bundle install`."
+  exit!
+end
+
+require 'pp'
 require 'fileutils'
 require 'json'
 require 'yaml'
diff --git a/generators/lib/core_extensions.rb b/generators/lib/core_extensions.rb
index 7b06bca9995b5f7d64e71d6ef87209bf10ab3cba..c664827078b2a6ae7559734216d39c0e65727fe5 100755
--- a/generators/lib/core_extensions.rb
+++ b/generators/lib/core_extensions.rb
@@ -1,11 +1,59 @@
+require 'json/pure'
+
+module JSON
+  module Pure
+    module Generator
+      module GeneratorMethods
+        module Hash
+          
+          private
+          # overwrites json/pure method
+          def json_transform(state)
+            delim = ','
+            delim << state.object_nl
+            result = '{'
+            result << state.object_nl
+            depth = state.depth += 1
+            first = true
+            indent = !state.object_nl.empty?
+            keys.map{|k| k.to_s}.sort.each { |key|
+              value = self[key] || self[key.to_sym]
+              result << delim unless first
+              result << state.indent * depth if indent
+              result << key.to_s.to_json(state)
+              result << state.space_before
+              result << ':'
+              result << state.space
+              result << case value
+                # no idea why this is not handled by json/pure
+              when Fixnum
+                value.to_s
+              else
+                value.to_json(state)
+              end
+              
+              first = false
+            }
+            depth = state.depth -= 1
+            result << state.object_nl
+            result << state.indent * depth if indent if indent
+            result << '}'
+            result
+          end
+        end
+      end
+    end
+  end
+end
+
 class Numeric
 
   def K;    self*10**3;     end
   def M;    self*10**6;     end
   def G;    self*10**9;     end
   def T;    self*10**12;    end
-  
-  { 
+
+  {
     :KiB => 1024, :MiB => 1024**2, :GiB => 1024**3, :TiB => 1024**4,
     :KB => 1.K/1.024, :MB => 1.M/1.024**2, :GB => 1.G/1.024**3, :TB => 1.T/1.024**4
   }.each do |method, multiplier|
@@ -26,68 +74,8 @@ end
 class Hash
   def recursive_merge!(h)
     self.merge!(h) {|key, _old, _new| if _old.class == Hash then _old.recursive_merge!(_new) else _new end  }
-  end  
-  
-  
-  # Returns a JSON string containing a JSON object, that is unparsed from
-  # this Hash instance.
-  # _state_ is a JSON::State object, that can also be used to configure the
-  # produced JSON string output further.
-  # _depth_ is used to find out nesting depth, to indent accordingly.
-  # 
-  # Contrary to the original implementation, the keys are *sorted*.
-  # 
-  def to_json(state = nil, depth = 0, *)
-    if state
-      state = JSON.state.from_state(state)
-      state.check_max_nesting(depth)
-      json_check_circular(state) { json_transform(state, depth) }
-    else
-      json_transform(state, depth)
-    end
-  end
-
-  private
-
-  def json_check_circular(state)
-    if state and state.check_circular?
-      state.seen?(self) and raise JSON::CircularDatastructure,
-          "circular data structures not supported!"
-      state.remember self
-    end
-    yield
-  ensure
-    state and state.forget self
-  end
-
-  def json_shift(state, depth)
-    state and not state.object_nl.empty? or return ''
-    state.indent * depth
   end
 
-  def json_transform(state, depth)
-    tmp_hash = {}
-    self.each do |key, value|
-      tmp_hash[key.to_s] = value
-    end
-    delim = ','
-    delim << state.object_nl if state
-    result = '{'
-    result << state.object_nl if state
-    result << tmp_hash.sort.map { |(key,value)|
-      s = json_shift(state, depth + 1)
-      s << key.to_s.to_json(state, depth + 1)
-      s << state.space_before if state
-      s << ':'
-      s << state.space if state
-      s << value.to_json(state, depth + 1)
-    }.join(delim)
-    result << state.object_nl if state
-    result << json_shift(state, depth)
-    result << '}'
-    result
-  end
-  
 end
 
 
@@ -105,5 +93,5 @@ module Enumerable
     r = Hash.new
     each{ |e| (r[yield(e)] ||= []) << e }
     r
-  end  
+  end
 end