From f85821c268b6d70b3bb5224eb43b266e9f15caab Mon Sep 17 00:00:00 2001 From: Mitchell Hashimoto Date: Wed, 1 Sep 2010 08:27:29 -0700 Subject: [PATCH] Refactor VagrantError to be more flexible so not as many subclasses will be needed --- lib/vagrant/errors.rb | 26 ++++++++++++++++++++------ test/locales/en.yml | 9 ++++++--- test/vagrant/errors_test.rb | 18 +++++++++++++----- 3 files changed, 39 insertions(+), 14 deletions(-) diff --git a/lib/vagrant/errors.rb b/lib/vagrant/errors.rb index 265db8bfd..73d8c8cd6 100644 --- a/lib/vagrant/errors.rb +++ b/lib/vagrant/errors.rb @@ -9,7 +9,6 @@ module Vagrant # error code, and the error key is used as a default message from # I18n. class VagrantError < StandardError - DEFAULT_NAMESPACE = "vagrant.errors" @@used_codes = [] def self.status_code(code = nil) @@ -23,19 +22,34 @@ module Vagrant def self.error_key(key=nil, namespace=nil) define_method(:error_key) { key } - define_method(:error_namespace) { namespace } if namespace + error_namespace(namespace) if namespace + end + + def self.error_namespace(namespace) + define_method(:error_namespace) { namespace } end def initialize(message=nil, *args) - message = translate_error(error_key, message) if respond_to?(:error_key) + message = { :_key => message } if message && !message.is_a?(Hash) + message = { :_key => error_key, :_namespace => error_namespace }.merge(message || {}) + message = translate_error(message) + super end + # The default error namespace which is used for the error key. + # This can be overridden here or by calling the "error_namespace" + # class method. + def error_namespace; "vagrant.errors"; end + + # The key for the error message. This should be set using the + # {error_key} method but can be overridden here if needed. + def error_key; ""; end + protected - def translate_error(key, opts=nil) - namespace = respond_to?(:error_namespace) ? error_namespace : DEFAULT_NAMESPACE - I18n.t("#{namespace}.#{key}", opts) + def translate_error(opts) + I18n.t("#{opts[:_namespace]}.#{opts[:_key]}", opts) end end diff --git a/test/locales/en.yml b/test/locales/en.yml index 9e6528136..c57214ace 100644 --- a/test/locales/en.yml +++ b/test/locales/en.yml @@ -1,5 +1,8 @@ en: vagrant: - errors: - test_key: This is a test key - test_key_with_interpolation: This is a test key that says %{key} \ No newline at end of file + test: + errors: + test_key: This is a test key + test_key_with_interpolation: This is a test key that says %{key} + alternate: + test_key: This is an alternate diff --git a/test/vagrant/errors_test.rb b/test/vagrant/errors_test.rb index 84919ebd7..ab885df4f 100644 --- a/test/vagrant/errors_test.rb +++ b/test/vagrant/errors_test.rb @@ -2,7 +2,8 @@ require "test_helper" class ErrorsTest < Test::Unit::TestCase setup do - @super = Vagrant::Errors::VagrantError + @klass = Vagrant::Errors::VagrantError + @super = Class.new(@klass) { error_namespace("vagrant.test.errors") } end should "set the given status code" do @@ -12,23 +13,30 @@ class ErrorsTest < Test::Unit::TestCase should "raise an error if attempting to set the same status code twice" do klass = Class.new(@super) { status_code(4445) } + assert_raises(RuntimeError) { Class.new(@super) { status_code(4445) } } end - should "use the given message if no set error key" do + should "translate the given message if non-hash is given" do klass = Class.new(@super) - assert_equal "foo", klass.new("foo").message + assert_equal I18n.t("vagrant.test.errors.test_key"), klass.new("test_key").message + end + + should "use the alternate namespace if given" do + klass = Class.new(@super) + instance = klass.new(:_key => :test_key, :_namespace => "vagrant.test.alternate") + assert_equal I18n.t("vagrant.test.alternate.test_key"), instance.message end should "use the translation from I18n if specified" do klass = Class.new(@super) { error_key(:test_key) } - assert_equal I18n.t("vagrant.errors.test_key"), klass.new.message + assert_equal I18n.t("vagrant.test.errors.test_key"), klass.new.message end should "use the translation with the options specified if key given" do klass = Class.new(@super) { error_key(:test_key_with_interpolation) } - assert_equal I18n.t("vagrant.errors.test_key_with_interpolation", :key => "yo"), klass.new(:key => "yo").message + assert_equal I18n.t("vagrant.test.errors.test_key_with_interpolation", :key => "yo"), klass.new(:key => "yo").message end end