[前][次][番号順一覧][スレッド一覧]

ruby-changes:21916

From: tenderlove <ko1@a...>
Date: Wed, 7 Dec 2011 08:12:48 +0900 (JST)
Subject: [ruby-changes:21916] tenderlove:r33965 (trunk): * ext/psych/lib/psych.rb (module Psych): parse and load methods take

tenderlove	2011-12-07 08:12:37 +0900 (Wed, 07 Dec 2011)

  New Revision: 33965

  http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=33965

  Log:
    * ext/psych/lib/psych.rb (module Psych): parse and load methods take
      an optional file name that is used when raising Psych::SyntaxError
      exceptions
    * ext/psych/lib/psych/syntax_error.rb (module Psych): allow nil file
      names and handle nil file names in the exception message
    * test/psych/test_exception.rb (module Psych): Tests for changes.

  Modified files:
    trunk/ChangeLog
    trunk/ext/psych/lib/psych/syntax_error.rb
    trunk/ext/psych/lib/psych.rb
    trunk/test/psych/test_exception.rb

Index: ChangeLog
===================================================================
--- ChangeLog	(revision 33964)
+++ ChangeLog	(revision 33965)
@@ -1,3 +1,12 @@
+Wed Dec  7 08:04:31 2011  Aaron Patterson <aaron@t...>
+
+	* ext/psych/lib/psych.rb (module Psych): parse and load methods take
+	  an optional file name that is used when raising Psych::SyntaxError
+	  exceptions
+	* ext/psych/lib/psych/syntax_error.rb (module Psych): allow nil file
+	  names and handle nil file names in the exception message
+	* test/psych/test_exception.rb (module Psych): Tests for changes.
+
 Tue Dec  6 18:26:33 2011  Tanaka Akira  <akr@f...>
 
 	* ext/dbm/dbm.c: use db_version() instead of DB_VERSION_STRING to
Index: ext/psych/lib/psych/syntax_error.rb
===================================================================
--- ext/psych/lib/psych/syntax_error.rb	(revision 33964)
+++ ext/psych/lib/psych/syntax_error.rb	(revision 33965)
@@ -3,8 +3,9 @@
     attr_reader :file, :line, :column, :offset, :problem, :context
 
     def initialize file, line, col, offset, problem, context
-      err     = [problem, context].compact.join ' '
-      message = "(%s): %s at line %d column %d" % [file, err, line, col]
+      err      = [problem, context].compact.join ' '
+      filename = file || '<unknown>'
+      message  = "(%s): %s at line %d column %d" % [filename, err, line, col]
 
       @file    = file
       @line    = line
Index: ext/psych/lib/psych.rb
===================================================================
--- ext/psych/lib/psych.rb	(revision 33964)
+++ ext/psych/lib/psych.rb	(revision 33965)
@@ -106,34 +106,58 @@
   ###
   # Load +yaml+ in to a Ruby data structure.  If multiple documents are
   # provided, the object contained in the first document will be returned.
+  # +filename+ will be used in the exception message if any exception is raised
+  # while parsing.
   #
+  # Raises a Psych::SyntaxError when a YAML syntax error is detected.
+  #
   # Example:
   #
-  #   Psych.load("--- a")           # => 'a'
-  #   Psych.load("---\n - a\n - b") # => ['a', 'b']
-  def self.load yaml
-    result = parse(yaml)
+  #   Psych.load("--- a")             # => 'a'
+  #   Psych.load("---\n - a\n - b")   # => ['a', 'b']
+  #
+  #   begin
+  #     Psych.load("--- `", "file.txt")
+  #   rescue Psych::SyntaxError => ex
+  #     ex.file    # => 'file.txt'
+  #     ex.message # => "(foo.txt): found character that cannot start any token"
+  #   end
+  def self.load yaml, filename = nil
+    result = parse(yaml, filename)
     result ? result.to_ruby : result
   end
 
   ###
   # Parse a YAML string in +yaml+.  Returns the first object of a YAML AST.
+  # +filename+ is used in the exception message if a Psych::SyntaxError is
+  # raised.
   #
+  # Raises a Psych::SyntaxError when a YAML syntax error is detected.
+  #
   # Example:
   #
   #   Psych.parse("---\n - a\n - b") # => #<Psych::Nodes::Sequence:0x00>
   #
+  #   begin
+  #     Psych.parse("--- `", "file.txt")
+  #   rescue Psych::SyntaxError => ex
+  #     ex.file    # => 'file.txt'
+  #     ex.message # => "(foo.txt): found character that cannot start any token"
+  #   end
+  #
   # See Psych::Nodes for more information about YAML AST.
-  def self.parse yaml
-    children = parse_stream(yaml).children
+  def self.parse yaml, filename = nil
+    children = parse_stream(yaml, filename).children
     children.empty? ? false : children.first.children.first
   end
 
   ###
   # Parse a file at +filename+. Returns the YAML AST.
+  #
+  # Raises a Psych::SyntaxError when a YAML syntax error is detected.
   def self.parse_file filename
     File.open filename do |f|
-      parse f
+      parse f, filename
     end
   end
 
@@ -146,15 +170,26 @@
   ###
   # Parse a YAML string in +yaml+.  Returns the full AST for the YAML document.
   # This method can handle multiple YAML documents contained in +yaml+.
+  # +filename+ is used in the exception message if a Psych::SyntaxError is
+  # raised.
   #
+  # Raises a Psych::SyntaxError when a YAML syntax error is detected.
+  #
   # Example:
   #
   #   Psych.parse_stream("---\n - a\n - b") # => #<Psych::Nodes::Stream:0x00>
   #
+  #   begin
+  #     Psych.parse_stream("--- `", "file.txt")
+  #   rescue Psych::SyntaxError => ex
+  #     ex.file    # => 'file.txt'
+  #     ex.message # => "(foo.txt): found character that cannot start any token"
+  #   end
+  #
   # See Psych::Nodes for more information about YAML AST.
-  def self.parse_stream yaml
+  def self.parse_stream yaml, filename = nil
     parser = self.parser
-    parser.parse yaml
+    parser.parse yaml, filename
     parser.handler.root
   end
 
@@ -221,15 +256,15 @@
   #
   #   Psych.load_stream("--- foo\n...\n--- bar\n...") # => ['foo', 'bar']
   #
-  def self.load_stream yaml
-    parse_stream(yaml).children.map { |child| child.to_ruby }
+  def self.load_stream yaml, filename = nil
+    parse_stream(yaml, filename).children.map { |child| child.to_ruby }
   end
 
   ###
   # Load the document contained in +filename+.  Returns the yaml contained in
   # +filename+ as a ruby object
   def self.load_file filename
-    File.open(filename) { |f| self.load f }
+    File.open(filename) { |f| self.load f, filename }
   end
 
   # :stopdoc:
Index: test/psych/test_exception.rb
===================================================================
--- test/psych/test_exception.rb	(revision 33964)
+++ test/psych/test_exception.rb	(revision 33965)
@@ -16,12 +16,88 @@
       @wups = Wups.new
     end
 
+    def test_load_takes_file
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.load '--- `'
+      end
+      assert_nil ex.file
+
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.load '--- `', 'meow'
+      end
+      assert_equal 'meow', ex.file
+    end
+
+    def test_psych_parse_stream_takes_file
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.parse_stream '--- `'
+      end
+      assert_nil ex.file
+      assert_match '(<unknown>)', ex.message
+
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.parse_stream '--- `', 'omg!'
+      end
+      assert_equal 'omg!', ex.file
+      assert_match 'omg!', ex.message
+    end
+
+    def test_load_stream_takes_file
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.load_stream '--- `'
+      end
+      assert_nil ex.file
+      assert_match '(<unknown>)', ex.message
+
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.load_stream '--- `', 'omg!'
+      end
+      assert_equal 'omg!', ex.file
+    end
+
+    def test_parse_file_exception
+      t = Tempfile.new(['parsefile', 'yml'])
+      t.binmode
+      t.write '--- `'
+      t.close
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.parse_file t.path
+      end
+      assert_equal t.path, ex.file
+      t.close(true)
+    end
+
+    def test_load_file_exception
+      t = Tempfile.new(['loadfile', 'yml'])
+      t.binmode
+      t.write '--- `'
+      t.close
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.load_file t.path
+      end
+      assert_equal t.path, ex.file
+      t.close(true)
+    end
+
+    def test_psych_parse_takes_file
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.parse '--- `'
+      end
+      assert_match '(<unknown>)', ex.message
+      assert_nil ex.file
+
+      ex = assert_raises(Psych::SyntaxError) do
+        Psych.parse '--- `', 'omg!'
+      end
+      assert_match 'omg!', ex.message
+    end
+
     def test_attributes
       e = assert_raises(Psych::SyntaxError) {
         Psych.load '--- `foo'
       }
 
-      assert_equal '<unknown>', e.file
+      assert_nil e.file
       assert_equal 1, e.line
       assert_equal 5, e.column
       # FIXME: offset isn't being set correctly by libyaml

--
ML: ruby-changes@q...
Info: http://www.atdot.net/~ko1/quickml/

[前][次][番号順一覧][スレッド一覧]