Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
98 changes: 91 additions & 7 deletions stdlib/psych/0/psych.rbs
Original file line number Diff line number Diff line change
Expand Up @@ -261,8 +261,92 @@ module Psych
# Psych.dump({a: "b"}, stringify_names: true) # => "---\na: b\n"
#
%a{annotate:rdoc:copy:Psych.dump}
def self.dump: (untyped o, ?indentation: Integer, ?line_width: Integer, ?canonical: bool, ?header: bool) -> String
| [IO] (untyped o, IO, ?indentation: Integer, ?line_width: Integer, ?canonical: bool, ?header: bool) -> IO
def self.dump: (untyped o, ?indentation: Integer, ?line_width: Integer, ?canonical: bool, ?header: bool, ?stringify_names: bool) -> String
| [IO] (untyped o, IO, ?indentation: Integer, ?line_width: Integer, ?canonical: bool, ?header: bool, ?stringify_names: bool) -> IO

# <!--
# rdoc-file=ext/psych/lib/psych.rb
# - Psych.safe_dump(o) -> string of yaml
# - Psych.safe_dump(o, options) -> string of yaml
# - Psych.safe_dump(o, io) -> io object passed in
# - Psych.safe_dump(o, io, options) -> io object passed in
# -->
# Safely dump Ruby object `o` to a YAML string. Optional `options` may be passed
# in to control the output format. If an IO object is passed in, the YAML will
# be dumped to that IO object. By default, only the following classes are
# allowed to be serialized:
#
# * TrueClass
# * FalseClass
# * NilClass
# * Integer
# * Float
# * String
# * Array
# * Hash
#
# Arbitrary classes can be allowed by adding those classes to the
# `permitted_classes` keyword argument. They are additive. For example, to
# allow Date serialization:
#
# Psych.safe_dump(yaml, permitted_classes: [Date])
#
# Now the Date class can be dumped in addition to the classes listed above.
#
# A Psych::DisallowedClass exception will be raised if the object contains a
# class that isn't in the `permitted_classes` list.
#
# Currently supported options are:
#
# <code>:indentation</code>
# : Number of space characters used to indent. Acceptable value should be in
# <code>0..9</code> range, otherwise option is ignored.
#
# Default: `2`.
#
# <code>:line_width</code>
# : Max character to wrap line at. For unlimited line width use
# <code>-1</code>.
#
# Default: `0` (meaning "wrap at 81").
#
# <code>:canonical</code>
# : Write "canonical" YAML form (very verbose, yet strictly formal).
#
# Default: `false`.
#
# <code>:header</code>
# : Write <code>%YAML [version]</code> at the beginning of document.
#
# Default: `false`.
#
#
# <code>:stringify_names</code>
# : Dump symbol keys in Hash objects as string.
#
# Default: `false`.
#
#
# Example:
#
# # Dump an array, get back a YAML string
# Psych.safe_dump(['a', 'b']) # => "---\n- a\n- b\n"
#
# # Dump an array to an IO object
# Psych.safe_dump(['a', 'b'], StringIO.new) # => #<StringIO:0x000001009d0890>
#
# # Dump an array with indentation set
# Psych.safe_dump(['a', ['b']], indentation: 3) # => "---\n- a\n- - b\n"
#
# # Dump an array to an IO with indentation set
# Psych.safe_dump(['a', ['b']], StringIO.new, indentation: 3)
#
# # Dump hash with symbol keys as string
# Psych.dump({a: "b"}, stringify_names: true) # => "---\na: b\n"
#
%a{annotate:rdoc:copy:Psych.safe_dump}
def self.safe_dump: (untyped o, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?indentation: Integer, ?line_width: Integer, ?canonical: bool, ?header: bool, ?stringify_names: bool) -> String
| [IO] (untyped o, IO, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?indentation: Integer, ?line_width: Integer, ?canonical: bool, ?header: bool, ?stringify_names: bool) -> IO

# <!--
# rdoc-file=ext/psych/lib/psych.rb
Expand Down Expand Up @@ -298,7 +382,7 @@ module Psych
# to `safe_load` except that `Symbol` objects are allowed by default.
#
%a{annotate:rdoc:copy:Psych.load}
def self.load: (String yaml, ?filename: String | _ToStr | _ToS?, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool) -> untyped
def self.load: (String yaml, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?filename: String | _ToStr | _ToS?, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool, ?strict_integer: bool) -> untyped

# <!--
# rdoc-file=ext/psych/lib/psych.rb
Expand All @@ -309,7 +393,7 @@ module Psych
# `fallback` return value, which defaults to `nil`. See load for options.
#
%a{annotate:rdoc:copy:Psych.load_file}
def self.load_file: (path, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool) -> untyped
def self.load_file: (path, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool, ?strict_integer: bool) -> untyped

# <!--
# rdoc-file=ext/psych/lib/psych.rb
Expand Down Expand Up @@ -360,7 +444,7 @@ module Psych
# Psych.safe_load("---\n foo: bar", symbolize_names: true) # => {:foo=>"bar"}
#
%a{annotate:rdoc:copy:Psych.safe_load}
def self.safe_load: (String yaml, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?filename: String | _ToStr | _ToS?, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool) -> untyped
def self.safe_load: (String yaml, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?filename: String | _ToStr | _ToS?, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool, ?strict_integer: bool) -> untyped

# <!--
# rdoc-file=ext/psych/lib/psych.rb
Expand Down Expand Up @@ -411,7 +495,7 @@ module Psych
# options.
#
%a{annotate:rdoc:copy:Psych.safe_load_file}
def self.safe_load_file: (path, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool) -> untyped
def self.safe_load_file: (path, ?permitted_classes: Array[Class], ?permitted_symbols: Array[Symbol], ?aliases: bool, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool, ?strict_integer: bool) -> untyped

# <!--
# rdoc-file=ext/psych/lib/psych.rb
Expand All @@ -426,7 +510,7 @@ module Psych
# safe_load_file method.
#
%a{annotate:rdoc:copy:Psych.unsafe_load_file}
def self.unsafe_load_file: (path, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool) -> untyped
def self.unsafe_load_file: (path, ?fallback: untyped, ?symbolize_names: bool, ?freeze: bool, ?strict_integer: bool) -> untyped

class Exception < ::RuntimeError
end
Expand Down
60 changes: 59 additions & 1 deletion test/stdlib/psych_test.rb
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
require_relative "test_helper"

require "psych"
require "date"
require "tmpdir"

class PsychSingletonTest < Test::Unit::TestCase
include TestHelper

library "psych"
library "psych", "date"
testing "singleton(::Psych)"

def test_load
Expand All @@ -23,6 +24,14 @@ def test_load
foo: 123
YAML
)

assert_send_type(
"(::String, permitted_classes: ::Array[::Class], permitted_symbols: ::Array[::Symbol], aliases: bool, strict_integer: bool) -> untyped",
Psych, :load, <<-YAML, permitted_classes: [Date], permitted_symbols: [:foo], aliases: true, strict_integer: true
foo: &foo 2026-11-05
bar: *foo
YAML
)
end

def test_load_file
Expand All @@ -40,6 +49,11 @@ def test_load_file
"(::_ToPath, fallback: ::String, symbolize_names: bool, freeze: bool) -> untyped",
Psych, :load_file, Pathname(File.join(dir, "test.yaml")), fallback: "foo", symbolize_names: false, freeze: false
)

assert_send_type(
"(::String, permitted_classes: ::Array[::Class], permitted_symbols: ::Array[::Symbol], aliases: bool, strict_integer: bool) -> untyped",
Psych, :load_file, File.join(dir, "test.yaml"), permitted_classes: [Date], permitted_symbols: [:foo], aliases: true, strict_integer: true
)
end
end

Expand All @@ -54,6 +68,13 @@ def test_safe_load
assert_send_type(
"(::String, permitted_classes: ::Array[::Class], permitted_symbols: ::Array[::Symbol], aliases: bool, filename: ::_ToS, fallback: ::Symbol, symbolize_names: bool, freeze: bool) -> untyped",
Psych, :safe_load, <<-YAML, permitted_classes: [Integer], permitted_symbols: [:foo], aliases: true, filename: ToS.new("foo.yaml"), fallback: :foo, symbolize_names: true, freeze: false
foo: 123
YAML
)

assert_send_type(
"(::String, strict_integer: bool) -> untyped",
Psych, :safe_load, <<-YAML, strict_integer: true
foo: 123
YAML
)
Expand All @@ -74,6 +95,11 @@ def test_safe_load_file
"(::_ToPath, permitted_classes: ::Array[::Class], permitted_symbols: ::Array[::Symbol], aliases: bool, fallback: ::Symbol, symbolize_names: bool, freeze: bool) -> untyped",
Psych, :safe_load_file, Pathname(File.join(dir, "test.yaml")), permitted_classes: [Integer], permitted_symbols: [:foo], aliases: true, fallback: :foo, symbolize_names: true, freeze: false
)

assert_send_type(
"(::String, strict_integer: bool) -> untyped",
Psych, :safe_load_file, File.join(dir, "test.yaml"), strict_integer: true
)
end
end

Expand All @@ -92,6 +118,11 @@ def test_unsafe_load_file
"(::_ToPath, fallback: ::String, symbolize_names: bool, freeze: bool) -> untyped",
Psych, :unsafe_load_file, Pathname(File.join(dir, "test.yaml")), fallback: "foo", symbolize_names: false, freeze: false
)

assert_send_type(
"(::String, strict_integer: bool) -> untyped",
Psych, :unsafe_load_file, File.join(dir, "test.yaml"), strict_integer: true
)
end
end

Expand All @@ -110,6 +141,33 @@ def test_dump
"(::Array[::Integer], indentation: ::Integer, line_width: ::Integer, canonical: bool, header: bool) -> ::String",
Psych, :dump, [1], indentation: 3, line_width: 30, canonical: true, header: true
)

assert_send_type(
"(::Hash[::Symbol, ::Integer], ::StringIO, stringify_names: bool) -> ::StringIO",
Psych, :dump, { foo: 1 }, StringIO.new(), stringify_names: true
)
end

def test_safe_dump
assert_send_type(
"(::Array[::Integer]) -> ::String",
Psych, :safe_dump, [1]
)

assert_send_type(
"(::Array[::Integer], ::StringIO) -> ::StringIO",
Psych, :safe_dump, [1], StringIO.new()
)

assert_send_type(
"(::Array[::Date], ::StringIO, permitted_classes: ::Array[::Class], permitted_symbols: ::Array[::Symbol], aliases: bool) -> ::StringIO",
Psych, :safe_dump, [Date.new(2026, 11, 5)], StringIO.new(), permitted_classes: [Date], permitted_symbols: [:foo], aliases: true
)

assert_send_type(
"(::Hash[::String, ::Integer], ::StringIO, indentation: ::Integer, line_width: ::Integer, canonical: bool, header: bool, stringify_names: bool) -> ::StringIO",
Psych, :safe_dump, { "foo" => 1 }, StringIO.new(), indentation: 3, line_width: 30, canonical: true, header: true, stringify_names: true
)
end

def test_to_yaml
Expand Down
Loading