module YAML

Overview

The YAML module provides serialization and deserialization of YAML to/from native Crystal data structures.

Parsing with #load and #load_all

Deserializes a YAML document into a Type. A Type is a union of all possible YAML types, so casting to a specific type is necessary before the value is practically usable.

require "yaml"

data = YAML.load("foo: bar")
(data as Hash)["foo"] # => "bar"

Parsing with YAML#mapping

YAML#mapping defines how an object is mapped to YAML. Mapped data is accessible through generated properties like Foo#bar. It is more type-safe and efficient.

Dumping with YAML.dump or #to_yaml

YAML.dump generates the YAML representation for an object. An IO can be passed and it will be written there, otherwise it will be returned as a string. Similarly, #to_yaml (with or without an IO) on any object does the same.

yaml = YAML.dump({hello: "world"})                                # => "--- \nhello: world"
File.open("file.yml", "w") { |f| YAML.dump({hello: "world"}, f) } # => writes it to the file
# or:
yaml = {hello: "world"}.to_yaml                                # => "--- \nhello: world"
File.open("file.yml", "w") { |f| {hello: "world"}.to_yaml(f) } # => writes it to the file

Defined in:

yaml/mapping.cr
yaml/to_yaml.cr
yaml/yaml.cr

Class Method Summary

Macro Summary

Class Method Detail

def self.dump(object, io : IO) #

Serializes an object to YAML, writing it to io.


[View source]
def self.dump(object) #

Serializes an object to YAML, returning it as a string.


[View source]
def self.load(data : String) #

Deserializes a YAML document.

# ./foo.yml
data:
  string: "foobar"
  array:
    - John
    - Sarah
  hash: {key: value}
  paragraph: |
    foo
    bar
require "yaml"
YAML.load(File.read("./foo.yml"))
# => {
# => "data" => {
# => "string" => "foobar",
# => "array" => ["John", "Sarah"],
# => "hash" => {"key" => "value"},
# => "paragraph" => "foo\nbar\n"
# => }

[View source]
def self.load_all(data : String) #

Deserializes multiple YAML documents.

# ./foo.yml
foo: bar
---
hello: world
require "yaml"
YAML.load_all(File.read("./foo.yml"))
# => [{"foo" => "bar"}, {"hello" => "world"}]

[View source]

Macro Detail

macro mapping(properties, strict = false) #

The YAML.mapping macro defines how an object is mapped to YAML.

It takes hash literal as argument, in which attributes and types are defined. Once defined, Object#from_yaml populates properties of the class from the YAML document.

require "yaml"

class Employee
  YAML.mapping({
    title: String,
    name:  String,
  })
end

employee = Employee.from_yaml("title: Manager\nname: John")
employee.title # => "Manager"
employee.name  # => "John"

employee.name = "Jenny"
employee.name # => "Jenny"

Attributes not mapped with YAML.mapping are not defined as properties. Also, missing attributes raise a ParseException.

employee = Employee.from_yaml("title: Manager\nname: John\nage: 30")
employee.age # => undefined method 'age'.

employee = Employee.from_yaml("title: Manager")
# => ParseException: missing yaml attribute: name

You can also define attributes for each property.

class Employee
  YAML.mapping({
    title: String,
    name:  {
      type:    String,
      nilable: true,
      key:     "firstname",
    },
  })
end

Available attributes:

  • type (required) defines its type. In the example above, title: String is a shortcut to title: {type: String}.
  • nilable defines if a property can be a Nil.
  • key defines whick key to read from a YAML document. It defaults to the name of the property.
  • converter takes an alternate type for parsing. It requires a #from_yaml method in that class, and returns an instance of the given type.

[View source]