Commit 8f62a75b authored by Tim Hinderliter's avatar Tim Hinderliter
Browse files

Merge branch 'pl-rc-1.0.0' into pl-release

parents a84ae3b7 c6ab55d0
......@@ -22,6 +22,7 @@
require "chef/mixin/checksum"
require "chef/cookbook_loader"
require "mixlib/authentication/signatureverification"
require "chef/json"
class Application < Merb::Controller
......@@ -102,11 +103,11 @@ class Application < Merb::Controller
def access_denied
raise Unauthorized, "You must authenticate first!"
end
def get_available_recipes
all_cookbooks_list = Chef::CookbookVersion.cdb_list(true)
available_recipes = all_cookbooks_list.sort{ |a,b| a.name.to_s <=> b.name.to_s }.inject([]) do |result, element|
element.recipes.sort.each do |r|
element.recipes.sort.each do |r|
if r =~ /^(.+)::default$/
result << $1
else
......@@ -118,5 +119,19 @@ class Application < Merb::Controller
available_recipes
end
# Fix CHEF-1292/PL-538; cause Merb to pass the max nesting constant into
# obj.to_json, which it calls by default based on the original request's
# accept headers and the type passed into Merb::Controller.display
#
# TODO: tim, 2010-11-24: would be nice to instead have Merb call
# Chef::JSON.to_json, instead of obj.to_json, but changing that
# behavior is convoluted in Merb. This override is assuming that
# Merb is eventually calling obj.to_json, which takes the :max_nesting
# option.
override! :display
def display(obj)
super(obj, nil, {:max_nesting => Chef::JSON::JSON_MAX_NESTING})
end
end
......@@ -102,4 +102,37 @@ Merb::Router.prepare do
match('/').to(:controller => 'main', :action =>'index').name(:top)
# Need to monkey patch Merb so that it inflates JSON input with a higher
# recursion depth allowed (the default is 19). See CHEF-1292/PL-538.
module Merb
class Request
# ==== Returns
# Hash:: Parameters from body if this is a JSON request.
#
# ==== Notes
# If the JSON object parses as a Hash, it will be merged with the
# parameters hash. If it parses to anything else (such as an Array, or
# if it inflates to an Object) it will be accessible via the inflated_object
# parameter.
#
# :api: private
def json_params
@json_params ||= begin
if Merb::Const::JSON_MIME_TYPE_REGEXP.match(content_type)
begin
# Call Chef's JSON utility instead of the default in Merb,
# JSON.parse.
jobj = Chef::JSON.from_json(raw_post)
jobj = jobj.to_mash if jobj.is_a?(Hash)
rescue JSON::ParserError
jobj = Mash.new
end
jobj.is_a?(Hash) ? jobj : { :inflated_object => jobj }
end
end
end
end
end
end
......@@ -38,7 +38,7 @@ class DatabagItems < Application
begin
@databag_item = Chef::DataBagItem.new
@databag_item.data_bag params[:databag_id]
@databag_item.raw_data = JSON.parse(params[:json_data])
@databag_item.raw_data = Chef::JSON.from_json(params[:json_data])
raise ArgumentError, "Updating id is not allowed" unless @databag_item.raw_data['id'] == params[:id] #to be consistent with other objects, changing id is not allowed.
@databag_item.save
redirect(url(:databag_databag_items, :databag_id => params[:databag_id], :id => @databag_item.name), :message => { :notice => "Updated Databag Item #{@databag_item.name}" })
......@@ -61,7 +61,7 @@ class DatabagItems < Application
@databag_name = params[:databag_id]
@databag_item = Chef::DataBagItem.new
@databag_item.data_bag @databag_name
@databag_item.raw_data = JSON.parse(params[:json_data])
@databag_item.raw_data = Chef::JSON.from_json(params[:json_data])
@databag_item.create
redirect(url(:databag_databag_items, :databag_id => @databag_name), :message => { :notice => "Databag item created successfully" })
rescue => e
......
......@@ -89,14 +89,14 @@ class Nodes < Application
begin
@node = Chef::Node.new
@node.name params[:name]
@node.normal_attrs = JSON.parse(params[:attributes])
@node.normal_attrs = Chef::JSON.from_json(params[:attributes])
@node.run_list.reset!(params[:for_node] ? params[:for_node] : [])
raise ArgumentError, "Node name cannot be blank" if (params[:name].nil? || params[:name].length==0)
@node.create
redirect(url(:nodes), :message => { :notice => "Created Node #{@node.name}" })
rescue => e
Chef::Log.error("#{e}\n#{e.backtrace.join("\n")}")
@node.normal_attrs = JSON.parse(params[:attributes])
@node.normal_attrs = Chef::JSON.from_json(params[:attributes])
@available_recipes = get_available_recipes
@available_roles = Chef::Role.list.keys.sort
@node.run_list params[:for_node]
......@@ -110,7 +110,7 @@ class Nodes < Application
begin
@node = Chef::Node.load(params[:id])
@node.run_list.reset!(params[:for_node] ? params[:for_node] : [])
@node.normal_attrs = JSON.parse(params[:attributes])
@node.normal_attrs = Chef::JSON.from_json(params[:attributes])
@node.save
@_message = { :notice => "Updated Node" }
render :show
......
......@@ -90,8 +90,8 @@ class Roles < Application
@role.name(params[:name])
@role.run_list(params[:for_role] ? params[:for_role] : [])
@role.description(params[:description]) if params[:description] != ''
@role.default_attributes(JSON.parse(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(JSON.parse(params[:override_attributes])) if params[:override_attributes] != ''
@role.default_attributes(Chef::JSON.from_json(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(Chef::JSON.from_json(params[:override_attributes])) if params[:override_attributes] != ''
@role.create
redirect(url(:roles), :message => { :notice => "Created Role #{@role.name}" })
rescue => e
......@@ -99,8 +99,8 @@ class Roles < Application
@available_recipes = get_available_recipes
@available_roles = Chef::Role.list.keys.sort
@role = Chef::Role.new
@role.default_attributes(JSON.parse(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(JSON.parse(params[:override_attributes])) if params[:override_attributes] != ''
@role.default_attributes(Chef::JSON.from_json(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(Chef::JSON.from_json(params[:override_attributes])) if params[:override_attributes] != ''
@run_list = Chef::RunList.new.reset!(Array(params[:for_role]))
@_message = { :error => "Could not create role" }
render :new
......@@ -113,8 +113,8 @@ class Roles < Application
@role = Chef::Role.load(params[:id])
@role.run_list(params[:for_role] ? params[:for_role] : [])
@role.description(params[:description]) if params[:description] != ''
@role.default_attributes(JSON.parse(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(JSON.parse(params[:override_attributes])) if params[:override_attributes] != ''
@role.default_attributes(Chef::JSON.from_json(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(Chef::JSON.from_json(params[:override_attributes])) if params[:override_attributes] != ''
@role.save
@_message = { :notice => "Updated Role" }
render :show
......@@ -124,8 +124,8 @@ class Roles < Application
@available_roles = Chef::Role.list.keys.sort
@run_list = Chef::RunList.new.reset!( Array(params[:for_role]))
Chef::Log.error(@run_list.inspect)
@role.default_attributes(JSON.parse(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(JSON.parse(params[:override_attributes])) if params[:override_attributes] != ''
@role.default_attributes(Chef::JSON.from_json(params[:default_attributes])) if params[:default_attributes] != ''
@role.override_attributes(Chef::JSON.from_json(params[:override_attributes])) if params[:override_attributes] != ''
@_message = {:error => "Could not update role #{params[:id]}"}
render :edit
end
......
......@@ -24,7 +24,7 @@ require 'chef/couchdb'
require 'chef/certificate'
require 'chef/index_queue'
require 'extlib'
require 'json'
require 'chef/json'
class Chef
class ApiClient
......
......@@ -181,7 +181,7 @@ class Chef::Application::Client < Chef::Application
end
begin
@chef_client_json = JSON.parse(json_io.read)
@chef_client_json = Chef::JSON.from_json(json_io.read)
json_io.close unless json_io.closed?
rescue JSON::ParserError => error
Chef::Application.fatal!("Could not parse the provided JSON file (#{Chef::Config[:json_attribs]})!: " + error.message, 2)
......
......@@ -145,7 +145,7 @@ class Chef::Application::Solo < Chef::Application
end
begin
@chef_solo_json = JSON.parse(json_io.read)
@chef_solo_json = Chef::JSON.from_json(json_io.read)
json_io.close unless json_io.closed?
rescue JSON::ParserError => error
Chef::Application.fatal!("Could not parse the provided JSON file (#{Chef::Config[:json_attribs]})!: " + error.message, 2)
......
......@@ -430,12 +430,12 @@ class Chef
end
def self.from_json(string)
o = JSON.parse(string)
o = Chef::JSON.from_json(string)
self.from_hash(o)
end
def from_json(string)
o = JSON.parse(string)
o = Chef::JSON.from_json(string)
from_hash(o)
end
......
......@@ -21,7 +21,7 @@ require 'chef/config'
require 'chef/rest'
require 'chef/log'
require 'digest/sha2'
require 'json'
require 'chef/json'
# We want to fail on create if uuidtools isn't installed
begin
......
......@@ -25,7 +25,7 @@ require 'chef/couchdb'
require 'chef/data_bag_item'
require 'chef/index_queue'
require 'extlib'
require 'json'
require 'chef/json'
class Chef
class DataBag
......
......@@ -25,7 +25,7 @@ require 'chef/couchdb'
require 'chef/index_queue'
require 'chef/data_bag'
require 'extlib'
require 'json'
require 'chef/json'
class Chef
class DataBagItem
......
......@@ -18,7 +18,7 @@
require 'chef/mixin/params_validate'
require 'chef/mixin/create_path'
require 'chef/exceptions'
require 'json'
require 'chef/json'
require 'fileutils'
class Chef
......
......@@ -41,7 +41,7 @@ class Chef
build_report_dir
savetime = Time.now.strftime("%Y%m%d%H%M%S")
File.open(File.join(config[:path], "chef-run-report-#{savetime}.json"), "w") do |file|
file.puts JSON.pretty_generate(data)
file.puts Chef::JSON.to_json_pretty(data)
end
end
......
......@@ -56,7 +56,7 @@ class Chef
alias :start :run
def call_action_for_message(message)
amqp_payload = JSON.parse(message[:payload], :create_additions => false, :max_nesting => false)
amqp_payload = Chef::JSON.from_json(message[:payload], :create_additions => false, :max_nesting => false)
action = amqp_payload["action"].to_sym
app_payload = amqp_payload["payload"]
assert_method_whitelisted(action)
......@@ -73,4 +73,4 @@ class Chef
end
end
end
\ No newline at end of file
end
#
# Author:: Daniel DeLeo (<dan@kallistec.com>)
# Author:: Seth Falcon (<seth@opscode.com>)
# Copyright:: Copyright (c) 2009 Daniel DeLeo
# Copyright:: Copyright (c) 2010 Opscode, Inc.
# License:: Apache License, Version 2.0
#
# Licensed under the Apache License, Version 2.0 (the "License");
......@@ -15,6 +17,7 @@
# See the License for the specific language governing permissions and
# limitations under the License.
#
require 'chef/json'
class Chef
module IndexQueue
......@@ -67,7 +70,8 @@ class Chef
object_with_metadata = with_indexer_metadata(metadata)
obj_id = object_with_metadata["id"]
AmqpClient.instance.queue_for_object(obj_id) do |queue|
queue.publish({:action => :add, :payload => self.with_indexer_metadata(metadata)}.to_json)
obj = {:action => :add, :payload => self.with_indexer_metadata(metadata)}
queue.publish(Chef::JSON.to_json(obj))
end
end
......@@ -76,7 +80,8 @@ class Chef
object_with_metadata = with_indexer_metadata(metadata)
obj_id = object_with_metadata["id"]
AmqpClient.instance.queue_for_object(obj_id) do |queue|
queue.publish({:action => :delete, :payload => self.with_indexer_metadata(metadata)}.to_json)
obj = {:action => :delete, :payload => self.with_indexer_metadata(metadata)}
queue.publish(Chef::JSON.to_json(obj))
end
end
......
#
# Author:: Tim Hinderliter (<tim@opscode.com>)
# Copyright:: Copyright (c) 2010 Opscode, Inc.
# License:: Apache License, Version 2.0
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# Wrapper class for interacting with JSON.
require 'json'
class Chef
class JSON
JSON_MAX_NESTING = 1000
class <<self
# See CHEF-1292/PL-538. Increase the max nesting for JSON, which defaults
# to 19, and isn't enough for some (for example, a Node within a Node)
# structures.
def opts_add_max_nesting(opts)
if opts.nil? || !opts.has_key?(:max_nesting)
opts = opts.nil? ? Hash.new : opts.clone
opts[:max_nesting] = JSON_MAX_NESTING
end
opts
end
# Just call the JSON gem's parse method with a modified :max_nesting field
def from_json(source, opts = {})
::JSON.parse(source, opts_add_max_nesting(opts))
end
def to_json(obj, opts = nil)
obj.to_json(opts_add_max_nesting(opts))
end
def to_json_pretty(obj, opts = nil)
::JSON.pretty_generate(obj, opts_add_max_nesting(opts))
end
end
end
end
......@@ -289,7 +289,7 @@ class Chef
def output(data)
case config[:format]
when "json", nil
stdout.puts JSON.pretty_generate(data)
stdout.puts Chef::JSON.to_json_pretty(data)
when "yaml"
require 'yaml'
stdout.puts YAML::dump(data)
......@@ -335,7 +335,7 @@ class Chef
end
def edit_data(data, parse_output=true)
output = JSON.pretty_generate(data)
output = Chef::JSON.to_json_pretty(data)
if (!config[:no_editor])
filename = "knife-edit-"
......@@ -353,7 +353,7 @@ class Chef
File.unlink(filename)
end
parse_output ? JSON.parse(output) : output
parse_output ? Chef::JSON.from_json(output) : output
end
def confirm(question, append_instructions=true)
......@@ -404,7 +404,7 @@ class Chef
case from_file
when /\.(js|json)$/
JSON.parse(IO.read(filename))
Chef::JSON.from_json(IO.read(filename))
when /\.rb$/
r = klass.new
r.from_file(filename)
......@@ -434,8 +434,8 @@ class Chef
# We wouldn't have to do these shenanigans if all the editable objects
# implemented to_hash, or if to_json against a hash returned a string
# with stable key order.
object_parsed_again = JSON.parse(object.to_json, :create_additions => false)
output_parsed_again = JSON.parse(output.to_json, :create_additions => false)
object_parsed_again = Chef::JSON.from_json(Chef::JSON.to_json(object), :create_additions => false)
output_parsed_again = Chef::JSON.from_json(Chef::JSON.to_json(output), :create_additions => false)
if object_parsed_again != output_parsed_again
output.save
self.msg("Saved #{output}")
......
......@@ -17,7 +17,7 @@
#
require 'chef/knife'
require 'json'
require 'chef/json'
require 'tempfile'
require 'erubis'
......
......@@ -18,7 +18,7 @@
require 'chef/knife'
require 'chef/api_client'
require 'json'
require 'chef/json'
class Chef
class Knife
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment