Skip to content

Instantly share code, notes, and snippets.

@chris-roerig
Last active June 9, 2019 15:12
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save chris-roerig/39bbf6191c6dc1b8d44ad2c705ba7932 to your computer and use it in GitHub Desktop.
Save chris-roerig/39bbf6191c6dc1b8d44ad2c705ba7932 to your computer and use it in GitHub Desktop.
Description level Ruby 2.6.0 documentation

    
Simple Access Control Lists.

Access control lists are composed of “allow” and “deny” halves to control access.  Use “all” or “*” to match any address.  To match a specific address use any address or address mask that IPAddr can understand.

Example:

list = %w[
  deny all
  allow 192.168.1.1
  allow ::ffff:192.168.1.2
  allow 192.168.1.3
]

# From Socket#peeraddr, see also ACL#allow_socket?
addr = ["AF_INET", 10, "lc630", "192.168.1.3"]

acl = ACL.new
p acl.allow_addr?(addr) # => true

acl = ACL.new(list, ACL::DENY_ALLOW)
p acl.allow_addr?(addr) # => true


  


    
An entry in an ACL

  


    
A list of ACLEntry objects.  Used to implement the allow and deny halves of an ACL

  


    
ARGF is a stream designed for use in scripts that process files given as command-line arguments or passed in via STDIN.

The arguments passed to your script are stored in the ARGV Array, one argument per element. ARGF assumes that any arguments that aren't filenames have been removed from ARGV. For example:

$ ruby argf.rb --verbose file1 file2

ARGV  #=> ["--verbose", "file1", "file2"]
option = ARGV.shift #=> "--verbose"
ARGV  #=> ["file1", "file2"]

You can now use ARGF to work with a concatenation of each of these named files. For instance, ARGF.read will return the contents of file1 followed by the contents of file2.

After a file in ARGV has been read ARGF removes it from the Array. Thus, after all files have been read ARGV will be empty.

You can manipulate ARGV yourself to control what ARGF operates on. If you remove a file from ARGV, it is ignored by ARGF; if you add files to ARGV, they are treated as if they were named on the command line. For example:

ARGV.replace ["file1"]
ARGF.readlines # Returns the contents of file1 as an Array
ARGV           #=> []
ARGV.replace ["file2", "file3"]
ARGF.read      # Returns the contents of file2 and file3


If ARGV is empty, ARGF acts as if it contained STDIN, i.e. the data piped to your script. For example:

$ echo "glark" | ruby -e 'p ARGF.read'
"glark\n"

  


    
The Addrinfo class maps struct addrinfo to ruby.  This structure identifies an Internet host and a service.

  


    
Raised when the arguments are wrong and there isn't a more specific Exception class.

Ex: passing the wrong number of arguments

[1, 2, 3].first(4, 5)


raises the exception:

ArgumentError: wrong number of arguments (given 2, expected 1)

Ex: passing an argument that is not acceptable:

[1, 2, 3].first(-4)


raises the exception:

ArgumentError: negative array size

  


    
Arrays are ordered, integer-indexed collections of any object.

Array indexing starts at 0, as in C or Java.  A negative index is assumed to be relative to the end of the array—that is, an index of -1 indicates the last element of the array, -2 is the next to last element in the array, and so on.

Creating Arrays¶ ↑

A new array can be created by using the literal constructor [].  Arrays can contain different types of objects.  For example, the array below contains an Integer, a String and a Float:

ary = [1, "two", 3.0] #=> [1, "two", 3.0]


An array can also be created by explicitly calling Array.new with zero, one (the initial size of the Array) or two arguments (the initial size and a default object).

ary = Array.new    #=> []
Array.new(3)       #=> [nil, nil, nil]
Array.new(3, true) #=> [true, true, true]


Note that the second argument populates the array with references to the same object.  Therefore, it is only recommended in cases when you need to instantiate arrays with natively immutable objects such as Symbols, numbers, true or false.

To create an array with separate objects a block can be passed instead. This method is safe to use with mutable objects such as hashes, strings or other arrays:

Array.new(4) {Hash.new}    #=> [{}, {}, {}, {}]
Array.new(4) {|i| i.to_s } #=> ["0", "1", "2", "3"]


This is also a quick way to build up multi-dimensional arrays:

empty_table = Array.new(3) {Array.new(3)}
#=> [[nil, nil, nil], [nil, nil, nil], [nil, nil, nil]]


An array can also be created by using the Array() method, provided by Kernel, which tries to call to_ary, then to_a on its argument.

Array({:a => "a", :b => "b"}) #=> [[:a, "a"], [:b, "b"]]


Example Usage¶ ↑

In addition to the methods it mixes in through the Enumerable module, the Array class has proprietary methods for accessing, searching and otherwise manipulating arrays.

Some of the more common ones are illustrated below.

Accessing Elements¶ ↑

Elements in an array can be retrieved using the Array#[] method.  It can take a single integer argument (a numeric index), a pair of arguments (start and length) or a range. Negative indices start counting from the end, with -1 being the last element.

arr = [1, 2, 3, 4, 5, 6]
arr[2]    #=> 3
arr[100]  #=> nil
arr[-3]   #=> 4
arr[2, 3] #=> [3, 4, 5]
arr[1..4] #=> [2, 3, 4, 5]
arr[1..-3] #=> [2, 3, 4]


Another way to access a particular array element is by using the at method

arr.at(0) #=> 1


The slice method works in an identical manner to Array#[].

To raise an error for indices outside of the array bounds or else to provide a default value when that happens, you can use fetch.

arr = ['a', 'b', 'c', 'd', 'e', 'f']
arr.fetch(100) #=> IndexError: index 100 outside of array bounds: -6...6
arr.fetch(100, "oops") #=> "oops"


The special methods first and last will return the first and last elements of an array, respectively.

arr.first #=> 1
arr.last  #=> 6


To return the first n elements of an array, use take

arr.take(3) #=> [1, 2, 3]


drop does the opposite of take, by returning the elements after n elements have been dropped:

arr.drop(3) #=> [4, 5, 6]


Obtaining Information about an Array¶ ↑

Arrays keep track of their own length at all times.  To query an array about the number of elements it contains, use length, count or size.

browsers = ['Chrome', 'Firefox', 'Safari', 'Opera', 'IE']
browsers.length #=> 5
browsers.count #=> 5


To check whether an array contains any elements at all

browsers.empty? #=> false


To check whether a particular item is included in the array

browsers.include?('Konqueror') #=> false


Adding Items to Arrays¶ ↑

Items can be added to the end of an array by using either push or <<

arr = [1, 2, 3, 4]
arr.push(5) #=> [1, 2, 3, 4, 5]
arr << 6    #=> [1, 2, 3, 4, 5, 6]


unshift will add a new item to the beginning of an array.

arr.unshift(0) #=> [0, 1, 2, 3, 4, 5, 6]


With insert you can add a new element to an array at any position.

arr.insert(3, 'apple')  #=> [0, 1, 2, 'apple', 3, 4, 5, 6]


Using the insert method, you can also insert multiple values at once:

arr.insert(3, 'orange', 'pear', 'grapefruit')
#=> [0, 1, 2, "orange", "pear", "grapefruit", "apple", 3, 4, 5, 6]


Removing Items from an Array¶ ↑

The method pop removes the last element in an array and returns it:

arr =  [1, 2, 3, 4, 5, 6]
arr.pop #=> 6
arr #=> [1, 2, 3, 4, 5]


To retrieve and at the same time remove the first item, use shift:

arr.shift #=> 1
arr #=> [2, 3, 4, 5]


To delete an element at a particular index:

arr.delete_at(2) #=> 4
arr #=> [2, 3, 5]


To delete a particular element anywhere in an array, use delete:

arr = [1, 2, 2, 3]
arr.delete(2) #=> 2
arr #=> [1,3]


A useful method if you need to remove nil values from an array is compact:

arr = ['foo', 0, nil, 'bar', 7, 'baz', nil]
arr.compact  #=> ['foo', 0, 'bar', 7, 'baz']
arr          #=> ['foo', 0, nil, 'bar', 7, 'baz', nil]
arr.compact! #=> ['foo', 0, 'bar', 7, 'baz']
arr          #=> ['foo', 0, 'bar', 7, 'baz']


Another common need is to remove duplicate elements from an array.

It has the non-destructive uniq, and destructive method uniq!

arr = [2, 5, 6, 556, 6, 6, 8, 9, 0, 123, 556]
arr.uniq #=> [2, 5, 6, 556, 8, 9, 0, 123]


Iterating over Arrays¶ ↑

Like all classes that include the Enumerable module, Array has an each method, which defines what elements should be iterated over and how.  In case of Array's each, all elements in the Array instance are yielded to the supplied block in sequence.

Note that this operation leaves the array unchanged.

arr = [1, 2, 3, 4, 5]
arr.each {|a| print a -= 10, " "}
# prints: -9 -8 -7 -6 -5
#=> [1, 2, 3, 4, 5]


Another sometimes useful iterator is reverse_each which will iterate over the elements in the array in reverse order.

words = %w[first second third fourth fifth sixth]
str = ""
words.reverse_each {|word| str += "#{word} "}
p str #=> "sixth fifth fourth third second first "


The map method can be used to create a new array based on the original array, but with the values modified by the supplied block:

arr.map {|a| 2*a}     #=> [2, 4, 6, 8, 10]
arr                   #=> [1, 2, 3, 4, 5]
arr.map! {|a| a**2}   #=> [1, 4, 9, 16, 25]
arr                   #=> [1, 4, 9, 16, 25]


Selecting Items from an Array¶ ↑

Elements can be selected from an array according to criteria defined in a block.  The selection can happen in a destructive or a non-destructive manner.  While the destructive operations will modify the array they were called on, the non-destructive methods usually return a new array with the selected elements, but leave the original array unchanged.

Non-destructive Selection¶ ↑

arr = [1, 2, 3, 4, 5, 6]
arr.select {|a| a > 3}       #=> [4, 5, 6]
arr.reject {|a| a < 3}       #=> [3, 4, 5, 6]
arr.drop_while {|a| a < 4}   #=> [4, 5, 6]
arr                          #=> [1, 2, 3, 4, 5, 6]


Destructive Selection¶ ↑

select! and reject! are the corresponding destructive methods to select and reject

Similar to select vs. reject, delete_if and keep_if have the exact opposite result when supplied with the same block:

arr.delete_if {|a| a < 4}   #=> [4, 5, 6]
arr                         #=> [4, 5, 6]

arr = [1, 2, 3, 4, 5, 6]
arr.keep_if {|a| a < 4}   #=> [1, 2, 3]
arr                       #=> [1, 2, 3]


  


    
BasicObject is the parent class of all classes in Ruby.  It's an explicit blank class.

BasicObject can be used for creating object hierarchies independent of Ruby's object hierarchy, proxy objects like the Delegator class, or other uses where namespace pollution from Ruby's methods and classes must be avoided.

To avoid polluting BasicObject for other users an appropriately named subclass of BasicObject should be created instead of directly modifying BasicObject:

class MyObjectSystem < BasicObject
end


BasicObject does not include Kernel (for methods like puts) and BasicObject is outside of the namespace of the standard library so common classes will not be found without using a full class path.

A variety of strategies can be used to provide useful portions of the standard library to subclasses of BasicObject.  A subclass could include Kernel to obtain puts, exit, etc.  A custom Kernel-like module could be created and included or delegation can be used via method_missing:

class MyObjectSystem < BasicObject
  DELEGATE = [:puts, :p]

  def method_missing(name, *args, &block)
    super unless DELEGATE.include? name
    ::Kernel.send(name, *args, &block)
  end

  def respond_to_missing?(name, include_private = false)
    DELEGATE.include?(name) or super
  end
end


Access to classes and modules from the Ruby standard library can be obtained in a BasicObject subclass by referencing the desired constant from the root like ::File or ::Enumerator. Like method_missing, const_missing can be used to delegate constant lookup to Object:

class MyObjectSystem < BasicObject
  def self.const_missing(name)
    ::Object.const_get(name)
  end
end


  


    
BasicSocket is the super class for all the Socket classes.

  


    
A data object, representing the times associated with a benchmark measurement.

  


    
BigDecimal provides arbitrary-precision floating point decimal arithmetic.

Introduction¶ ↑

Ruby provides built-in support for arbitrary precision integer arithmetic.

For example:

42**13  #=>   1265437718438866624512


BigDecimal provides similar support for very large or very accurate floating point numbers.

Decimal arithmetic is also useful for general calculation, because it provides the correct answers people expect–whereas normal binary floating point arithmetic often introduces subtle errors because of the conversion between base 10 and base 2.

For example, try:

sum = 0
10_000.times do
  sum = sum + 0.0001
end
print sum #=> 0.9999999999999062


and contrast with the output from:

require 'bigdecimal'

sum = BigDecimal("0")
10_000.times do
  sum = sum + BigDecimal("0.0001")
end
print sum #=> 0.1E1


Similarly:

(BigDecimal("1.2") - BigDecimal("1.0")) == BigDecimal("0.2") #=> true

(1.2 - 1.0) == 0.2 #=> false


Special features of accurate decimal arithmetic¶ ↑

Because BigDecimal is more accurate than normal binary floating point arithmetic, it requires some special values.

Infinity¶ ↑

BigDecimal sometimes needs to return infinity, for example if you divide a value by zero.

BigDecimal("1.0") / BigDecimal("0.0")  #=> Infinity
BigDecimal("-1.0") / BigDecimal("0.0")  #=> -Infinity


You can represent infinite numbers to BigDecimal using the strings 'Infinity', '+Infinity' and '-Infinity' (case-sensitive)

Not a Number¶ ↑

When a computation results in an undefined value, the special value NaN (for 'not a number') is returned.

Example:

BigDecimal("0.0") / BigDecimal("0.0") #=> NaN


You can also create undefined values.

NaN is never considered to be the same as any other value, even NaN itself:

n = BigDecimal('NaN')
n == 0.0 #=> false
n == n #=> false


Positive and negative zero¶ ↑

If a computation results in a value which is too small to be represented as a BigDecimal within the currently specified limits of precision, zero must be returned.

If the value which is too small to be represented is negative, a BigDecimal value of negative zero is returned.

BigDecimal("1.0") / BigDecimal("-Infinity") #=> -0.0


If the value is positive, a value of positive zero is returned.

BigDecimal("1.0") / BigDecimal("Infinity") #=> 0.0


(See BigDecimal.mode for how to specify limits of precision.)

Note that -0.0 and 0.0 are considered to be the same for the purposes of comparison.

Note also that in mathematics, there is no particular concept of negative or positive zero; true mathematical zero has no sign.

bigdecimal/util¶ ↑

When you require bigdecimal/util, the to_d method will be available on BigDecimal and the native Integer, Float, Rational, and String classes:

require 'bigdecimal/util'

42.to_d         # => 0.42e2
0.5.to_d        # => 0.5e0
(2/3r).to_d(3)  # => 0.667e0
"0.5".to_d      # => 0.5e0


License¶ ↑

Copyright (C) 2002 by Shigeo Kobayashi <shigeo@tinyforest.gr.jp>.

BigDecimal is released under the Ruby and 2-clause BSD licenses. See LICENSE.txt for details.

Maintained by mrkn <mrkn@mrkn.jp> and ruby-core members.

Documented by zzak <zachary@zacharyscott.net>, mathew <meta@pobox.com>, and many other contributors.

  


    
Objects of class Binding encapsulate the execution context at some particular place in the code and retain this context for future use. The variables, methods, value of self, and possibly an iterator block that can be accessed in this context are all retained. Binding objects can be created using Kernel#binding, and are made available to the callback of Kernel#set_trace_func.

These binding objects can be passed as the second argument of the Kernel#eval method, establishing an environment for the evaluation.

class Demo
  def initialize(n)
    @secret = n
  end
  def get_binding
    binding
  end
end

k1 = Demo.new(99)
b1 = k1.get_binding
k2 = Demo.new(-3)
b2 = k2.get_binding

eval("@secret", b1)   #=> 99
eval("@secret", b2)   #=> -3
eval("@secret")       #=> nil


Binding objects have no class-specific methods.

  


    
used for Creating Specifications from the Gemcutter Endpoint

  


    
Handles all the fetching with the rubygems server

  


    
This error is raised if HTTP authentication is required, but not provided.

  


    
This error is raised if HTTP authentication is provided, but incorrect.

  


    
This is the error raised if OpenSSL fails the cert verification

  


    
This error is raised if the API returns a 413 (only printed in verbose)

  


    
This error is raised when it looks like the network is down

  


    
This is the error raised when a source is HTTPS and OpenSSL didn't load

  


    
Adds support for setting custom HTTP headers when fetching gems from the server.

TODO: Get rid of this when and if gemstash only supports RubyGems versions that contain github.com/rubygems/rubygems/commit/3db265cc20b2f813.

  


    
This class contains all of the logic for determining the next version of a Gem to update to based on the requested level (patch, minor, major). Primarily designed to work with Resolver which will provide it the list of available dependency versions as found in its index, before returning it to to the resolution engine to select the best version.

  


    
Class used to build the list of sockets that correspond to

a given mirror.

One mirror may correspond to many different addresses, both

because of it having many dns entries or because
the network interface is both ipv4 and ipv5


  


    
An error caused by attempting to fulfil a dependency that was circular

@note This exception will be thrown iff a {Vertex} is added to a

{DependencyGraph} that has a {DependencyGraph::Vertex#path_to?} an
existing {DependencyGraph::Vertex}

  


    
A directed acyclic graph that is tuned to hold named dependencies

  


    
An action that modifies a {DependencyGraph} that is reversible. @abstract

  


    
@!visibility private (see DependencyGraph#add_edge_no_circular)

  


    
@!visibility private (see DependencyGraph#delete_edge)

  


    
@!visibility private @see DependencyGraph#detach_vertex_named

  


    
A log for dependency graph actions

  


    
@!visibility private @see DependencyGraph#tag

  


    
A vertex in a {DependencyGraph} that encapsulates a {#name} and a {#payload}

  


    
A state that encapsulates a set of {#requirements} with an {Array} of possibilities

  


    
An error caused by searching for a dependency that is completely unknown, i.e. has no versions available whatsoever.

  


    
A state that encapsulates a single possibility to fulfill the given {#requirement}

  


    
This class encapsulates a dependency resolver. The resolver is responsible for determining which set of dependencies to activate, with feedback from the {#specification_provider}

  


    
A specific resolution from a given {Resolver}

  


    
An error that occurred during the resolution process

  


    
An error caused by conflicts in version

  


    
Persistent connections for Net::HTTP

Bundler::Persistent::Net::HTTP::Persistent maintains persistent connections across all the servers you wish to talk to.  For each host:port you communicate with a single persistent connection is created.

Multiple Bundler::Persistent::Net::HTTP::Persistent objects will share the same set of connections.

For each thread you start a new connection will be created.  A Bundler::Persistent::Net::HTTP::Persistent connection will not be shared across threads.

You can shut down the HTTP connections when done by calling shutdown.  You should name your Bundler::Persistent::Net::HTTP::Persistent object if you intend to call this method.

Example:

require 'bundler/vendor/net-http-persistent/lib/net/http/persistent'

uri = URI 'http://example.com/awesome/web/service'

http = Bundler::Persistent::Net::HTTP::Persistent.new 'my_app_name'

# perform a GET
response = http.request uri

# or

get = Net::HTTP::Get.new uri.request_uri
response = http.request get

# create a POST
post_uri = uri + 'create'
post = Net::HTTP::Post.new post_uri.path
post.set_form_data 'some' => 'cool data'

# perform the POST, the URI is always required
response http.request post_uri, post


Note that for GET, HEAD and other requests that do not have a body you want to use URI#request_uri not URI#path.  The request_uri contains the query params which are sent in the body for other requests.

SSL¶ ↑

SSL connections are automatically created depending upon the scheme of the URI.  SSL connections are automatically verified against the default certificate store for your computer.  You can override this by changing verify_mode or by specifying an alternate cert_store.

Here are the SSL settings, see the individual methods for documentation:
certificate        

This client's certificate
ca_file            

The certificate-authority
cert_store         

An SSL certificate store
private_key        

The client's SSL private key
reuse_ssl_sessions 

Reuse a previously opened SSL session for a new connection
ssl_version        

Which specific SSL version to use
verify_callback    

For server certificate verification
verify_mode        

How connections should be verified


Proxies¶ ↑

A proxy can be set through proxy= or at initialization time by providing a second argument to ::new.  The proxy may be the URI of the proxy server or :ENV which will consult environment variables.

See proxy= and proxy_from_env for details.

Headers¶ ↑

Headers may be specified for use in every request.  headers are appended to any headers on the request.  override_headers replace existing headers on the request.

The difference between the two can be seen in setting the User-Agent.  Using http.headers['User-Agent'] = 'MyUserAgent' will send “Ruby, MyUserAgent” while http.override_headers['User-Agent'] = 'MyUserAgent' will send “MyUserAgent”.

Tuning¶ ↑

Segregation¶ ↑

By providing an application name to ::new you can separate your connections from the connections of other applications.

Idle Timeout¶ ↑

If a connection hasn't been used for this number of seconds it will automatically be reset upon the next use to avoid attempting to send to a closed connection. The default value is 5 seconds. nil means no timeout. Set through idle_timeout.

Reducing this value may help avoid the “too many connection resets” error when sending non-idempotent requests while increasing this value will cause fewer round-trips.

Read Timeout¶ ↑

The amount of time allowed between reading two chunks from the socket.  Set through read_timeout

Max Requests¶ ↑

The number of requests that should be made before opening a new connection. Typically many keep-alive capable servers tune this to 100 or less, so the 101st request will fail with ECONNRESET. If unset (default), this value has no effect, if set, connections will be reset on the request after max_requests.

Open Timeout¶ ↑

The amount of time to wait for a connection to be opened.  Set through open_timeout.

Socket Options¶ ↑

Socket options may be set on newly-created connections.  See socket_options for details.

Non-Idempotent Requests¶ ↑

By default non-idempotent requests will not be retried per RFC 2616.  By setting retry_change_requests to true requests will automatically be retried once.

Only do this when you know that retrying a POST or other non-idempotent request is safe for your application and will not create duplicate resources.

The recommended way to handle non-idempotent requests is the following:

require 'bundler/vendor/net-http-persistent/lib/net/http/persistent'

uri = URI 'http://example.com/awesome/web/service'
post_uri = uri + 'create'

http = Bundler::Persistent::Net::HTTP::Persistent.new 'my_app_name'

post = Net::HTTP::Post.new post_uri.path
# ... fill in POST request

begin
  response = http.request post_uri, post
rescue Bundler::Persistent::Net::HTTP::Persistent::Error

  # POST failed, make a new request to verify the server did not process
  # the request
  exists_uri = uri + '...'
  response = http.get exists_uri

  # Retry if it failed
  retry if response.code == '404'
end


The method of determining if the resource was created or not is unique to the particular service you are using.  Of course, you will want to add protection from infinite looping.

Connection Termination¶ ↑

If you are done using the Bundler::Persistent::Net::HTTP::Persistent instance you may shut down all the connections in the current thread with shutdown.  This is not recommended for normal use, it should only be used when it will be several minutes before you make another HTTP request.

If you are using multiple threads, call shutdown in each thread when the thread is done making requests.  If you don't call shutdown, that's OK. Ruby will automatically garbage collect and shutdown your HTTP connections when the thread terminates.

  


    
Error class for errors raised by Bundler::Persistent::Net::HTTP::Persistent.  Various SystemCallErrors are re-raised with a human-readable message under this class.

  


    
This Net::HTTP subclass adds SSL session reuse and Server Name Indication (SNI) RFC 3546.

DO NOT DEPEND UPON THIS CLASS

This class is an implementation detail and is subject to change or removal at any time.

  


    
Dsl to parse the Gemfile looking for plugins to install

  


    
Represents a lazily loaded gem specification, where the full specification is on the source server in rubygems' “quick” index. The proxy object is to be seeded with what we're given from the source's abbreviated index - the full specification will only be fetched when necessary.

  


    
General purpose class for retrying code that may fail

  


    
RubyGems 1.8.0 to 1.8.4

  


    
RubyGems versions 1.3.6 and 1.3.7

  


    
RubyGems 2.0

  


    
RubyGems 1.4 through 1.6

  


    
RubyGems 1.8.5-1.8.19

  


    
RubyGems 2.1.0

  


    
RubyGems 1.8.20+

  


    
RubyGems 1.7

  


    
A mirror

Contains both the uri that should be used as a mirror and the

fallback timeout which will be used for probing if the mirror
replies on time or not.

  


    
Class used to parse one configuration line

Gets the configuration line and the value.

This object provides a `update_mirror` method
used to setup the given mirror value.

  


    
Class used to build the mirror set and then find a mirror for a given URI

@param prober [Prober object, nil] by default a TCPSocketProbe, this object

will be used to probe the mirror address to validate that the mirror replies.

  


    
Class used for probing TCP availability for a given mirror.

  


    
Socket address builder.

Given a socket type, a host and a port,

provides a method to build sockaddr string


  


    
The GitProxy is responsible to interact with git repositories. All actions required by the Git source is encapsulated in this object.

  


    
Bundler::Thor::Actions#capture depends on what kind of buffer is used in ERB. Thus CapturableERB fixes ERB to use String buffer.

  


    
A dynamic command that handles method missing scenarios.

  


    
A dynamic command that handles method missing scenarios.

  


    
Bundler::Thor::Error is raised when it's caused by wrong usage of thor classes. Those errors have their backtrace suppressed and are nicely shown to the user.

Errors that are caused by the developer, like declaring a method which overwrites a thor keyword, SHOULD NOT raise a Bundler::Thor::Error. This way, we ensure that developer errors are shown with full backtrace.

  


    
Bundler::Thor has a special class called Bundler::Thor::Group. The main difference to Bundler::Thor class is that it invokes all commands at once. It also include some methods that allows invocations to be done at the class method, which are not available to Bundler::Thor commands.

  


    
A command that is hidden in help messages but still invocable.

  


    
A command that is hidden in help messages but still invocable.

  


    
Raised when a command was found, but not invoked properly.

  


    
Inherit from Bundler::Thor::Shell::Basic and add set_color behavior. Check Bundler::Thor::Shell::Basic to see all available methods.

  


    
Inherit from Bundler::Thor::Shell::Basic and add set_color behavior. Check Bundler::Thor::Shell::Basic to see all available methods.

  


    
Raised when a command was not found.

  


    
Raised when a command was not found.

  


    
Internal error, should be rescued

  


    
Overview¶ ↑

The Common Gateway Interface (CGI) is a simple protocol for passing an HTTP request from a web server to a standalone program, and returning the output to the web browser.  Basically, a CGI program is called with the parameters of the request passed in either in the environment (GET) or via $stdin (POST), and everything it prints to $stdout is returned to the client.

This file holds the CGI class.  This class provides functionality for retrieving HTTP request parameters, managing cookies, and generating HTML output.

The file CGI::Session provides session management functionality; see that class for more details.

See www.w3.org/CGI/ for more information on the CGI protocol.

Introduction¶ ↑

CGI is a large class, providing several categories of methods, many of which are mixed in from other modules.  Some of the documentation is in this class, some in the modules CGI::QueryExtension and CGI::HtmlExtension.  See CGI::Cookie for specific information on handling cookies, and cgi/session.rb (CGI::Session) for information on sessions.

For queries, CGI provides methods to get at environmental variables, parameters, cookies, and multipart request data.  For responses, CGI provides methods for writing output and generating HTML.

Read on for more details.  Examples are provided at the bottom.

Queries¶ ↑

The CGI class dynamically mixes in parameter and cookie-parsing functionality,  environmental variable access, and support for parsing multipart requests (including uploaded files) from the CGI::QueryExtension module.

Environmental Variables¶ ↑

The standard CGI environmental variables are available as read-only attributes of a CGI object.  The following is a list of these variables:

AUTH_TYPE               HTTP_HOST          REMOTE_IDENT
CONTENT_LENGTH          HTTP_NEGOTIATE     REMOTE_USER
CONTENT_TYPE            HTTP_PRAGMA        REQUEST_METHOD
GATEWAY_INTERFACE       HTTP_REFERER       SCRIPT_NAME
HTTP_ACCEPT             HTTP_USER_AGENT    SERVER_NAME
HTTP_ACCEPT_CHARSET     PATH_INFO          SERVER_PORT
HTTP_ACCEPT_ENCODING    PATH_TRANSLATED    SERVER_PROTOCOL
HTTP_ACCEPT_LANGUAGE    QUERY_STRING       SERVER_SOFTWARE
HTTP_CACHE_CONTROL      REMOTE_ADDR
HTTP_FROM               REMOTE_HOST


For each of these variables, there is a corresponding attribute with the same name, except all lower case and without a preceding HTTP_. content_length and server_port are integers; the rest are strings.

Parameters¶ ↑

The method params() returns a hash of all parameters in the request as name/value-list pairs, where the value-list is an Array of one or more values.  The CGI object itself also behaves as a hash of parameter names to values, but only returns a single value (as a String) for each parameter name.

For instance, suppose the request contains the parameter “favourite_colours” with the multiple values “blue” and “green”.  The following behavior would occur:

cgi.params["favourite_colours"]  # => ["blue", "green"]
cgi["favourite_colours"]         # => "blue"


If a parameter does not exist, the former method will return an empty array, the latter an empty string.  The simplest way to test for existence of a parameter is by the has_key? method.

Cookies¶ ↑

HTTP Cookies are automatically parsed from the request.  They are available from the cookies() accessor, which returns a hash from cookie name to CGI::Cookie object.

Multipart requests¶ ↑

If a request's method is POST and its content type is multipart/form-data, then it may contain uploaded files.  These are stored by the QueryExtension module in the parameters of the request.  The parameter name is the name attribute of the file input field, as usual.  However, the value is not a string, but an IO object, either an IOString for small files, or a Tempfile for larger ones.  This object also has the additional singleton methods:
local_path()

the path of the uploaded file on the local filesystem
original_filename()

the name of the file on the client computer
content_type()

the content type of the file


Responses¶ ↑

The CGI class provides methods for sending header and content output to the HTTP client, and mixes in methods for programmatic HTML generation from CGI::HtmlExtension and CGI::TagMaker modules.  The precise version of HTML to use for HTML generation is specified at object creation time.

Writing output¶ ↑

The simplest way to send output to the HTTP client is using the out() method. This takes the HTTP headers as a hash parameter, and the body content via a block.  The headers can be generated as a string using the http_header() method.  The output stream can be written directly to using the print() method.

Generating HTML¶ ↑

Each HTML element has a corresponding method for generating that element as a String.  The name of this method is the same as that of the element, all lowercase.  The attributes of the element are passed in as a hash, and the body as a no-argument block that evaluates to a String.  The HTML generation module knows which elements are always empty, and silently drops any passed-in body.  It also knows which elements require matching closing tags and which don't.  However, it does not know what attributes are legal for which elements.

There are also some additional HTML generation methods mixed in from the CGI::HtmlExtension module.  These include individual methods for the different types of form inputs, and methods for elements that commonly take particular attributes where the attributes can be directly specified as arguments, rather than via a hash.

Utility HTML escape and other methods like a function.¶ ↑

There are some utility tool defined in cgi/util.rb . And when include, you can use utility methods like a function.

Examples of use¶ ↑

Get form values¶ ↑

require "cgi"
cgi = CGI.new
value = cgi['field_name']   # <== value string for 'field_name'
  # if not 'field_name' included, then return "".
fields = cgi.keys            # <== array of field names

# returns true if form has 'field_name'
cgi.has_key?('field_name')
cgi.has_key?('field_name')
cgi.include?('field_name')


CAUTION! cgi returned an Array with the old cgi.rb(included in Ruby 1.6)

Get form values as hash¶ ↑

require "cgi"
cgi = CGI.new
params = cgi.params


cgi.params is a hash.

cgi.params['new_field_name'] = ["value"]  # add new param
cgi.params['field_name'] = ["new_value"]  # change value
cgi.params.delete('field_name')           # delete param
cgi.params.clear                          # delete all params


Save form values to file¶ ↑

require "pstore"
db = PStore.new("query.db")
db.transaction do
  db["params"] = cgi.params
end


Restore form values from file¶ ↑

require "pstore"
db = PStore.new("query.db")
db.transaction do
  cgi.params = db["params"]
end


Get multipart form values¶ ↑

require "cgi"
cgi = CGI.new
value = cgi['field_name']   # <== value string for 'field_name'
value.read                  # <== body of value
value.local_path            # <== path to local file of value
value.original_filename     # <== original filename of value
value.content_type          # <== content_type of value


and value has StringIO or Tempfile class methods.

Get cookie values¶ ↑

require "cgi"
cgi = CGI.new
values = cgi.cookies['name']  # <== array of 'name'
  # if not 'name' included, then return [].
names = cgi.cookies.keys      # <== array of cookie names


and cgi.cookies is a hash.

Get cookie objects¶ ↑

require "cgi"
cgi = CGI.new
for name, cookie in cgi.cookies
  cookie.expires = Time.now + 30
end
cgi.out("cookie" => cgi.cookies) {"string"}

cgi.cookies # { "name1" => cookie1, "name2" => cookie2, ... }

require "cgi"
cgi = CGI.new
cgi.cookies['name'].expires = Time.now + 30
cgi.out("cookie" => cgi.cookies['name']) {"string"}


Print http header and html string to $DEFAULT_OUTPUT ($>)¶ ↑

require "cgi"
cgi = CGI.new("html4")  # add HTML generation methods
cgi.out do
  cgi.html do
    cgi.head do
      cgi.title { "TITLE" }
    end +
    cgi.body do
      cgi.form("ACTION" => "uri") do
        cgi.p do
          cgi.textarea("get_text") +
          cgi.br +
          cgi.submit
        end
      end +
      cgi.pre do
        CGI::escapeHTML(
          "params: #{cgi.params.inspect}\n" +
          "cookies: #{cgi.cookies.inspect}\n" +
          ENV.collect do |key, value|
            "#{key} --> #{value}\n"
          end.join("")
        )
      end
    end
  end
end

# add HTML generation methods
CGI.new("html3")    # html3.2
CGI.new("html4")    # html4.01 (Strict)
CGI.new("html4Tr")  # html4.01 Transitional
CGI.new("html4Fr")  # html4.01 Frameset
CGI.new("html5")    # html5


Some utility methods¶ ↑

require 'cgi/util'
CGI.escapeHTML('Usage: foo "bar" <baz>')


Some utility methods like a function¶ ↑

require 'cgi/util'
include CGI::Util
escapeHTML('Usage: foo "bar" <baz>')
h('Usage: foo "bar" <baz>') # alias


  


    
Class representing an HTTP cookie.

In addition to its specific fields and methods, a Cookie instance is a delegator to the array of its values.

See RFC 2965.

Examples of use¶ ↑

cookie1 = CGI::Cookie.new("name", "value1", "value2", ...)
cookie1 = CGI::Cookie.new("name" => "name", "value" => "value")
cookie1 = CGI::Cookie.new('name'     => 'name',
                          'value'    => ['value1', 'value2', ...],
                          'path'     => 'path',   # optional
                          'domain'   => 'domain', # optional
                          'expires'  => Time.now, # optional
                          'secure'   => true,     # optional
                          'httponly' => true      # optional
                          )

cgi.out("cookie" => [cookie1, cookie2]) { "string" }

name     = cookie1.name
values   = cookie1.value
path     = cookie1.path
domain   = cookie1.domain
expires  = cookie1.expires
secure   = cookie1.secure
httponly = cookie1.httponly

cookie1.name     = 'name'
cookie1.value    = ['value1', 'value2', ...]
cookie1.path     = 'path'
cookie1.domain   = 'domain'
cookie1.expires  = Time.now + 30
cookie1.secure   = true
cookie1.httponly = true

  


    
Exception raised when there is an invalid encoding detected

  


    
Overview¶ ↑

This file provides the CGI::Session class, which provides session support for CGI scripts.  A session is a sequence of HTTP requests and responses linked together and associated with a single client. Information associated with the session is stored on the server between requests.  A session id is passed between client and server with every request and response, transparently to the user.  This adds state information to the otherwise stateless HTTP request/response protocol.

Lifecycle¶ ↑

A CGI::Session instance is created from a CGI object.  By default, this CGI::Session instance will start a new session if none currently exists, or continue the current session for this client if one does exist.  The new_session option can be used to either always or never create a new session.  See new() for more details.

delete() deletes a session from session storage.  It does not however remove the session id from the client.  If the client makes another request with the same id, the effect will be to start a new session with the old session's id.

Setting and retrieving session data.¶ ↑

The Session class associates data with a session as key-value pairs. This data can be set and retrieved by indexing the Session instance using '[]', much the same as hashes (although other hash methods are not supported).

When session processing has been completed for a request, the session should be closed using the close() method.  This will store the session's state to persistent storage.  If you want to store the session's state to persistent storage without finishing session processing for this request, call the update() method.

Storing session state¶ ↑

The caller can specify what form of storage to use for the session's data with the database_manager option to CGI::Session::new.  The following storage classes are provided as part of the standard library:
CGI::Session::FileStore

stores data as plain text in a flat file.  Only works with String data.  This is the default storage type.
CGI::Session::MemoryStore

stores data in an in-memory hash.  The data only persists for as long as the current Ruby interpreter instance does.
CGI::Session::PStore

stores data in Marshalled format.  Provided by cgi/session/pstore.rb.  Supports data of any type, and provides file-locking and transaction support.


Custom storage types can also be created by defining a class with the following methods:

new(session, options)
restore  # returns hash of session data.
update
close
delete


Changing storage type mid-session does not work.  Note in particular that by default the FileStore and PStore session data files have the same name.  If your application switches from one to the other without making sure that filenames will be different and clients still have old sessions lying around in cookies, then things will break nastily!

Maintaining the session id.¶ ↑

Most session state is maintained on the server.  However, a session id must be passed backwards and forwards between client and server to maintain a reference to this session state.

The simplest way to do this is via cookies.  The CGI::Session class provides transparent support for session id communication via cookies if the client has cookies enabled.

If the client has cookies disabled, the session id must be included as a parameter of all requests sent by the client to the server.  The CGI::Session class in conjunction with the CGI class will transparently add the session id as a hidden input field to all forms generated using the CGI#form() HTML generation method.  No built-in support is provided for other mechanisms, such as URL re-writing.  The caller is responsible for extracting the session id from the session_id attribute and manually encoding it in URLs and adding it as a hidden input to HTML forms created by other mechanisms.  Also, session expiry is not automatically handled.

Examples of use¶ ↑

Setting the user's name¶ ↑

require 'cgi'
require 'cgi/session'
require 'cgi/session/pstore'     # provides CGI::Session::PStore

cgi = CGI.new("html4")

session = CGI::Session.new(cgi,
    'database_manager' => CGI::Session::PStore,  # use PStore
    'session_key' => '_rb_sess_id',              # custom session key
    'session_expires' => Time.now + 30 * 60,     # 30 minute timeout
    'prefix' => 'pstore_sid_')                   # PStore option
if cgi.has_key?('user_name') and cgi['user_name'] != ''
    # coerce to String: cgi[] returns the
    # string-like CGI::QueryExtension::Value
    session['user_name'] = cgi['user_name'].to_s
elsif !session['user_name']
    session['user_name'] = "guest"
end
session.close


Creating a new session safely¶ ↑

require 'cgi'
require 'cgi/session'

cgi = CGI.new("html4")

# We make sure to delete an old session if one exists,
# not just to free resources, but to prevent the session
# from being maliciously hijacked later on.
begin
    session = CGI::Session.new(cgi, 'new_session' => false)
    session.delete
rescue ArgumentError  # if no old session
end
session = CGI::Session.new(cgi, 'new_session' => true)
session.close


  


    
File-based session storage class.

Implements session storage as a flat file of 'key=value' values. This storage type only works directly with String values; the user is responsible for converting other types to Strings when storing and from Strings when retrieving.

  


    
In-memory session storage class.

Implements session storage as a global in-memory hash.  Session data will only persist for as long as the Ruby interpreter instance does.

  


    
Dummy session storage class.

Implements session storage place holder.  No actual storage will be done.

  


    
PStore-based session storage class.

This builds upon the top-level PStore class provided by the library file pstore.rb.  Session data is marshalled and stored in a file.  File locking and transaction services are provided.

  


    
This class provides a complete interface to CSV files and data.  It offers tools to enable you to read and write to and from Strings or IO objects, as needed.

The most generic interface of the library is:

csv = CSV.new(string_or_io, **options)

# Reading: IO object should be open for read
csv.read # => array of rows
# or
csv.each do |row|
  # ...
end
# or
row = csv.shift

# Writing: IO object should be open for write
csv << row


There are several specialized class methods for one-statement reading or writing, described in the Specialized Methods section.

If a String is passed into ::new, it is internally wrapped into a StringIO object.

options can be used for specifying the particular CSV flavor (column separators, row separators, value quoting and so on), and for data conversion, see Data Conversion section for the description of the latter.

Specialized Methods¶ ↑

Reading¶ ↑

# From a file: all at once
arr_of_rows = CSV.read("path/to/file.csv", **options)
# iterator-style:
CSV.foreach("path/to/file.csv", **options) do |row|
  # ...
end

# From a string
arr_of_rows = CSV.parse("CSV,data,String", **options)
# or
CSV.parse("CSV,data,String", **options) do |row|
  # ...
end


Writing¶ ↑

# To a file
CSV.open("path/to/file.csv", "wb") do |csv|
  csv << ["row", "of", "CSV", "data"]
  csv << ["another", "row"]
  # ...
end

# To a String
csv_string = CSV.generate do |csv|
  csv << ["row", "of", "CSV", "data"]
  csv << ["another", "row"]
  # ...
end


Shortcuts¶ ↑

# Core extensions for converting one line
csv_string = ["CSV", "data"].to_csv   # to CSV
csv_array  = "CSV,String".parse_csv   # from CSV

# CSV() method
CSV             { |csv_out| csv_out << %w{my data here} }  # to $stdout
CSV(csv = "")   { |csv_str| csv_str << %w{my data here} }  # to a String
CSV($stderr)    { |csv_err| csv_err << %w{my data here} }  # to $stderr
CSV($stdin)     { |csv_in|  csv_in.each { |row| p row } }  # from $stdin


Data Conversion¶ ↑

CSV with headers¶ ↑

CSV allows to specify column names of CSV file, whether they are in data, or provided separately. If headers specified, reading methods return an instance of CSV::Table, consisting of CSV::Row.

# Headers are part of data
data = CSV.parse(<<~ROWS, headers: true)
  Name,Department,Salary
  Bob,Engineering,1000
  Jane,Sales,2000
  John,Management,5000
ROWS

data.class      #=> CSV::Table
data.first      #=> #<CSV::Row "Name":"Bob" "Department":"Engineering" "Salary":"1000">
data.first.to_h #=> {"Name"=>"Bob", "Department"=>"Engineering", "Salary"=>"1000"}

# Headers provided by developer
data = CSV.parse('Bob,Engeneering,1000', headers: %i[name department salary])
data.first      #=> #<CSV::Row name:"Bob" department:"Engineering" salary:"1000">


Typed data reading¶ ↑

CSV allows to provide a set of data converters e.g. transformations to try on input data. Converter could be a symbol from CSV::Converters constant's keys, or lambda.

# Without any converters:
CSV.parse('Bob,2018-03-01,100')
#=> [["Bob", "2018-03-01", "100"]]

# With built-in converters:
CSV.parse('Bob,2018-03-01,100', converters: %i[numeric date])
#=> [["Bob", #<Date: 2018-03-01>, 100]]

# With custom converters:
CSV.parse('Bob,2018-03-01,100', converters: [->(v) { Time.parse(v) rescue v }])
#=> [["Bob", 2018-03-01 00:00:00 +0200, "100"]]


CSV and Character Encodings (M17n or Multilingualization)¶ ↑

This new CSV parser is m17n savvy.  The parser works in the Encoding of the IO or String object being read from or written to.  Your data is never transcoded (unless you ask Ruby to transcode it for you) and will literally be parsed in the Encoding it is in.  Thus CSV will return Arrays or Rows of Strings in the Encoding of your data.  This is accomplished by transcoding the parser itself into your Encoding.

Some transcoding must take place, of course, to accomplish this multiencoding support.  For example, :col_sep, :row_sep, and :quote_char must be transcoded to match your data.  Hopefully this makes the entire process feel transparent, since CSV's defaults should just magically work for your data.  However, you can set these values manually in the target Encoding to avoid the translation.

It's also important to note that while all of CSV's core parser is now Encoding agnostic, some features are not.  For example, the built-in converters will try to transcode data to UTF-8 before making conversions. Again, you can provide custom converters that are aware of your Encodings to avoid this translation.  It's just too hard for me to support native conversions in all of Ruby's Encodings.

Anyway, the practical side of this is simple:  make sure IO and String objects passed into CSV have the proper Encoding set and everything should just work. CSV methods that allow you to open IO objects (CSV::foreach(), CSV::open(), CSV::read(), and CSV::readlines()) do allow you to specify the Encoding.

One minor exception comes when generating CSV into a String with an Encoding that is not ASCII compatible.  There's no existing data for CSV to use to prepare itself and thus you will probably need to manually specify the desired Encoding for most of those cases.  It will try to guess using the fields in a row of output though, when using CSV::generate_line() or Array#to_csv().

I try to point out any other Encoding issues in the documentation of methods as they come up.

This has been tested to the best of my ability with all non-“dummy” Encodings Ruby ships with.  However, it is brave new code and may have some bugs. Please feel free to report any issues you find with it.

  


    
The error thrown when the parser encounters illegal CSV formatting.

  


    
A CSV::Row is part Array and part Hash.  It retains an order for the fields and allows duplicates just as an Array would, but also allows you to access fields by name just as you could if they were in a Hash.

All rows returned by CSV will be constructed from this class, if header row processing is activated.

  


    
A CSV::Table is a two-dimensional data structure for representing CSV documents.  Tables allow you to work with the data by row or column, manipulate the data, and even convert the results back to CSV, if needed.

All tables returned by CSV will be constructed from this class, if header row processing is activated.

  


    
Extends any Class to include json_creatable? method.

Classes in Ruby are first-class objects—each is an instance of class Class.

Typically, you create a new class by using:

class Name
 # some code describing the class behavior
end


When a new class is created, an object of type Class is initialized and assigned to a global constant (Name in this case).

When Name.new is called to create a new object, the new method in Class is run by default. This can be demonstrated by overriding new in Class:

class Class
  alias old_new new
  def new(*args)
    print "Creating a new ", self.name, "\n"
    old_new(*args)
  end
end

class Name
end

n = Name.new


produces:

Creating a new Name


Classes, modules, and objects are interrelated. In the diagram that follows, the vertical arrows represent inheritance, and the parentheses metaclasses. All metaclasses are instances of the class `Class'.

                         +---------+             +-...
                         |         |             |
         BasicObject-----|-->(BasicObject)-------|-...
             ^           |         ^             |
             |           |         |             |
          Object---------|----->(Object)---------|-...
             ^           |         ^             |
             |           |         |             |
             +-------+   |         +--------+    |
             |       |   |         |        |    |
             |    Module-|---------|--->(Module)-|-...
             |       ^   |         |        ^    |
             |       |   |         |        |    |
             |     Class-|---------|---->(Class)-|-...
             |       ^   |         |        ^    |
             |       +---+         |        +----+
             |                     |
obj--->OtherClass---------->(OtherClass)-----------...

  


    
The exception class which will be raised when pushing into a closed Queue.  See Queue#close and SizedQueue#close.

  


    
A complex number can be represented as a paired real number with imaginary unit; a+bi.  Where a is real part, b is imaginary part and i is imaginary unit.  Real a equals complex a+0i mathematically.

Complex object can be created as literal, and also by using Kernel#Complex, Complex::rect, Complex::polar or to_c method.

2+1i                 #=> (2+1i)
Complex(1)           #=> (1+0i)
Complex(2, 3)        #=> (2+3i)
Complex.polar(2, 3)  #=> (-1.9799849932008908+0.2822400161197344i)
3.to_c               #=> (3+0i)


You can also create complex object from floating-point numbers or strings.

Complex(0.3)         #=> (0.3+0i)
Complex('0.3-0.5i')  #=> (0.3-0.5i)
Complex('2/3+3/4i')  #=> ((2/3)+(3/4)*i)
Complex('1@2')       #=> (-0.4161468365471424+0.9092974268256817i)

0.3.to_c             #=> (0.3+0i)
'0.3-0.5i'.to_c      #=> (0.3-0.5i)
'2/3+3/4i'.to_c      #=> ((2/3)+(3/4)*i)
'1@2'.to_c           #=> (-0.4161468365471424+0.9092974268256817i)


A complex object is either an exact or an inexact number.

Complex(1, 1) / 2    #=> ((1/2)+(1/2)*i)
Complex(1, 1) / 2.0  #=> (0.5+0.5i)


  


    
ConditionVariable objects augment class Mutex. Using condition variables, it is possible to suspend while in the middle of a critical section until a resource becomes available.

Example:

mutex = Mutex.new
resource = ConditionVariable.new

a = Thread.new {
   mutex.synchronize {
     # Thread 'a' now needs the resource
     resource.wait(mutex)
     # 'a' can now have the resource
   }
}

b = Thread.new {
   mutex.synchronize {
     # Thread 'b' has finished using the resource
     resource.signal
   }
}


  


    
Continuation objects are generated by Kernel#callcc, after having +require+d continuation. They hold a return address and execution context, allowing a nonlocal return to the end of the callcc block from anywhere within a program. Continuations are somewhat analogous to a structured version of C's setjmp/longjmp (although they contain more state, so you might consider them closer to threads).

For instance:

require "continuation"
arr = [ "Freddie", "Herbie", "Ron", "Max", "Ringo" ]
callcc{|cc| $cc = cc}
puts(message = arr.shift)
$cc.call unless message =~ /Max/


produces:

Freddie
Herbie
Ron
Max


Also you can call callcc in other methods:

require "continuation"

def g
  arr = [ "Freddie", "Herbie", "Ron", "Max", "Ringo" ]
  cc = callcc { |cc| cc }
  puts arr.shift
  return cc, arr.size
end

def f
  c, size = g
  c.call(c) if size > 1
end

f


This (somewhat contrived) example allows the inner loop to abandon processing early:

require "continuation"
callcc {|cont|
  for i in 0..4
    print "\n#{i}: "
    for j in i*5...(i+1)*5
      cont.call() if j == 17
      printf "%3d", j
    end
  end
}
puts


produces:

0:   0  1  2  3  4
1:   5  6  7  8  9
2:  10 11 12 13 14
3:  15 16

  


    
Introduction¶ ↑

The DBM class provides a wrapper to a Unix-style dbm or Database Manager library.

Dbm databases do not have tables or columns; they are simple key-value data stores, like a Ruby Hash except not resident in RAM. Keys and values must be strings.

The exact library used depends on how Ruby was compiled. It could be any of the following:

The original ndbm library is released in 4.3BSD. It is based on dbm library in Unix Version 7 but has different API to support multiple databases in a process.

Berkeley DB versions 1 thru 6, also known as BDB and Sleepycat DB, now owned by Oracle Corporation.

Berkeley DB 1.x, still found in 4.4BSD derivatives (FreeBSD, OpenBSD, etc).

gdbm, the GNU implementation of dbm.

qdbm, another open source reimplementation of dbm.


All of these dbm implementations have their own Ruby interfaces available, which provide richer (but varying) APIs.

Cautions¶ ↑

Before you decide to use DBM, there are some issues you should consider:

Each implementation of dbm has its own file format. Generally, dbm libraries will not read each other's files. This makes dbm files a bad choice for data exchange.

Even running the same OS and the same dbm implementation, the database file format may depend on the CPU architecture. For example, files may not be portable between PowerPC and 386, or between 32 and 64 bit Linux.

Different versions of Berkeley DB use different file formats. A change to the OS may therefore break DBM access to existing files.

Data size limits vary between implementations. Original Berkeley DB was limited to 2GB of data. Dbm libraries also sometimes limit the total size of a key/value pair, and the total size of all the keys that hash to the same value. These limits can be as little as 512 bytes. That said, gdbm and recent versions of Berkeley DB do away with these limits.


Given the above cautions, DBM is not a good choice for long term storage of important data. It is probably best used as a fast and easy alternative to a Hash for processing large amounts of data.

Example¶ ↑

require 'dbm'
db = DBM.open('rfcs', 0666, DBM::WRCREAT)
db['822'] = 'Standard for the Format of ARPA Internet Text Messages'
db['1123'] = 'Requirements for Internet Hosts - Application and Support'
db['3068'] = 'An Anycast Prefix for 6to4 Relay Routers'
puts db['822']


  


    
Exception class used to return errors from the dbm library.

  


    
This library provides debugging functionality to Ruby.

To add a debugger to your code, start by requiring debug in your program:

def say(word)
  require 'debug'
  puts word
end


This will cause Ruby to interrupt execution and show a prompt when the say method is run.

Once you're inside the prompt, you can start debugging your program.

(rdb:1) p word
"hello"

Getting help¶ ↑

You can get help at any time by pressing h.

(rdb:1) h
Debugger help v.-0.002b
Commands
  b[reak] [file:|class:]<line|method>
  b[reak] [class.]<line|method>
                             set breakpoint to some position
  wat[ch] <expression>       set watchpoint to some expression
  cat[ch] (<exception>|off)  set catchpoint to an exception
  b[reak]                    list breakpoints
  cat[ch]                    show catchpoint
  del[ete][ nnn]             delete some or all breakpoints
  disp[lay] <expression>     add expression into display expression list
  undisp[lay][ nnn]          delete one particular or all display expressions
  c[ont]                     run until program ends or hit breakpoint
  s[tep][ nnn]               step (into methods) one line or till line nnn
  n[ext][ nnn]               go over one line or till line nnn
  w[here]                    display frames
  f[rame]                    alias for where
  l[ist][ (-|nn-mm)]         list program, - lists backwards
                             nn-mm lists given lines
  up[ nn]                    move to higher frame
  down[ nn]                  move to lower frame
  fin[ish]                   return to outer frame
  tr[ace] (on|off)           set trace mode of current thread
  tr[ace] (on|off) all       set trace mode of all threads
  q[uit]                     exit from debugger
  v[ar] g[lobal]             show global variables
  v[ar] l[ocal]              show local variables
  v[ar] i[nstance] <object>  show instance variables of object
  v[ar] c[onst] <object>     show constants of object
  m[ethod] i[nstance] <obj>  show methods of object
  m[ethod] <class|module>    show instance methods of class or module
  th[read] l[ist]            list all threads
  th[read] c[ur[rent]]       show current thread
  th[read] [sw[itch]] <nnn>  switch thread context to nnn
  th[read] stop <nnn>        stop thread nnn
  th[read] resume <nnn>      resume thread nnn
  p expression               evaluate expression and print its value
  h[elp]                     print this help
  <everything else>          evaluate

Usage¶ ↑

The following is a list of common functionalities that the debugger provides.

Navigating through your code¶ ↑

In general, a debugger is used to find bugs in your program, which often means pausing execution and inspecting variables at some point in time.

Let's look at an example:

def my_method(foo)
  require 'debug'
  foo = get_foo if foo.nil?
  raise if foo.nil?
end


When you run this program, the debugger will kick in just before the foo assignment.

(rdb:1) p foo
nil

In this example, it'd be interesting to move to the next line and inspect the value of foo again. You can do that by pressing n:

(rdb:1) n # goes to next line
(rdb:1) p foo
nil

You now know that the original value of foo was nil, and that it still was nil after calling get_foo.

Other useful commands for navigating through your code are:
c

Runs the program until it either exists or encounters another breakpoint. You usually press c when you are finished debugging your program and want to resume its execution.
s

Steps into method definition. In the previous example, s would take you inside the method definition of get_foo.
r

Restart the program.
q

Quit the program.


Inspecting variables¶ ↑

You can use the debugger to easily inspect both local and global variables. We've seen how to inspect local variables before:

(rdb:1) p my_arg
42

You can also pretty print the result of variables or expressions:

(rdb:1) pp %w{a very long long array containing many words}
["a",
 "very",
 "long",
 ...
]

You can list all local variables with +v l+:

(rdb:1) v l
  foo => "hello"

Similarly, you can show all global variables with +v g+:

(rdb:1) v g
  all global variables

Finally, you can omit p if you simply want to evaluate a variable or expression

(rdb:1) 5**2
25

Going beyond basics¶ ↑

Ruby Debug provides more advanced functionalities like switching between threads, setting breakpoints and watch expressions, and more. The full list of commands is available at any time by pressing h.

Staying out of trouble¶ ↑

Make sure you remove every instance of +require 'debug'+ before shipping your code. Failing to do so may result in your program hanging unpredictably.

Debug is not available in safe mode.

  


    
An Array wrapper that can be sent to another server via DRb.

All entries in the array will be dumped or be references that point to the local server.

  


    
Error raised by a dRuby protocol when it doesn't support the scheme specified in a URI.  See DRb::DRbProtocol.

  


    
Error raised by the DRbProtocol module when it cannot find any protocol implementation support the scheme specified in a URI.

  


    
Class handling the connection between a DRbObject and the server the real object lives on.

This class maintains a pool of connections, to reduce the overhead of starting and closing down connections for each method call.

This class is used internally by DRbObject.  The user does not normally need to deal with it directly.

  


    
Error raised when an error occurs on the underlying communication protocol.

  


    
Superclass of all errors raised in the DRb module.

  


    
Class responsible for converting between an object and its id.

This, the default implementation, uses an object's local ObjectSpace __id__ as its id.  This means that an object's identification over drb remains valid only while that object instance remains alive within the server runtime.

For alternative mechanisms, see DRb::TimerIdConv in drb/timeridconv.rb and DRbNameIdConv in sample/name.rb in the full drb distribution.

  


    
Class responsible for converting between an object and its id.

This, the default implementation, uses an object's local ObjectSpace __id__ as its id.  This means that an object's identification over drb remains valid only while that object instance remains alive within the server runtime.

For alternative mechanisms, see DRb::TimerIdConv in drb/timeridconv.rb and DRbNameIdConv in sample/name.rb in the full drb distribution.

  


    
Handler for sending and receiving drb messages.

This takes care of the low-level marshalling and unmarshalling of drb requests and responses sent over the wire between server and client.  This relieves the implementor of a new drb protocol layer with having to deal with these details.

The user does not have to directly deal with this object in normal use.

  


    
Object wrapping a reference to a remote drb object.

Method calls on this object are relayed to the remote object that this object is a stub for.

  


    
Object wrapping a reference to a remote drb object.

Method calls on this object are relayed to the remote object that this object is a stub for.

  


    
An exception wrapping an error object

  


    
The protocol for DRb over an SSL socket

The URI for a DRb socket over SSL is: drbssl://<host>:<port>?<option>.  The option is optional

  


    
SSLConfig handles the needed SSL information for establishing a DRbSSLSocket connection, including generating the X509 / RSA pair.

An instance of this config can be passed to DRbSSLSocket.new, DRbSSLSocket.open and DRbSSLSocket.open_server

See DRb::DRbSSLSocket::SSLConfig.new for more details

  


    
Error raised by the DRb module when an attempt is made to refer to the context's current drb server but the context does not have one. See current_server.

  


    
The default drb protocol which communicates over a TCP socket.

The DRb TCP protocol URI looks like: druby://<host>:<port>?<option>.  The option is optional.

  


    
Implements DRb over a UNIX socket

DRb UNIX socket URIs look like drbunix:<path>?<option>.  The option is optional.

  


    
Class wrapping a marshalled object whose type is unknown locally.

If an object is returned by a method invoked over drb, but the class of the object is unknown in the client namespace, or the object is a constant unknown in the client namespace, then the still-marshalled object is returned wrapped in a DRbUnknown instance.

If this object is passed as an argument to a method invoked over drb, then the wrapped object is passed instead.

The class or constant name of the object can be read from the name attribute.  The marshalled object is held in the buf attribute.

  


    
An exception wrapping a DRb::DRbUnknown object

  


    
The GW provides a synchronized store for participants in the gateway to communicate.

  


    
Gateway id conversion forms a gateway between different DRb protocols or networks.

The gateway needs to install this id conversion and create servers for each of the protocols or networks it will be a gateway between.  It then needs to create a server that attaches to each of these networks.  For example:

require 'drb/drb'
require 'drb/unix'
require 'drb/gw'

DRb.install_id_conv DRb::GWIdConv.new
gw = DRb::GW.new
s1 = DRb::DRbServer.new 'drbunix:/path/to/gateway', gw
s2 = DRb::DRbServer.new 'druby://example:10000', gw

s1.thread.join
s2.thread.join


Each client must register services with the gateway, for example:

DRb.start_service 'drbunix:', nil # an anonymous server
gw = DRbObject.new nil, 'drbunix:/path/to/gateway'
gw[:unix] = some_service
DRb.thread.join


  


    
Timer id conversion keeps objects alive for a certain amount of time after their last access.  The default time period is 600 seconds and can be changed upon initialization.

To use TimerIdConv:

DRb.install_id_conv TimerIdConv.new 60 # one minute


  


    
This is a deprecated class, base class for C extensions using Data_Make_Struct or Data_Wrap_Struct.

  


    
date and datetime class - Tadayoshi Funaba 1998-2011

'date' provides two classes: Date and DateTime.

Terms and Definitions¶ ↑

Some terms and definitions are based on ISO 8601 and JIS X 0301.

Calendar Date¶ ↑

The calendar date is a particular day of a calendar year, identified by its ordinal number within a calendar month within that year.

In those classes, this is so-called “civil”.

Ordinal Date¶ ↑

The ordinal date is a particular day of a calendar year identified by its ordinal number within the year.

In those classes, this is so-called “ordinal”.

Week Date¶ ↑

The week date is a date identified by calendar week and day numbers.

The calendar week is a seven day period within a calendar year, starting on a Monday and identified by its ordinal number within the year; the first calendar week of the year is the one that includes the first Thursday of that year. In the Gregorian calendar, this is equivalent to the week which includes January 4.

In those classes, this is so-called “commercial”.

Julian Day Number¶ ↑

The Julian day number is in elapsed days since noon (Greenwich Mean Time) on January 1, 4713 BCE (in the Julian calendar).

In this document, the astronomical Julian day number is the same as the original Julian day number. And the chronological Julian day number is a variation of the Julian day number. Its days begin at midnight on local time.

In this document, when the term “Julian day number” simply appears, it just refers to “chronological Julian day number”, not the original.

In those classes, those are so-called “ajd” and “jd”.

Modified Julian Day Number¶ ↑

The modified Julian day number is in elapsed days since midnight (Coordinated Universal Time) on November 17, 1858 CE (in the Gregorian calendar).

In this document, the astronomical modified Julian day number is the same as the original modified Julian day number. And the chronological modified Julian day number is a variation of the modified Julian day number. Its days begin at midnight on local time.

In this document, when the term “modified Julian day number” simply appears, it just refers to “chronological modified Julian day number”, not the original.

In those classes, those are so-called “amjd” and “mjd”.

Date¶ ↑

A subclass of Object that includes the Comparable module and easily handles date.

A Date object is created with Date::new, Date::jd, Date::ordinal, Date::commercial, Date::parse, Date::strptime, Date::today, Time#to_date, etc.

require 'date'

Date.new(2001,2,3)
 #=> #<Date: 2001-02-03 ...>
Date.jd(2451944)
 #=> #<Date: 2001-02-03 ...>
Date.ordinal(2001,34)
 #=> #<Date: 2001-02-03 ...>
Date.commercial(2001,5,6)
 #=> #<Date: 2001-02-03 ...>
Date.parse('2001-02-03')
 #=> #<Date: 2001-02-03 ...>
Date.strptime('03-02-2001', '%d-%m-%Y')
 #=> #<Date: 2001-02-03 ...>
Time.new(2001,2,3).to_date
 #=> #<Date: 2001-02-03 ...>


All date objects are immutable; hence cannot modify themselves.

The concept of a date object can be represented as a tuple of the day count, the offset and the day of calendar reform.

The day count denotes the absolute position of a temporal dimension. The offset is relative adjustment, which determines decoded local time with the day count. The day of calendar reform denotes the start day of the new style. The old style of the West is the Julian calendar which was adopted by Caesar. The new style is the Gregorian calendar, which is the current civil calendar of many countries.

The day count is virtually the astronomical Julian day number. The offset in this class is usually zero, and cannot be specified directly.

A Date object can be created with an optional argument, the day of calendar reform as a Julian day number, which should be 2298874 to 2426355 or negative/positive infinity. The default value is Date::ITALY (2299161=1582-10-15). See also sample/cal.rb.

$ ruby sample/cal.rb -c it 10 1582
    October 1582
 S  M Tu  W Th  F  S
    1  2  3  4 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30
31

$ ruby sample/cal.rb -c gb  9 1752
   September 1752
 S  M Tu  W Th  F  S
       1  2 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30

A Date object has various methods. See each reference.

d = Date.parse('3rd Feb 2001')
                             #=> #<Date: 2001-02-03 ...>
d.year                       #=> 2001
d.mon                        #=> 2
d.mday                       #=> 3
d.wday                       #=> 6
d += 1                       #=> #<Date: 2001-02-04 ...>
d.strftime('%a %d %b %Y')    #=> "Sun 04 Feb 2001"


  


    
DateTime¶ ↑

A subclass of Date that easily handles date, hour, minute, second, and offset.

DateTime does not consider any leap seconds, does not track any summer time rules.

A DateTime object is created with DateTime::new, DateTime::jd, DateTime::ordinal, DateTime::commercial, DateTime::parse, DateTime::strptime, DateTime::now, Time#to_datetime, etc.

require 'date'

DateTime.new(2001,2,3,4,5,6)
                    #=> #<DateTime: 2001-02-03T04:05:06+00:00 ...>


The last element of day, hour, minute, or second can be a fractional number. The fractional number's precision is assumed at most nanosecond.

DateTime.new(2001,2,3.5)
                    #=> #<DateTime: 2001-02-03T12:00:00+00:00 ...>


An optional argument, the offset, indicates the difference between the local time and UTC. For example, Rational(3,24) represents ahead of 3 hours of UTC, Rational(-5,24) represents behind of 5 hours of UTC. The offset should be -1 to +1, and its precision is assumed at most second. The default value is zero (equals to UTC).

DateTime.new(2001,2,3,4,5,6,Rational(3,24))
                    #=> #<DateTime: 2001-02-03T04:05:06+03:00 ...>


The offset also accepts string form:

DateTime.new(2001,2,3,4,5,6,'+03:00')
                    #=> #<DateTime: 2001-02-03T04:05:06+03:00 ...>


An optional argument, the day of calendar reform (start), denotes a Julian day number, which should be 2298874 to 2426355 or negative/positive infinity. The default value is Date::ITALY (2299161=1582-10-15).

A DateTime object has various methods. See each reference.

d = DateTime.parse('3rd Feb 2001 04:05:06+03:30')
                    #=> #<DateTime: 2001-02-03T04:05:06+03:30 ...>
d.hour              #=> 4
d.min               #=> 5
d.sec               #=> 6
d.offset            #=> (7/48)
d.zone              #=> "+03:30"
d += Rational('1.5')
                    #=> #<DateTime: 2001-02-04%16:05:06+03:30 ...>
d = d.new_offset('+09:00')
                    #=> #<DateTime: 2001-02-04%21:35:06+09:00 ...>
d.strftime('%I:%M:%S %p')
                    #=> "09:35:06 PM"
d > DateTime.new(1999)
                    #=> true


When should you use DateTime and when should you use Time?¶ ↑

It's a common misconception that William Shakespeare and Miguel de Cervantes died on the same day in history - so much so that UNESCO named April 23 as World Book Day because of this fact. However, because England hadn't yet adopted the Gregorian Calendar Reform (and wouldn't until 1752) their deaths are actually 10 days apart. Since Ruby's Time class implements a proleptic Gregorian calendar and has no concept of calendar reform there's no way to express this with Time objects. This is where DateTime steps in:

shakespeare = DateTime.iso8601('1616-04-23', Date::ENGLAND)
 #=> Tue, 23 Apr 1616 00:00:00 +0000
cervantes = DateTime.iso8601('1616-04-23', Date::ITALY)
 #=> Sat, 23 Apr 1616 00:00:00 +0000


Already you can see something is weird - the days of the week are different. Taking this further:

cervantes == shakespeare
 #=> false
(shakespeare - cervantes).to_i
 #=> 10


This shows that in fact they died 10 days apart (in reality 11 days since Cervantes died a day earlier but was buried on the 23rd). We can see the actual date of Shakespeare's death by using the gregorian method to convert it:

shakespeare.gregorian
 #=> Tue, 03 May 1616 00:00:00 +0000


So there's an argument that all the celebrations that take place on the 23rd April in Stratford-upon-Avon are actually the wrong date since England is now using the Gregorian calendar. You can see why when we transition across the reform date boundary:

# start off with the anniversary of Shakespeare's birth in 1751
shakespeare = DateTime.iso8601('1751-04-23', Date::ENGLAND)
 #=> Tue, 23 Apr 1751 00:00:00 +0000

# add 366 days since 1752 is a leap year and April 23 is after February 29
shakespeare + 366
 #=> Thu, 23 Apr 1752 00:00:00 +0000

# add another 365 days to take us to the anniversary in 1753
shakespeare + 366 + 365
 #=> Fri, 04 May 1753 00:00:00 +0000


As you can see, if we're accurately tracking the number of solar years since Shakespeare's birthday then the correct anniversary date would be the 4th May and not the 23rd April.

So when should you use DateTime in Ruby and when should you use Time? Almost certainly you'll want to use Time since your app is probably dealing with current dates and times. However, if you need to deal with dates and times in a historical context you'll want to use DateTime to avoid making the same mistakes as UNESCO. If you also have to deal with timezones then best of luck - just bear in mind that you'll probably be dealing with local solar times, since it wasn't until the 19th century that the introduction of the railways necessitated the need for Standard Time and eventually timezones.

  


    
This library provides three different ways to delegate method calls to an object.  The easiest to use is SimpleDelegator.  Pass an object to the constructor and all methods supported by the object will be delegated.  This object can be changed later.

Going a step further, the top level DelegateClass method allows you to easily setup delegation through class inheritance.  This is considerably more flexible and thus probably the most common use for this library.

Finally, if you need full control over the delegation scheme, you can inherit from the abstract class Delegator and customize as needed.  (If you find yourself needing this control, have a look at Forwardable which is also in the standard library.  It may suit your needs better.)

SimpleDelegator's implementation serves as a nice example of the use of Delegator:

class SimpleDelegator < Delegator
  def __getobj__
    @delegate_sd_obj # return object we are delegating to, required
  end

  def __setobj__(obj)
    @delegate_sd_obj = obj # change delegation object,
                           # a feature we're providing
  end
end


Notes¶ ↑

Be advised, RDoc will not detect delegated methods.

  


    
This abstract class provides a common interface to message digest implementation classes written in C.

Write a Digest subclass in C¶ ↑

Digest::Base provides a common interface to message digest classes written in C. These classes must provide a struct of type rb_digest_metadata_t:

typedef int (*rb_digest_hash_init_func_t)(void *);
typedef void (*rb_digest_hash_update_func_t)(void *, unsigned char *, size_t);
typedef int (*rb_digest_hash_finish_func_t)(void *, unsigned char *);

typedef struct {
  int api_version;
  size_t digest_len;
  size_t block_len;
  size_t ctx_size;
  rb_digest_hash_init_func_t init_func;
  rb_digest_hash_update_func_t update_func;
  rb_digest_hash_finish_func_t finish_func;
} rb_digest_metadata_t;

This structure must be set as an instance variable named metadata (without the +@+ in front of the name). By example:

 static const rb_digest_metadata_t sha1 = {
    RUBY_DIGEST_API_VERSION,
    SHA1_DIGEST_LENGTH,
    SHA1_BLOCK_LENGTH,
    sizeof(SHA1_CTX),
    (rb_digest_hash_init_func_t)SHA1_Init,
    (rb_digest_hash_update_func_t)SHA1_Update,
    (rb_digest_hash_finish_func_t)SHA1_Finish,
};

rb_ivar_set(cDigest_SHA1, rb_intern("metadata"),
            Data_Wrap_Struct(0, 0, 0, (void *)&sha1));

  


    
This module stands as a base class for digest implementation classes.

  


    
A class for calculating message digests using the MD5 Message-Digest Algorithm by RSA Data Security, Inc., described in RFC1321.

MD5 calculates a digest of 128 bits (16 bytes).

Examples¶ ↑

require 'digest'

# Compute a complete digest
Digest::MD5.hexdigest 'abc'      #=> "90015098..."

# Compute digest by chunks
md5 = Digest::MD5.new               # =>#<Digest::MD5>
md5.update "ab"
md5 << "c"                           # alias for #update
md5.hexdigest                        # => "90015098..."

# Use the same object to compute another digest
md5.reset
md5 << "message"
md5.hexdigest                        # => "78e73102..."


  


    
A class for calculating message digests using RIPEMD-160 cryptographic hash function, designed by Hans Dobbertin, Antoon Bosselaers, and Bart Preneel.

RMD160 calculates a digest of 160 bits (20 bytes).

Examples¶ ↑

require 'digest'

# Compute a complete digest
Digest::RMD160.hexdigest 'abc'      #=> "8eb208f7..."

# Compute digest by chunks
rmd160 = Digest::RMD160.new               # =>#<Digest::RMD160>
rmd160.update "ab"
rmd160 << "c"                           # alias for #update
rmd160.hexdigest                        # => "8eb208f7..."

# Use the same object to compute another digest
rmd160.reset
rmd160 << "message"
rmd160.hexdigest                        # => "1dddbe1b..."


  


    
A class for calculating message digests using the SHA-1 Secure Hash Algorithm by NIST (the US' National Institute of Standards and Technology), described in FIPS PUB 180-1.

See Digest::Instance for digest API.

SHA-1 calculates a digest of 160 bits (20 bytes).

Examples¶ ↑

require 'digest'

# Compute a complete digest
Digest::SHA1.hexdigest 'abc'      #=> "a9993e36..."

# Compute digest by chunks
sha1 = Digest::SHA1.new               # =>#<Digest::SHA1>
sha1.update "ab"
sha1 << "c"                           # alias for #update
sha1.hexdigest                        # => "a9993e36..."

# Use the same object to compute another digest
sha1.reset
sha1 << "message"
sha1.hexdigest                        # => "6f9b9af3..."


  


    
Objects of class Dir are directory streams representing directories in the underlying file system. They provide a variety of ways to list directories and their contents. See also File.

The directory used in these examples contains the two regular files (config.h and main.rb), the parent directory (..), and the directory itself (.).

  


    
ENV is a hash-like accessor for environment variables.

  


    
Raised by some IO operations when reaching the end of file. Many IO methods exist in two forms,

one that returns nil when the end of file is reached, the other raises EOFError.

EOFError is a subclass of IOError.

file = File.open("/etc/hosts")
file.read
file.gets     #=> nil
file.readline #=> EOFError: end of file reached


  


    
ERB – Ruby Templating¶ ↑

Introduction¶ ↑

ERB provides an easy to use but powerful templating system for Ruby.  Using ERB, actual Ruby code can be added to any plain text document for the purposes of generating document information details and/or flow control.

A very simple example is this:

require 'erb'

x = 42
template = ERB.new <<-EOF
  The value of x is: <%= x %>
EOF
puts template.result(binding)


Prints: The value of x is: 42

More complex examples are given below.

Recognized Tags¶ ↑

ERB recognizes certain tags in the provided template and converts them based on the rules below:

<% Ruby code -- inline with output %>
<%= Ruby expression -- replace with result %>
<%# comment -- ignored -- useful in testing %>
% a line of Ruby code -- treated as <% line %> (optional -- see ERB.new)
%% replaced with % if first thing on a line and % processing is used
<%% or %%> -- replace with <% or %> respectively

All other text is passed through ERB filtering unchanged.

Options¶ ↑

There are several settings you can change when you use ERB:

the nature of the tags that are recognized;

the value of $SAFE under which the template is run;

the binding used to resolve local variables in the template.


See the ERB.new and ERB#result methods for more detail.

Character encodings¶ ↑

ERB (or Ruby code generated by ERB) returns a string in the same character encoding as the input string.  When the input string has a magic comment, however, it returns a string in the encoding specified by the magic comment.

# -*- coding: utf-8 -*-
require 'erb'

template = ERB.new <<EOF
<%#-*- coding: Big5 -*-%>
  \_\_ENCODING\_\_ is <%= \_\_ENCODING\_\_ %>.
EOF
puts template.result


Prints: _ENCODING_ is Big5.

Examples¶ ↑

Plain Text¶ ↑

ERB is useful for any generic templating situation.  Note that in this example, we use the convenient “% at start of line” tag, and we quote the template literally with %q{...} to avoid trouble with the backslash.

require "erb"

# Create template.
template = %q{
  From:  James Edward Gray II <james@grayproductions.net>
  To:  <%= to %>
  Subject:  Addressing Needs

  <%= to[/\w+/] %>:

  Just wanted to send a quick note assuring that your needs are being
  addressed.

  I want you to know that my team will keep working on the issues,
  especially:

  <%# ignore numerous minor requests -- focus on priorities %>
  % priorities.each do |priority|
    * <%= priority %>
  % end

  Thanks for your patience.

  James Edward Gray II
}.gsub(/^  /, '')

message = ERB.new(template, trim_mode: "%<>")

# Set up template data.
to = "Community Spokesman <spokesman@ruby_community.org>"
priorities = [ "Run Ruby Quiz",
               "Document Modules",
               "Answer Questions on Ruby Talk" ]

# Produce result.
email = message.result
puts email


Generates:

From:  James Edward Gray II <james@grayproductions.net>
To:  Community Spokesman <spokesman@ruby_community.org>
Subject:  Addressing Needs

Community:

Just wanted to send a quick note assuring that your needs are being addressed.

I want you to know that my team will keep working on the issues, especially:

    * Run Ruby Quiz
    * Document Modules
    * Answer Questions on Ruby Talk

Thanks for your patience.

James Edward Gray II

Ruby in HTML¶ ↑

ERB is often used in .rhtml files (HTML with embedded Ruby).  Notice the need in this example to provide a special binding when the template is run, so that the instance variables in the Product object can be resolved.

require "erb"

# Build template data class.
class Product
  def initialize( code, name, desc, cost )
    @code = code
    @name = name
    @desc = desc
    @cost = cost

    @features = [ ]
  end

  def add_feature( feature )
    @features << feature
  end

  # Support templating of member data.
  def get_binding
    binding
  end

  # ...
end

# Create template.
template = %{
  <html>
    <head><title>Ruby Toys -- <%= @name %></title></head>
    <body>

      <h1><%= @name %> (<%= @code %>)</h1>
      <p><%= @desc %></p>

      <ul>
        <% @features.each do |f| %>
          <li><b><%= f %></b></li>
        <% end %>
      </ul>

      <p>
        <% if @cost < 10 %>
          <b>Only <%= @cost %>!!!</b>
        <% else %>
           Call for a price, today!
        <% end %>
      </p>

    </body>
  </html>
}.gsub(/^  /, '')

rhtml = ERB.new(template)

# Set up template data.
toy = Product.new( "TZ-1002",
                   "Rubysapien",
                   "Geek's Best Friend!  Responds to Ruby commands...",
                   999.95 )
toy.add_feature("Listens for verbal commands in the Ruby language!")
toy.add_feature("Ignores Perl, Java, and all C variants.")
toy.add_feature("Karate-Chop Action!!!")
toy.add_feature("Matz signature on left leg.")
toy.add_feature("Gem studded eyes... Rubies, of course!")

# Produce result.
rhtml.run(toy.get_binding)


Generates (some blank lines removed):

<html>
  <head><title>Ruby Toys -- Rubysapien</title></head>
  <body>

    <h1>Rubysapien (TZ-1002)</h1>
    <p>Geek's Best Friend!  Responds to Ruby commands...</p>

    <ul>
        <li><b>Listens for verbal commands in the Ruby language!</b></li>
        <li><b>Ignores Perl, Java, and all C variants.</b></li>
        <li><b>Karate-Chop Action!!!</b></li>
        <li><b>Matz signature on left leg.</b></li>
        <li><b>Gem studded eyes... Rubies, of course!</b></li>
    </ul>

    <p>
         Call for a price, today!
    </p>

  </body>
</html>

Notes¶ ↑

There are a variety of templating solutions available in various Ruby projects:

ERB's big brother, eRuby, works the same but is written in C for speed;

Amrita (smart at producing HTML/XML);

cs/Template (written in C for speed);

RDoc, distributed with Ruby, uses its own template engine, which can be reused elsewhere;

and others; search RubyGems.org or The Ruby Toolbox.


Rails, the web application framework, uses ERB to create views.

  


    
An Encoding instance represents a character encoding usable in Ruby. It is defined as a constant under the Encoding namespace. It has a name and optionally, aliases:

Encoding::ISO_8859_1.name
#=> "ISO-8859-1"

Encoding::ISO_8859_1.names
#=> ["ISO-8859-1", "ISO8859-1"]


Ruby methods dealing with encodings return or accept Encoding instances as arguments (when a method accepts an Encoding instance as an argument, it can be passed an Encoding name or alias instead).

"some string".encoding
#=> #<Encoding:UTF-8>

string = "some string".encode(Encoding::ISO_8859_1)
#=> "some string"
string.encoding
#=> #<Encoding:ISO-8859-1>

"some string".encode "ISO-8859-1"
#=> "some string"


Encoding::ASCII_8BIT is a special encoding that is usually used for a byte string, not a character string. But as the name insists, its characters in the range of ASCII are considered as ASCII characters. This is useful when you use ASCII-8BIT characters with other ASCII compatible characters.

Changing an encoding¶ ↑

The associated Encoding of a String can be changed in two different ways.

First, it is possible to set the Encoding of a string to a new Encoding without changing the internal byte representation of the string, with String#force_encoding. This is how you can tell Ruby the correct encoding of a string.

string
#=> "R\xC3\xA9sum\xC3\xA9"
string.encoding
#=> #<Encoding:ISO-8859-1>
string.force_encoding(Encoding::UTF_8)
#=> "R\u00E9sum\u00E9"


Second, it is possible to transcode a string, i.e. translate its internal byte representation to another encoding. Its associated encoding is also set to the other encoding. See String#encode for the various forms of transcoding, and the Encoding::Converter class for additional control over the transcoding process.

string
#=> "R\u00E9sum\u00E9"
string.encoding
#=> #<Encoding:UTF-8>
string = string.encode!(Encoding::ISO_8859_1)
#=> "R\xE9sum\xE9"
string.encoding
#=> #<Encoding::ISO-8859-1>


Script encoding¶ ↑

All Ruby script code has an associated Encoding which any String literal created in the source code will be associated to.

The default script encoding is Encoding::UTF-8 after v2.0, but it can be changed by a magic comment on the first line of the source code file (or second line, if there is a shebang line on the first). The comment must contain the word coding or encoding, followed by a colon, space and the Encoding name or alias:

# encoding: UTF-8

"some string".encoding
#=> #<Encoding:UTF-8>


The __ENCODING__ keyword returns the script encoding of the file which the keyword is written:

# encoding: ISO-8859-1

__ENCODING__
#=> #<Encoding:ISO-8859-1>


ruby -K will change the default locale encoding, but this is not recommended. Ruby source files should declare its script encoding by a magic comment even when they only depend on US-ASCII strings or regular expressions.

Locale encoding¶ ↑

The default encoding of the environment. Usually derived from locale.

see Encoding.locale_charmap, Encoding.find('locale')

Filesystem encoding¶ ↑

The default encoding of strings from the filesystem of the environment. This is used for strings of file names or paths.

see Encoding.find('filesystem')

External encoding¶ ↑

Each IO object has an external encoding which indicates the encoding that Ruby will use to read its data. By default Ruby sets the external encoding of an IO object to the default external encoding. The default external encoding is set by locale encoding or the interpreter -E option. Encoding.default_external returns the current value of the external encoding.

ENV["LANG"]
#=> "UTF-8"
Encoding.default_external
#=> #<Encoding:UTF-8>

$ ruby -E ISO-8859-1 -e "p Encoding.default_external"
#<Encoding:ISO-8859-1>

$ LANG=C ruby -e 'p Encoding.default_external'
#<Encoding:US-ASCII>

The default external encoding may also be set through Encoding.default_external=, but you should not do this as strings created before and after the change will have inconsistent encodings.  Instead use ruby -E to invoke ruby with the correct external encoding.

When you know that the actual encoding of the data of an IO object is not the default external encoding, you can reset its external encoding with IO#set_encoding or set it at IO object creation (see IO.new options).

Internal encoding¶ ↑

To process the data of an IO object which has an encoding different from its external encoding, you can set its internal encoding. Ruby will use this internal encoding to transcode the data when it is read from the IO object.

Conversely, when data is written to the IO object it is transcoded from the internal encoding to the external encoding of the IO object.

The internal encoding of an IO object can be set with IO#set_encoding or at IO object creation (see IO.new options).

The internal encoding is optional and when not set, the Ruby default internal encoding is used. If not explicitly set this default internal encoding is nil meaning that by default, no transcoding occurs.

The default internal encoding can be set with the interpreter option -E. Encoding.default_internal returns the current internal encoding.

$ ruby -e 'p Encoding.default_internal'
nil

$ ruby -E ISO-8859-1:UTF-8 -e "p [Encoding.default_external, \
  Encoding.default_internal]"
[#<Encoding:ISO-8859-1>, #<Encoding:UTF-8>]

The default internal encoding may also be set through Encoding.default_internal=, but you should not do this as strings created before and after the change will have inconsistent encodings.  Instead use ruby -E to invoke ruby with the correct internal encoding.

IO encoding example¶ ↑

In the following example a UTF-8 encoded string “Ru00E9sumu00E9” is transcoded for output to ISO-8859-1 encoding, then read back in and transcoded to UTF-8:

string = "R\u00E9sum\u00E9"

open("transcoded.txt", "w:ISO-8859-1") do |io|
  io.write(string)
end

puts "raw text:"
p File.binread("transcoded.txt")
puts

open("transcoded.txt", "r:ISO-8859-1:UTF-8") do |io|
  puts "transcoded text:"
  p io.read
end


While writing the file, the internal encoding is not specified as it is only necessary for reading.  While reading the file both the internal and external encoding must be specified to obtain the correct result.

$ ruby t.rb
raw text:
"R\xE9sum\xE9"

transcoded text:
"R\u00E9sum\u00E9"

  


    
Raised by Encoding and String methods when the source encoding is incompatible with the target encoding.

  


    
Encoding conversion class.

  


    
Raised by transcoding methods when a named encoding does not correspond with a known converter.

  


    
Raised by Encoding and String methods when the string being transcoded contains a byte invalid for the either the source or target encoding.

  


    
Raised by Encoding and String methods when a transcoding operation fails.

  


    
EncodingError is the base class for encoding errors.

  


    
A class which allows both internal and external iteration.

An Enumerator can be created by the following methods.

Kernel#to_enum

Kernel#enum_for

Enumerator.new


Most methods have two forms: a block form where the contents are evaluated for each item in the enumeration, and a non-block form which returns a new Enumerator wrapping the iteration.

enumerator = %w(one two three).each
puts enumerator.class # => Enumerator

enumerator.each_with_object("foo") do |item, obj|
  puts "#{obj}: #{item}"
end

# foo: one
# foo: two
# foo: three

enum_with_obj = enumerator.each_with_object("foo")
puts enum_with_obj.class # => Enumerator

enum_with_obj.each do |item, obj|
  puts "#{obj}: #{item}"
end

# foo: one
# foo: two
# foo: three


This allows you to chain Enumerators together.  For example, you can map a list's elements to strings containing the index and the element as a string via:

puts %w[foo bar baz].map.with_index { |w, i| "#{i}:#{w}" }
# => ["0:foo", "1:bar", "2:baz"]


An Enumerator can also be used as an external iterator. For example, Enumerator#next returns the next value of the iterator or raises StopIteration if the Enumerator is at the end.

e = [1,2,3].each   # returns an enumerator object.
puts e.next   # => 1
puts e.next   # => 2
puts e.next   # => 3
puts e.next   # raises StopIteration


You can use this to implement an internal iterator as follows:

def ext_each(e)
  while true
    begin
      vs = e.next_values
    rescue StopIteration
      return $!.result
    end
    y = yield(*vs)
    e.feed y
  end
end

o = Object.new

def o.each
  puts yield
  puts yield(1)
  puts yield(1, 2)
  3
end

# use o.each as an internal iterator directly.
puts o.each {|*x| puts x; [:b, *x] }
# => [], [:b], [1], [:b, 1], [1, 2], [:b, 1, 2], 3

# convert o.each to an external iterator for
# implementing an internal iterator.
puts ext_each(o.to_enum) {|*x| puts x; [:b, *x] }
# => [], [:b], [1], [:b, 1], [1, 2], [:b, 1, 2], 3


  


    
Enumerator::ArithmeticSequence is a subclass of Enumerator, that is a representation of sequences of numbers with common difference. Instances of this class can be generated by the Range#step and Numeric#step methods.

  


    
Enumerator::Chain is a subclass of Enumerator, which represents a chain of enumerables that works as a single enumerator.

This type of objects can be created by Enumerable#chain and Enumerator#+.

  


    
Generator

  


    
Lazy

  


    
Yielder

  


    
Client sent TCP reset (RST) before server has accepted the connection requested by client.

  


    
Remote host reset the connection request.

  


    
Protocol error.

  


    
Descendants of class Exception are used to communicate between Kernel#raise and rescue statements in begin ... end blocks. Exception objects carry information about the exception – its type (the exception's class name), an optional descriptive string, and optional traceback information.  Exception subclasses may add additional information like NameError#name.

Programs may make subclasses of Exception, typically of StandardError or RuntimeError, to provide custom classes and add additional information. See the subclass list below for defaults for raise and rescue.

When an exception has been raised but not yet handled (in rescue, ensure, at_exit and END blocks) the global variable $! will contain the current exception and $@ contains the current exception's backtrace.

It is recommended that a library should have one subclass of StandardError or RuntimeError and have specific exception types inherit from it.  This allows the user to rescue a generic exception type to catch all exceptions the library may raise even if future versions of the library add new exception subclasses.

For example:

class MyLibrary
  class Error < RuntimeError
  end

  class WidgetError < Error
  end

  class FrobError < Error
  end

end


To handle both WidgetError and FrobError the library user can rescue MyLibrary::Error.

The built-in subclasses of Exception are:

NoMemoryError

ScriptError

LoadError

NotImplementedError

SyntaxError


SecurityError

SignalException

Interrupt


StandardError – default for rescue

ArgumentError

UncaughtThrowError


EncodingError

FiberError

IOError

EOFError


IndexError

KeyError

StopIteration


LocalJumpError

NameError

NoMethodError


RangeError

FloatDomainError


RegexpError

RuntimeError – default for raise

FrozenError


SystemCallError

Errno::*


ThreadError

TypeError

ZeroDivisionError


SystemExit

SystemStackError

fatal – impossible to rescue


  


    
The global value false is the only instance of class FalseClass and represents a logically false value in boolean expressions. The class provides operators allowing false to participate correctly in logical expressions.

  


    
Fibers are primitives for implementing light weight cooperative concurrency in Ruby. Basically they are a means of creating code blocks that can be paused and resumed, much like threads. The main difference is that they are never preempted and that the scheduling must be done by the programmer and not the VM.

As opposed to other stackless light weight concurrency models, each fiber comes with a stack.  This enables the fiber to be paused from deeply nested function calls within the fiber block.  See the ruby(1) manpage to configure the size of the fiber stack(s).

When a fiber is created it will not run automatically. Rather it must be explicitly asked to run using the Fiber#resume method. The code running inside the fiber can give up control by calling Fiber.yield in which case it yields control back to caller (the caller of the Fiber#resume).

Upon yielding or termination the Fiber returns the value of the last executed expression

For instance:

fiber = Fiber.new do
  Fiber.yield 1
  2
end

puts fiber.resume
puts fiber.resume
puts fiber.resume


produces

1
2
FiberError: dead fiber called

The Fiber#resume method accepts an arbitrary number of parameters, if it is the first call to resume then they will be passed as block arguments. Otherwise they will be the return value of the call to Fiber.yield

Example:

fiber = Fiber.new do |first|
  second = Fiber.yield first + 2
end

puts fiber.resume 10
puts fiber.resume 14
puts fiber.resume 18


produces

12
14
FiberError: dead fiber called

  


    
Raised when an invalid operation is attempted on a Fiber, in particular when attempting to call/resume a dead fiber, attempting to yield from the root fiber, or calling a fiber across threads.

fiber = Fiber.new{}
fiber.resume #=> nil
fiber.resume #=> FiberError: dead fiber called


  


    
C struct shell

  


    
A C struct wrapper

  


    
C union shell

  


    
A C union wrapper

  


    
Description¶ ↑

An FFI closure wrapper, for handling callbacks.

Example¶ ↑

closure = Class.new(Fiddle::Closure) {
  def call
    10
  end
}.new(Fiddle::TYPE_INT, [])
   #=> #<#<Class:0x0000000150d308>:0x0000000150d240>
func = Fiddle::Function.new(closure, [], Fiddle::TYPE_INT)
   #=> #<Fiddle::Function:0x00000001516e58>
func.call
   #=> 10


  


    
Extends Fiddle::Closure to allow for building the closure in a block

  


    
Used internally by Fiddle::Importer

  


    
standard dynamic load exception

  


    
Description¶ ↑

A representation of a C function

Examples¶ ↑

'strcpy'¶ ↑

@libc = Fiddle.dlopen "/lib/libc.so.6"
   #=> #<Fiddle::Handle:0x00000001d7a8d8>
f = Fiddle::Function.new(
  @libc['strcpy'],
  [Fiddle::TYPE_VOIDP, Fiddle::TYPE_VOIDP],
  Fiddle::TYPE_VOIDP)
   #=> #<Fiddle::Function:0x00000001d8ee00>
buff = "000"
   #=> "000"
str = f.call(buff, "123")
   #=> #<Fiddle::Pointer:0x00000001d0c380 ptr=0x000000018a21b8 size=0 free=0x00000000000000>
str.to_s
=> "123"

ABI check¶ ↑

@libc = Fiddle.dlopen "/lib/libc.so.6"
   #=> #<Fiddle::Handle:0x00000001d7a8d8>
f = Fiddle::Function.new(@libc['strcpy'], [TYPE_VOIDP, TYPE_VOIDP], TYPE_VOIDP)
   #=> #<Fiddle::Function:0x00000001d8ee00>
f.abi == Fiddle::Function::DEFAULT
   #=> true


  


    
The Fiddle::Handle is the manner to access the dynamic library

Example¶ ↑

Setup¶ ↑

libc_so = "/lib64/libc.so.6"
=> "/lib64/libc.so.6"
@handle = Fiddle::Handle.new(libc_so)
=> #<Fiddle::Handle:0x00000000d69ef8>

Setup, with flags¶ ↑

libc_so = "/lib64/libc.so.6"
=> "/lib64/libc.so.6"
@handle = Fiddle::Handle.new(libc_so, Fiddle::RTLD_LAZY | Fiddle::RTLD_GLOBAL)
=> #<Fiddle::Handle:0x00000000d69ef8>

See RTLD_LAZY and RTLD_GLOBAL

Addresses to symbols¶ ↑

strcpy_addr = @handle['strcpy']
=> 140062278451968

or

strcpy_addr = @handle.sym('strcpy')
=> 140062278451968

  


    
Fiddle::Pointer is a class to handle C pointers

  


    
A File is an abstraction of any file object accessible by the program and is closely associated with class IO. File includes the methods of module FileTest as class methods, allowing you to write (for example) File.exist?("foo").

In the description of File methods, permission bits are a platform-specific set of bits that indicate permissions of a file. On Unix-based systems, permissions are viewed as a set of three octets, for the owner, the group, and the rest of the world. For each of these entities, permissions may be set to read, write, or execute the file:

The permission bits 0644 (in octal) would thus be interpreted as read/write for owner, and read-only for group and other. Higher-order bits may also be used to indicate the type of file (plain, directory, pipe, socket, and so on) and various other special features. If the permissions are for a directory, the meaning of the execute bit changes; when set the directory can be searched.

On non-Posix operating systems, there may be only the ability to make a file read-only or read-write. In this case, the remaining permission bits will be synthesized to resemble typical values. For instance, on Windows NT the default permission bits are 0644, which means read/write for owner, read-only for all others. The only change that can be made is to make the file read-only, which is reported as 0444.

Various constants for the methods in File can be found in File::Constants.

  


    
Objects of class File::Stat encapsulate common status information for File objects. The information is recorded at the moment the File::Stat object is created; changes made to the file after that point will not be reflected. File::Stat objects are returned by IO#stat, File::stat, File#lstat, and File::lstat. Many of these methods return platform-specific values, and not all values are meaningful on all systems. See also Kernel#test.

  


    
Float objects represent inexact real numbers using the native architecture's double-precision floating point representation.

Floating point has a different arithmetic and is an inexact number. So you should know its esoteric system. See following:

docs.sun.com/source/806-3568/ncg_goldberg.html

wiki.github.com/rdp/ruby_tutorials_core/ruby-talk-faq#wiki-floats_imprecise

en.wikipedia.org/wiki/Floating_point#Accuracy_problems


  


    
Raised when attempting to convert special float values (in particular Infinity or NaN) to numerical classes which don't support them.

Float::INFINITY.to_r   #=> FloatDomainError: Infinity


  


    
Raised when there is an attempt to modify a frozen object.

[1, 2, 3].freeze << 4


raises the exception:

FrozenError: can't modify frozen Array

  


    
Summary¶ ↑

Ruby extension for GNU dbm (gdbm) – a simple database engine for storing key-value pairs on disk.

Description¶ ↑

GNU dbm is a library for simple databases. A database is a file that stores key-value pairs. Gdbm allows the user to store, retrieve, and delete data by key. It furthermore allows a non-sorted traversal of all key-value pairs. A gdbm database thus provides the same functionality as a hash. As with objects of the Hash class, elements can be accessed with []. Furthermore, GDBM mixes in the Enumerable module, thus providing convenient methods such as find, collect, map, etc.

A process is allowed to open several different databases at the same time. A process can open a database as a “reader” or a “writer”. Whereas a reader has only read-access to the database, a writer has read- and write-access. A database can be accessed either by any number of readers or by exactly one writer at the same time.

Examples¶ ↑

Opening/creating a database, and filling it with some entries:

require 'gdbm'

gdbm = GDBM.new("fruitstore.db")
gdbm["ananas"]    = "3"
gdbm["banana"]    = "8"
gdbm["cranberry"] = "4909"
gdbm.close


Reading out a database:

require 'gdbm'

gdbm = GDBM.new("fruitstore.db")
gdbm.each_pair do |key, value|
  print "#{key}: #{value}\n"
end
gdbm.close


produces

banana: 8
ananas: 3
cranberry: 4909


Links¶ ↑

www.gnu.org/software/gdbm/


  


    
BasicSpecification is an abstract class which implements some common code used by both Specification and StubSpecification.

  


    
Base class for all Gem commands.  When creating a new gem command, define initialize, execute, arguments, defaults_str, description and usage (as appropriate).  See the above mentioned methods for details.

A very good example to look at is Gem::Commands::ContentsCommand

  


    
The command manager registers and installs all the individual sub-commands supported by the gem command.

Extra commands can be provided by writing a rubygems_plugin.rb file in an installed gem.  You should register your command against the Gem::CommandManager instance, like this:

# file rubygems_plugin.rb
require 'rubygems/command_manager'

Gem::CommandManager.instance.register_command :edit


You should put the implementation of your command in rubygems/commands.

# file rubygems/commands/edit_command.rb
class Gem::Commands::EditCommand < Gem::Command
  # ...
end


See Gem::Command for instructions on writing gem commands.

  


    
Generates a index files for use as a gem server.

See `gem help generate_index`

  


    
Gem installer command line tool

See `gem help install`

  


    
An alternate to Gem::Commands::QueryCommand that searches for gems starting with the supplied argument.

  


    
Installs RubyGems itself.  This command is ordinarily only available from a RubyGems checkout or tarball.

  


    
Gem uninstaller command line tool

See `gem help uninstall`

  


    
Gem::ConfigFile RubyGems options and gem command options from gemrc.

gemrc is a YAML file that uses strings to match gem command arguments and symbols to match RubyGems options.

Gem command arguments use a String key that matches the command name and allow you to specify default arguments:

install: --no-rdoc --no-ri
update: --no-rdoc --no-ri

You can use gem: to set default arguments for all commands.

RubyGems options use symbol keys.  Valid options are:
:backtrace

See backtrace
:sources

Sets Gem::sources
:verbose

See verbose
:concurrent_downloads

See concurrent_downloads


gemrc files may exist in various locations and are read and merged in the following order:

system wide (/etc/gemrc)

per user (~/.gemrc)

per environment (gemrc files listed in the GEMRC environment variable)


  


    
Raised when there are conflicting gem specs loaded

  


    
Subclass of StreamUI that instantiates the user interaction using STDIN, STDOUT, and STDERR.

  


    
Installs a gem along with all its dependencies from local and remote gems.

  


    
Gem::DependencyList is used for installing and uninstalling gems in the correct order to avoid conflicts.

  


    
Raised by Gem::Resolver when a Gem::Dependency::Conflict reaches the toplevel.  Indicates which dependencies were incompatible through conflict and conflicting_dependencies

  


    
Cleans up after a partially-failed uninstall or for an invalid Gem::Specification.

If a specification was removed by hand this will remove any remaining files.

If a corrupt specification was installed this will clean up warnings by removing the bogus specification.

  


    
Potentially raised when a specification is validated.

  


    
Base exception class for RubyGems.  All exception raised by RubyGems are a subclass of this one.

  


    
Raised when there is an error while building extensions.

  


    
A fake Gem::RemoteFetcher for use in tests or to avoid real live HTTP requests when testing code that uses RubyGems.

Example:

@fetcher = Gem::FakeFetcher.new
@fetcher.data['http://gems.example.com/yaml'] = source_index.to_yaml
Gem::RemoteFetcher.fetcher = @fetcher

# invoke RubyGems code

paths = @fetcher.paths
assert_equal 'http://gems.example.com/yaml', paths.shift
assert paths.empty?, paths.join(', ')


See RubyGems' tests for more examples of FakeFetcher.

  


    
Signals that a file permission error is preventing the user from operating on the given directory.

  


    
Used to raise parsing and loading errors

  


    
Raised when attempting to uninstall a gem that isn't in GEM_HOME.

  


    
Run an instance of the gem program.

Gem::GemRunner is only intended for internal use by RubyGems itself.  It does not form any public API and may change at any time for any reason.

If you would like to duplicate functionality of `gem` commands, use the classes they call directly.

  


    
Raised by Gem::Resolver when dependencies conflict and create the inability to find a valid possible spec for a request.

  


    
Top level class for building the gem repository index.

  


    
The installer installs the files contained in the .gem into the Gem.home.

Gem::Installer does the work of putting files in all the right places on the filesystem including unpacking the gem into its gem dir, installing the gemspec in the specifications dir, storing the cached gem in the cache dir, and installing either wrappers or symlinks for executables.

The installer invokes pre and post install hooks.  Hooks can be added either through a rubygems_plugin.rb file in an installed gem or via a rubygems/defaults/#{RUBY_ENGINE}.rb or rubygems/defaults/operating_system.rb file.  See Gem.pre_install and Gem.post_install for details.

  


    
A test case for Gem::Installer.

  


    
Potentially raised when a specification is validated.

  


    
Raised when RubyGems is unable to load or activate a gem.  Contains the name and version requirements of the gem that either conflicts with already activated gems or that RubyGems is otherwise unable to activate.

  


    
Raised when trying to activate a gem, and that gem does not exist on the system.  Instead of rescuing from this class, make sure to rescue from the superclass Gem::LoadError to catch all types of load errors.

  


    
Raised when trying to activate a gem, and the gem exists on the system, but not the requested version. Instead of rescuing from this class, make sure to rescue from the superclass Gem::LoadError to catch all types of load errors.

  


    
This Gem::StreamUI subclass records input and output to StringIO for retrieval during tests.

  


    
Raised when you haven't provided enough input to your MockGemUi

  


    
IO wrapper that creates digests of contents written to the IO it wraps.

  


    
The format class knows the guts of the ancient .gem file format and provides the capability to read such ancient gems.

Please pretend this doesn't exist.

  


    
A header for a tar file

  


    
Raised when a tar file is corrupt

  


    
TarReader reads tar files and allows iteration over their items

  


    
Class for reading entries out of a tar file

  


    
Raised if the tar IO is not seekable

  


    
A test case for Gem::Package::Tar* classes

  


    
Allows writing of tar files

  


    
IO wrapper that allows writing a limited amount of data

  


    
IO wrapper that provides only write

  


    
Create a package based upon a Gem::Specification.  Gem packages, as well as zip files and tar/gzipped packages can be produced by this task.

In addition to the Rake targets generated by Rake::PackageTask, a Gem::PackageTask will also generate the following tasks:
“package_dir/name-version.gem”

Create a RubyGems package with the given name and version.


Example using a Gem::Specification:

require 'rubygems'
require 'rubygems/package_task'

spec = Gem::Specification.new do |s|
  s.summary = "Ruby based make-like utility."
  s.name = 'rake'
  s.version = PKG_VERSION
  s.requirements << 'none'
  s.files = PKG_FILES
  s.description = <<-EOF
Rake is a Make-like program implemented in Ruby. Tasks
and dependencies are specified in standard Ruby syntax.
  EOF
end

Gem::PackageTask.new(spec) do |pkg|
  pkg.need_zip = true
  pkg.need_tar = true
end


  


    
Gem::PathSupport facilitates the GEM_HOME and GEM_PATH environment settings to the rest of RubyGems.

  


    
Available list of platforms for targeting Gem installations.

See `gem help platform` for information on platform matching.

  


    
Generated when trying to lookup a gem to indicate that the gem was found, but that it isn't usable on the current platform.

fetch and install read these and report them to the user to aid in figuring out why a gem couldn't be installed.

  


    
Signals that a remote operation cannot be conducted, probably due to not being connected (or just not finding host).

  


    
RemoteFetcher handles the details of fetching gems and gem information from a remote source.

  


    
A FetchError exception wraps up the various possible IO and HTTP failures that could happen while downloading from the internet.

  


    
A FetchError that indicates that the reason for not being able to fetch data was that the host could not be contacted

  


    
Represents an error communicating via HTTP.

  


    
A RequestSet groups a request to activate a set of dependencies.

nokogiri = Gem::Dependency.new 'nokogiri', '~> 1.6'
pg = Gem::Dependency.new 'pg', '~> 0.14'

set = Gem::RequestSet.new nokogiri, pg

requests = set.resolve

p requests.map { |r| r.full_name }
#=> ["nokogiri-1.6.0", "mini_portile-0.5.1", "pg-0.17.0"]


  


    
A semi-compatible DSL for the Bundler Gemfile and Isolate gem dependencies files.

To work with both the Bundler Gemfile and Isolate formats this implementation takes some liberties to allow compatibility with each, most notably in source.

A basic gem dependencies file will look like the following:

source 'https://rubygems.org'

gem 'rails', '3.2.14a
gem 'devise', '~> 2.1', '>= 2.1.3'
gem 'cancan'
gem 'airbrake'
gem 'pg'

RubyGems recommends saving this as gem.deps.rb over Gemfile or Isolate.

To install the gems in this Gemfile use `gem install -g` to install it and create a lockfile.  The lockfile will ensure that when you make changes to your gem dependencies file a minimum amount of change is made to the dependencies of your gems.

RubyGems can activate all the gems in your dependencies file at startup using the RUBYGEMS_GEMDEPS environment variable or through Gem.use_gemdeps. See Gem.use_gemdeps for details and warnings.

See `gem help install` and `gem help gem_dependencies` for further details.

  


    
Parses a gem.deps.rb.lock file and constructs a LockSet containing the dependencies found inside.  If the lock file is missing no LockSet is constructed.

  


    
Raised when a lockfile cannot be parsed

  


    
A Requirement is a set of one or more version restrictions. It supports a few (=, !=, >, <, >=, <=, ~>) different restriction operators.

See Gem::Version for a description on how versions and requirements work together in RubyGems.

  


    
Raised when a bad requirement is encountered

  


    
Given a set of Gem::Dependency objects as needed and a way to query the set of available specs via set, calculates a set of ActivationRequest objects which indicate all the specs that should be activated to meet the all the requirements.

  


    
The global rubygems pool, available via the rubygems.org API. Returns instances of APISpecification.

  


    
Represents a specification retrieved via the rubygems.org API.

This is used to avoid loading the full Specification object when all we need is the name, version, and dependencies.

  


    
Specifies a Specification object that should be activated.  Also contains a dependency that was used to introduce this activation.

  


    
The BestSet chooses the best available method to query a remote index.

It combines IndexSet and APISet

  


    
A ComposedSet allows multiple sets to be queried like a single set.

To create a composed set with any number of sets use:

Gem::Resolver.compose_sets set1, set2


This method will eliminate nesting of composed sets.

  


    
Used internally to indicate that a dependency conflicted with a spec that would be activated.

  


    
A set which represents the installed gems. Respects all the normal settings that control where to look for installed gems.

  


    
Used Internally. Wraps a Dependency object to also track which spec contained the Dependency.

  


    
A GitSet represents gems that are sourced from git repositories.

This is used for gem dependency file support.

Example:

set = Gem::Resolver::GitSet.new
set.add_git_gem 'rake', 'git://example/rake.git', tag: 'rake-10.1.0'


  


    
A GitSpecification represents a gem that is sourced from a git repository and is being loaded through a gem dependencies file through the git: option.

  


    
The global rubygems pool represented via the traditional source index.

  


    
Represents a possible Specification object returned from IndexSet.  Used to delay needed to download full Specification objects when only the name and version are needed.

  


    
An InstalledSpecification represents a gem that is already installed locally.

  


    
A set of gems for installation sourced from remote sources and local .gem files

  


    
A LocalSpecification comes from a .gem file on the local filesystem.

  


    
A set of gems from a gem dependencies lockfile.

  


    
The LockSpecification comes from a lockfile (Gem::RequestSet::Lockfile).

A LockSpecification's dependency information is pre-filled from the lockfile.

  


    
An error caused by attempting to fulfil a dependency that was circular

@note This exception will be thrown iff a {Vertex} is added to a

{DependencyGraph} that has a {DependencyGraph::Vertex#path_to?} an
existing {DependencyGraph::Vertex}

  


    
A directed acyclic graph that is tuned to hold named dependencies

  


    
An action that modifies a {DependencyGraph} that is reversible. @abstract

  


    
@!visibility private (see DependencyGraph#add_edge_no_circular)

  


    
@!visibility private (see DependencyGraph#delete_edge)

  


    
@!visibility private @see DependencyGraph#detach_vertex_named

  


    
A log for dependency graph actions

  


    
@!visibility private @see DependencyGraph#tag

  


    
A vertex in a {DependencyGraph} that encapsulates a {#name} and a {#payload}

  


    
A state that encapsulates a set of {#requirements} with an {Array} of possibilities

  


    
An error caused by searching for a dependency that is completely unknown, i.e. has no versions available whatsoever.

  


    
A state that encapsulates a single possibility to fulfill the given {#requirement}

  


    
This class encapsulates a dependency resolver. The resolver is responsible for determining which set of dependencies to activate, with feedback from the {#specification_provider}

  


    
A specific resolution from a given {Resolver}

  


    
An error that occurred during the resolution process

  


    
An error caused by conflicts in version

  


    
The RequirementList is used to hold the requirements being considered while resolving a set of gems.

The RequirementList acts like a queue where the oldest items are removed first.

  


    
Resolver sets are used to look up specifications (and their dependencies) used in resolution.  This set is abstract.

  


    
The SourceSet chooses the best available method to query a remote index.

Kind off like BestSet but filters the sources for gems

  


    
The Resolver::SpecSpecification contains common functionality for Resolver specifications that are backed by a Gem::Specification.

  


    
A Resolver::Specification contains a subset of the information contained in a Gem::Specification.  Only the information necessary for dependency resolution in the resolver is included.

  


    
A VendorSet represents gems that have been unpacked into a specific directory that contains a gemspec.

This is used for gem dependency file support.

Example:

set = Gem::Resolver::VendorSet.new

set.add_vendor_gem 'rake', 'vendor/rake'


The directory vendor/rake must contain an unpacked rake gem along with a rake.gemspec (watching the given name).

  


    
A VendorSpecification represents a gem that has been unpacked into a project and is being loaded through a gem dependencies file through the path: option.

  


    
Raised when a gem dependencies file specifies a ruby version that does not match the current version.

  


    
Gem::Security default exception type

  


    
A Gem::Security::Policy object encapsulates the settings for verifying signed gem files.  This is the base class.  You can either declare an instance of this or use one of the preset security policies in Gem::Security::Policies.

  


    
The TrustDir manages the trusted certificates for gem signature verification.

  


    
Gem::Server and allows users to serve gems for consumption by `gem –remote-install`.

gem_server starts an HTTP server on the given port and serves the following:

“/” - Browsing of gem spec files for installed gems

“/specs.#{Gem.marshal_version}.gz” - specs name/version/platform index

“/latest_specs.#{Gem.marshal_version}.gz” - latest specs name/version/platform index

“/quick/” - Individual gemspecs

“/gems” - Direct access to download the installable gems

“/rdoc?q=” - Search for installed rdoc documentation


Usage¶ ↑

gem_server = Gem::Server.new Gem.dir, 8089, false
gem_server.run


  


    
SilentUI is a UI choice that is absolutely silent.

  


    
A Source knows how to list and fetch gems from a RubyGems marshal index.

There are other Source subclasses for installed gems, local gems, the bundler dependency API and so-forth.

  


    
A git gem for use in a gem dependencies file.

Example:

source =
  Gem::Source::Git.new 'rake', 'git@example:rake.git', 'rake-10.1.0', false

source.specs


  


    
Represents an installed gem.  This is used for dependency resolution.

  


    
The local source finds gems in the current directory for fulfilling dependencies.

  


    
A Lock source wraps an installed gem's source and sorts before other sources during dependency resolution.  This allows RubyGems to prefer gems from dependency lock files.

  


    
A source representing a single .gem file.  This is used for installation of local gems.

  


    
This represents a vendored source that is similar to an installed gem.

  


    
An error that indicates we weren't able to fetch some data from a source

  


    
The SourceList represents the sources rubygems has been configured to use. A source may be created from an array of sources:

Gem::SourceList.from %w[https://rubygems.example https://internal.example]


Or by adding them:

sources = Gem::SourceList.new
sources << 'https://rubygems.example'


The most common way to get a SourceList is Gem.sources.

  


    
SpecFetcher handles metadata updates from remote gem repositories.

  


    
Raised by the DependencyInstaller when a specific gem cannot be found

  


    
The Specification class contains the information for a Gem.  Typically defined in a .gemspec file or a Rakefile, and looks like this:

Gem::Specification.new do |s|
  s.name        = 'example'
  s.version     = '0.1.0'
  s.licenses    = ['MIT']
  s.summary     = "This is an example!"
  s.description = "Much longer explanation of the example!"
  s.authors     = ["Ruby Coder"]
  s.email       = 'rubycoder@example.com'
  s.files       = ["lib/example.rb"]
  s.homepage    = 'https://rubygems.org/gems/example'
  s.metadata    = { "source_code_uri" => "https://github.com/example/example" }
end


Starting in RubyGems 2.0, a Specification can hold arbitrary metadata.  See metadata for restrictions on the format and size of metadata items you may add to a specification.

  


    
Gem::StreamUI implements a simple stream based user interface.

  


    
An absolutely silent download reporter.

  


    
An absolutely silent progress reporter.

  


    
A basic dotted progress reporter.

  


    
A progress reporter that behaves nicely with threaded downloading.

  


    
A progress reporter that prints out messages about the current progress.

  


    
Gem::StubSpecification reads the stub: line from the gemspec.  This prevents us having to eval the entire gemspec in order to find out certain information.

  


    
Raised to indicate that a system exit should occur with the specified exit_code

  


    
RubyGemTestCase provides a variety of methods for testing rubygems and gem-related behavior in a sandbox.  Through RubyGemTestCase you can install and uninstall gems, fetch remote gems through a stub fetcher and be assured your normal set of gems is not affected.

Tests are always run at a safe level of 1.

  


    
The SpecFetcherSetup allows easy setup of a remote source in RubyGems tests:

spec_fetcher do |f|
  f.gem  'a', 1
  f.spec 'a', 2
  f.gem  'b', 1' 'a' => '~> 1.0'
end

The above declaration creates two gems, a-1 and b-1, with a dependency from b to a.  The declaration creates an additional spec a-2, but no gem for it (so it cannot be installed).

After the gems are created they are removed from Gem.dir.

  


    
The StaticSet is a static set of gem specifications used for testing only. It is available by requiring Gem::TestCase.

  


    
Raised when removing a gem with the uninstall command fails

  


    
An Uninstaller.

The uninstaller fires pre and post uninstall hooks.  Hooks can be added either through a rubygems_plugin.rb file in an installed gem or via a rubygems/defaults/#{RUBY_ENGINE}.rb or rubygems/defaults/operating_system.rb file.  See Gem.pre_uninstall and Gem.post_uninstall for details.

  


    
Raised by Resolver when a dependency requests a gem for which there is no spec.

  


    
The UriFormatter handles URIs from user-input and escaping.

uf = Gem::UriFormatter.new 'example.com'

p uf.normalize #=> 'http://example.com'


  


    
Validator performs various gem file and gem database validation

  


    
Raised by Gem::Validator when something is not right in a gem.

  


    
The Version class processes string versions into comparable values. A version string should normally be a series of numbers separated by periods. Each part (digits separated by periods) is considered its own number, and these are used for sorting. So for instance, 3.10 sorts higher than 3.2 because ten is greater than two.

If any part contains letters (currently only a-z are supported) then that version is considered prerelease. Versions with a prerelease part in the Nth part sort less than versions with N-1 parts. Prerelease parts are sorted alphabetically using the normal Ruby string sorting rules. If a prerelease part contains both letters and numbers, it will be broken into multiple parts to provide expected sort behavior (1.0.a10 becomes 1.0.a.10, and is greater than 1.0.a9).

Prereleases sort between real releases (newest to oldest):

1.0

1.0.b1

1.0.a.2

0.9


If you want to specify a version restriction that includes both prereleases and regular releases of the 1.x series this is the best way:

s.add_dependency 'example', '>= 1.0.0.a', '< 2.0.0'


How Software Changes¶ ↑

Users expect to be able to specify a version constraint that gives them some reasonable expectation that new versions of a library will work with their software if the version constraint is true, and not work with their software if the version constraint is false.  In other words, the perfect system will accept all compatible versions of the library and reject all incompatible versions.

Libraries change in 3 ways (well, more than 3, but stay focused here!).

The change may be an implementation detail only and have no effect on the client software.

The change may add new features, but do so in a way that client software written to an earlier version is still compatible.

The change may change the public interface of the library in such a way that old software is no longer compatible.


Some examples are appropriate at this point.  Suppose I have a Stack class that supports a push and a pop method.

Examples of Category 1 changes:¶ ↑

Switch from an array based implementation to a linked-list based implementation.

Provide an automatic (and transparent) backing store for large stacks.


Examples of Category 2 changes might be:¶ ↑

Add a depth method to return the current depth of the stack.

Add a top method that returns the current top of stack (without changing the stack).

Change push so that it returns the item pushed (previously it had no usable return value).


Examples of Category 3 changes might be:¶ ↑

Changes pop so that it no longer returns a value (you must use top to get the top of the stack).

Rename the methods to push_item and pop_item.


RubyGems Rational Versioning¶ ↑

Versions shall be represented by three non-negative integers, separated by periods (e.g. 3.1.4).  The first integers is the “major” version number, the second integer is the “minor” version number, and the third integer is the “build” number.

A category 1 change (implementation detail) will increment the build number.

A category 2 change (backwards compatible) will increment the minor version number and reset the build number.

A category 3 change (incompatible) will increment the major build number and reset the minor and build numbers.

Any “public” release of a gem should have a different version.  Normally that means incrementing the build number.  This means a developer can generate builds all day long, but as soon as they make a public release, the version must be updated.


Examples¶ ↑

Let's work through a project lifecycle using our Stack example from above.
Version 0.0.1

The initial Stack class is release.
Version 0.0.2

Switched to a linked=list implementation because it is cooler.
Version 0.1.0

Added a depth method.
Version 1.0.0

Added top and made pop return nil (pop used to return the  old top item).
Version 1.1.0

push now returns the value pushed (it used it return nil).
Version 1.1.1

Fixed a bug in the linked list implementation.
Version 1.1.2

Fixed a bug introduced in the last fix.


Client A needs a stack with basic push/pop capability.  They write to the original interface (no top), so their version constraint looks like:

gem 'stack', '>= 0.0'


Essentially, any version is OK with Client A.  An incompatible change to the library will cause them grief, but they are willing to take the chance (we call Client A optimistic).

Client B is just like Client A except for two things: (1) They use the depth method and (2) they are worried about future incompatibilities, so they write their version constraint like this:

gem 'stack', '~> 0.1'


The depth method was introduced in version 0.1.0, so that version or anything later is fine, as long as the version stays below version 1.0 where incompatibilities are introduced.  We call Client B pessimistic because they are worried about incompatible future changes (it is OK to be pessimistic!).

Preventing Version Catastrophe:¶ ↑

From: blog.zenspider.com/2008/10/rubygems-howto-preventing-cata.html

Let's say you're depending on the fnord gem version 2.y.z. If you specify your dependency as “>= 2.0.0” then, you're good, right? What happens if fnord 3.0 comes out and it isn't backwards compatible with 2.y.z? Your stuff will break as a result of using “>=”. The better route is to specify your dependency with an “approximate” version specifier (“~>”). They're a tad confusing, so here is how the dependency specifiers work:

Specification From  ... To (exclusive)
">= 3.0"      3.0   ... &infin;
"~> 3.0"      3.0   ... 4.0
"~> 3.0.0"    3.0.0 ... 3.1
"~> 3.5"      3.5   ... 4.0
"~> 3.5.0"    3.5.0 ... 3.6
"~> 3"        3.0   ... 4.0

For the last example, single-digit versions are automatically extended with a zero to give a sensible result.

  


    
The GetoptLong class allows you to parse command line options similarly to the GNU getopt_long() C library call. Note, however, that GetoptLong is a pure Ruby implementation.

GetoptLong allows for POSIX-style options like --file as well as single letter options like -f

The empty option -- (two minus symbols) is used to end option processing. This can be particularly important if options have optional arguments.

Here is a simple example of usage:

require 'getoptlong'

opts = GetoptLong.new(
  [ '--help', '-h', GetoptLong::NO_ARGUMENT ],
  [ '--repeat', '-n', GetoptLong::REQUIRED_ARGUMENT ],
  [ '--name', GetoptLong::OPTIONAL_ARGUMENT ]
)

dir = nil
name = nil
repetitions = 1
opts.each do |opt, arg|
  case opt
    when '--help'
      puts <<-EOF
hello [OPTION] ... DIR

-h, --help:
   show help

--repeat x, -n x:
   repeat x times

--name [name]:
   greet user by name, if name not supplied default is John

DIR: The directory in which to issue the greeting.
      EOF
    when '--repeat'
      repetitions = arg.to_i
    when '--name'
      if arg == ''
        name = 'John'
      else
        name = arg
      end
  end
end

if ARGV.length != 1
  puts "Missing dir argument (try --help)"
  exit 0
end

dir = ARGV.shift

Dir.chdir(dir)
for i in (1..repetitions)
  print "Hello"
  if name
    print ", #{name}"
  end
  puts
end


Example command line:

hello -n 6 --name -- /tmp

  


    
Error types.

  


    
A Hash is a dictionary-like collection of unique keys and their values. Also called associative arrays, they are similar to Arrays, but where an Array uses integers as its index, a Hash allows you to use any object type.

Hashes enumerate their values in the order that the corresponding keys were inserted.

A Hash can be easily created by using its implicit form:

grades = { "Jane Doe" => 10, "Jim Doe" => 6 }


Hashes allow an alternate syntax for keys that are symbols. Instead of

options = { :font_size => 10, :font_family => "Arial" }


You could write it as:

options = { font_size: 10, font_family: "Arial" }


Each named key is a symbol you can access in hash:

options[:font_size]  # => 10


A Hash can also be created through its ::new method:

grades = Hash.new
grades["Dorothy Doe"] = 9


Hashes have a default value that is returned when accessing keys that do not exist in the hash. If no default is set nil is used. You can set the default value by sending it as an argument to Hash.new:

grades = Hash.new(0)


Or by using the default= method:

grades = {"Timmy Doe" => 8}
grades.default = 0


Accessing a value in a Hash requires using its key:

puts grades["Jane Doe"] # => 0


Common Uses¶ ↑

Hashes are an easy way to represent data structures, such as

books         = {}
books[:matz]  = "The Ruby Programming Language"
books[:black] = "The Well-Grounded Rubyist"


Hashes are also commonly used as a way to have named parameters in functions. Note that no brackets are used below. If a hash is the last argument on a method call, no braces are needed, thus creating a really clean interface:

Person.create(name: "John Doe", age: 27)

def self.create(params)
  @name = params[:name]
  @age  = params[:age]
end


Hash Keys¶ ↑

Two objects refer to the same hash key when their hash value is identical and the two objects are eql? to each other.

A user-defined class may be used as a hash key if the hash and eql? methods are overridden to provide meaningful behavior.  By default, separate instances refer to separate hash keys.

A typical implementation of hash is based on the object's data while eql? is usually aliased to the overridden == method:

class Book
  attr_reader :author, :title

  def initialize(author, title)
    @author = author
    @title = title
  end

  def ==(other)
    self.class === other and
      other.author == @author and
      other.title == @title
  end

  alias eql? ==

  def hash
    @author.hash ^ @title.hash # XOR
  end
end

book1 = Book.new 'matz', 'Ruby in a Nutshell'
book2 = Book.new 'matz', 'Ruby in a Nutshell'

reviews = {}

reviews[book1] = 'Great reference!'
reviews[book2] = 'Nice and compact!'

reviews.length #=> 1


See also Object#hash and Object#eql?

  


    
Expect library adds the IO instance method expect, which does similar act to tcl's expect extension.

In order to use this method, you must require expect:

require 'expect'


Please see expect for usage.

The IO class is the basis for all input and output in Ruby. An I/O stream may be duplexed (that is, bidirectional), and so may use more than one native operating system stream.

Many of the examples in this section use the File class, the only standard subclass of IO. The two classes are closely associated.  Like the File class, the Socket library subclasses from IO (such as TCPSocket or UDPSocket).

The Kernel#open method can create an IO (or File) object for these types of arguments:

A plain string represents a filename suitable for the underlying operating system.

A string starting with "|" indicates a subprocess. The remainder of the string following the "|" is invoked as a process with appropriate input/output channels connected to it.

A string equal to "|-" will create another Ruby instance as a subprocess.


The IO may be opened with different file modes (read-only, write-only) and encodings for proper conversion.  See IO.new for these options.  See Kernel#open for details of the various command formats described above.

IO.popen, the Open3 library, or  Process#spawn may also be used to communicate with subprocesses through an IO.

Ruby will convert pathnames between different operating system conventions if possible.  For instance, on a Windows system the filename "/gumby/ruby/test.rb" will be opened as "\gumby\ruby\test.rb".  When specifying a Windows-style filename in a Ruby string, remember to escape the backslashes:

"C:\\gumby\\ruby\\test.rb"


Our examples here will use the Unix-style forward slashes; File::ALT_SEPARATOR can be used to get the platform-specific separator character.

The global constant ARGF (also accessible as $<) provides an IO-like stream which allows access to all files mentioned on the command line (or STDIN if no files are mentioned). ARGF#path and its alias ARGF#filename are provided to access the name of the file currently being read.

io/console¶ ↑

The io/console extension provides methods for interacting with the console.  The console can be accessed from IO.console or the standard input/output/error IO objects.

Requiring io/console adds the following methods:

IO::console

IO#raw

IO#raw!

IO#cooked

IO#cooked!

IO#getch

IO#echo=

IO#echo?

IO#noecho

IO#winsize

IO#winsize=

IO#iflush

IO#ioflush

IO#oflush


Example:

require 'io/console'
rows, columns = $stdout.winsize
puts "Your screen is #{columns} wide and #{rows} tall"


  


    
exception to wait for reading by EAGAIN. see IO.select.

  


    
exception to wait for writing by EAGAIN. see IO.select.

  


    
exception to wait for reading by EINPROGRESS. see IO.select.

  


    
exception to wait for writing by EINPROGRESS. see IO.select.

  


    
exception to wait for reading by EWOULDBLOCK. see IO.select.

  


    
exception to wait for writing by EWOULDBLOCK. see IO.select.

  


    
Raised when an IO operation fails.

File.open("/etc/hosts") {|f| f << "example"}
  #=> IOError: not opened for writing

File.open("/etc/hosts") {|f| f.close; f.read }
  #=> IOError: closed stream


Note that some IO failures raise SystemCallErrors and these are not subclasses of IOError:

File.open("does/not/exist")
  #=> Errno::ENOENT: No such file or directory - does/not/exist


  


    
IPAddr provides a set of methods to manipulate an IP address.  Both IPv4 and IPv6 are supported.

Example¶ ↑

require 'ipaddr'

ipaddr1 = IPAddr.new "3ffe:505:2::1"

p ipaddr1                   #=> #<IPAddr: IPv6:3ffe:0505:0002:0000:0000:0000:0000:0001/ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff>

p ipaddr1.to_s              #=> "3ffe:505:2::1"

ipaddr2 = ipaddr1.mask(48)  #=> #<IPAddr: IPv6:3ffe:0505:0002:0000:0000:0000:0000:0000/ffff:ffff:ffff:0000:0000:0000:0000:0000>

p ipaddr2.to_s              #=> "3ffe:505:2::"

ipaddr3 = IPAddr.new "192.168.2.0/24"

p ipaddr3                   #=> #<IPAddr: IPv4:192.168.2.0/255.255.255.0>


  


    
Raised when the address family is invalid such as an address with an unsupported family, an address with an inconsistent family, or an address who's family cannot be determined.

  


    
Generic IPAddr related error. Exceptions raised in this class should inherit from Error.

  


    
Raised when the provided IP address is an invalid address.

  


    
Raised when the address is an invalid length.

  


    
IPSocket is the super class of TCPSocket and UDPSocket.

  


    
An exception raised by IRB.irb_abort

  


    
A class that wraps the current state of the irb session, including the configuration of IRB.conf.

  


    
Use a File for IO with irb, see InputMethod

  


    
An irb inspector

In order to create your own custom inspector there are two things you should be aware of:

Inspector uses inspect_value, or inspect_proc, for output of return values.

This also allows for an optional init+, or init_proc, which is called when the inspector is activated.

Knowing this, you can create a rudimentary inspector as follows:

irb(main):001:0> ins = IRB::Inspector.new(proc{ |v| "omg! #{v}" })
irb(main):001:0> IRB.CurrentContext.inspect_mode = ins # => omg! #<IRB::Inspector:0x007f46f7ba7d28>
irb(main):001:0> "what?" #=> omg! what?

  


    
Raised in the event of an exception in a file loaded from an Irb session

  


    
An abstract class, or superclass, for CompositeNotifier and LeveledNotifier to inherit. It provides several wrapper methods for the OutputMethod object used by the Notifier.

  


    
A class that can be used to create a group of notifier objects with the intent of representing a leveled notification system for irb.

This class will allow you to generate other notifiers, and assign them the appropriate level for output.

The Notifier class provides a class-method Notifier.def_notifier to create a new composite notifier. Using the first composite notifier object you create, sibling notifiers can be initialized with def_notifier.

  


    
A leveled notifier is comparable to the composite group from CompositeNotifier#notifiers.

  


    
NoMsgNotifier is a LeveledNotifier that's used as the default notifier when creating a new CompositeNotifier.

This notifier is used as the zero index, or level 0, for CompositeNotifier#notifiers, and will not output messages of any sort.

  


    
An abstract output class for IO in irb. This is mainly used internally by IRB::Notifier. You can define your own output method to use with Irb.new, or Context.new

  


    
A standard output printer

  


    
Raised when the given index is invalid.

a = [:foo, :bar]
a.fetch(0)   #=> :foo
a[4]         #=> nil
a.fetch(4)   #=> IndexError: index 4 outside of array bounds: -2...2


  


    
Holds Integer values.  You cannot add a singleton method to an Integer object, any attempt to do so will raise a TypeError.

  


    
Raised when the interrupt signal is received, typically because the user has pressed Control-C (on most posix platforms). As such, it is a subclass of SignalException.

begin
  puts "Press ctrl-C when you get bored"
  loop {}
rescue Interrupt => e
  puts "Note: You will typically use Signal.trap instead."
end


produces:

Press ctrl-C when you get bored

then waits until it is interrupted with Control-C and then prints:

Note: You will typically use Signal.trap instead.

  


    
This is the JSON parser implemented as a C extension. It can be configured to be used by setting

JSON.parser = JSON::Ext::Parser


with the method parser= in JSON.

  


    
This exception is raised if a generator or unparser error occurs.

  


    
The base exception for JSON errors.

  


    
This exception is raised if the required unicode support is missing on the system. Usually this means that the iconv library is not installed.

  


    
This exception is raised if the nesting of parsed data structures is too deep.

  


    
This exception is raised if a parser error occurs.

  


    
This exception is raised if a generator or unparser error occurs.

  


    
Raised when the specified key is not found. It is a subclass of IndexError.

h = {"foo" => :bar}
h.fetch("foo") #=> :bar
h.fetch("baz") #=> KeyError: key not found: "baz"


  


    
Raised when a file required (a Ruby script, extension library, …) fails to load.

require 'this/file/does/not/exist'


raises the exception:

LoadError: no such file to load -- this/file/does/not/exist

  


    
Raised when Ruby can't yield as requested.

A typical scenario is attempting to yield when no block is given:

def call_block
  yield 42
end
call_block


raises the exception:

LocalJumpError: no block given (yield)

A more subtle example:

def get_me_a_return
  Proc.new { return 42 }
end
get_me_a_return.call


raises the exception:

LocalJumpError: unexpected return

  


    
Description¶ ↑

The Logger class provides a simple but sophisticated logging utility that you can use to output messages.

The messages have associated levels, such as INFO or ERROR that indicate their importance.  You can then give the Logger a level, and only messages at that level or higher will be printed.

The levels are:
UNKNOWN

An unknown message that should always be logged.
FATAL

An unhandleable error that results in a program crash.
ERROR

A handleable error condition.
WARN

A warning.
INFO

Generic (useful) information about system operation.
DEBUG

Low-level information for developers.


For instance, in a production system, you may have your Logger set to INFO or even WARN. When you are developing the system, however, you probably want to know about the program's internal state, and would set the Logger to DEBUG.

Note: Logger does not escape or sanitize any messages passed to it. Developers should be aware of when potentially malicious data (user-input) is passed to Logger, and manually escape the untrusted data:

logger.info("User-input: #{input.dump}")
logger.info("User-input: %p" % input)


You can use formatter= for escaping all data.

original_formatter = Logger::Formatter.new
logger.formatter = proc { |severity, datetime, progname, msg|
  original_formatter.call(severity, datetime, progname, msg.dump)
}
logger.info(input)


Example¶ ↑

This creates a Logger that outputs to the standard output stream, with a level of WARN:

require 'logger'

logger = Logger.new(STDOUT)
logger.level = Logger::WARN

logger.debug("Created logger")
logger.info("Program started")
logger.warn("Nothing to do!")

path = "a_non_existent_file"

begin
  File.foreach(path) do |line|
    unless line =~ /^(\w+) = (.*)$/
      logger.error("Line in wrong format: #{line.chomp}")
    end
  end
rescue => err
  logger.fatal("Caught exception; exiting")
  logger.fatal(err)
end


Because the Logger's level is set to WARN, only the warning, error, and fatal messages are recorded.  The debug and info messages are silently discarded.

Features¶ ↑

There are several interesting features that Logger provides, like auto-rolling of log files, setting the format of log messages, and specifying a program name in conjunction with the message.  The next section shows you how to achieve these things.

HOWTOs¶ ↑

How to create a logger¶ ↑

The options below give you various choices, in more or less increasing complexity.

Create a logger which logs messages to STDERR/STDOUT.

logger = Logger.new(STDERR)
logger = Logger.new(STDOUT)


Create a logger for the file which has the specified name.

logger = Logger.new('logfile.log')


Create a logger for the specified file.

file = File.open('foo.log', File::WRONLY | File::APPEND)
# To create new logfile, add File::CREAT like:
# file = File.open('foo.log', File::WRONLY | File::APPEND | File::CREAT)
logger = Logger.new(file)


Create a logger which ages the logfile once it reaches a certain size. Leave 10 “old” log files where each file is about 1,024,000 bytes.

logger = Logger.new('foo.log', 10, 1024000)


Create a logger which ages the logfile daily/weekly/monthly.

logger = Logger.new('foo.log', 'daily')
logger = Logger.new('foo.log', 'weekly')
logger = Logger.new('foo.log', 'monthly')



How to log a message¶ ↑

Notice the different methods (fatal, error, info) being used to log messages of various levels?  Other methods in this family are warn and debug.  add is used below to log a message of an arbitrary (perhaps dynamic) level.

Message in a block.

logger.fatal { "Argument 'foo' not given." }


Message as a string.

logger.error "Argument #{@foo} mismatch."


With progname.

logger.info('initialize') { "Initializing..." }


With severity.

logger.add(Logger::FATAL) { 'Fatal error!' }



The block form allows you to create potentially complex log messages, but to delay their evaluation until and unless the message is logged.  For example, if we have the following:

logger.debug { "This is a " + potentially + " expensive operation" }


If the logger's level is INFO or higher, no debug messages will be logged, and the entire block will not even be evaluated.  Compare to this:

logger.debug("This is a " + potentially + " expensive operation")


Here, the string concatenation is done every time, even if the log level is not set to show the debug message.

How to close a logger¶ ↑

logger.close


Setting severity threshold¶ ↑

Original interface.

logger.sev_threshold = Logger::WARN


Log4r (somewhat) compatible interface.

logger.level = Logger::INFO

# DEBUG < INFO < WARN < ERROR < FATAL < UNKNOWN


Symbol or String (case insensitive)

logger.level = :info
logger.level = 'INFO'

# :debug < :info < :warn < :error < :fatal < :unknown


Constructor

Logger.new(logdev, level: Logger::INFO)
Logger.new(logdev, level: :info)
Logger.new(logdev, level: 'INFO')



Format¶ ↑

Log messages are rendered in the output stream in a certain format by default.  The default format and a sample are shown below:

Log format:

SeverityID, [DateTime #pid] SeverityLabel -- ProgName: message

Log sample:

I, [1999-03-03T02:34:24.895701 #19074]  INFO -- Main: info.

You may change the date and time format via datetime_format=.

logger.datetime_format = '%Y-%m-%d %H:%M:%S'
      # e.g. "2004-01-03 00:54:26"


or via the constructor.

Logger.new(logdev, datetime_format: '%Y-%m-%d %H:%M:%S')


Or, you may change the overall format via the formatter= method.

logger.formatter = proc do |severity, datetime, progname, msg|
  "#{datetime}: #{msg}\n"
end
# e.g. "2005-09-22 08:51:08 +0900: hello world"


or via the constructor.

Logger.new(logdev, formatter: proc {|severity, datetime, progname, msg|
  "#{datetime}: #{msg}\n"
})


  


    
Default formatter for log messages.

  


    
Device used for logging messages.

  


    
MatchData encapsulates the result of matching a Regexp against string. It is returned by Regexp#match and String#match, and also stored in a global variable returned by Regexp.last_match.

Usage:

url = 'https://docs.ruby-lang.org/en/2.5.0/MatchData.html'
m = url.match(/(\d\.?)+/)   # => #<MatchData "2.5.0" 1:"0">
m.string                    # => "https://docs.ruby-lang.org/en/2.5.0/MatchData.html"
m.regexp                    # => /(\d\.?)+/
# entire matched substring:
m[0]                        # => "2.5.0"

# Working with unnamed captures
m = url.match(%r{([^/]+)/([^/]+)\.html$})
m.captures                  # => ["2.5.0", "MatchData"]
m[1]                        # => "2.5.0"
m.values_at(1, 2)           # => ["2.5.0", "MatchData"]

# Working with named captures
m = url.match(%r{(?<version>[^/]+)/(?<module>[^/]+)\.html$})
m.captures                  # => ["2.5.0", "MatchData"]
m.named_captures            # => {"version"=>"2.5.0", "module"=>"MatchData"}
m[:version]                 # => "2.5.0"
m.values_at(:version, :module)
                            # => ["2.5.0", "MatchData"]
# Numerical indexes are working, too
m[1]                        # => "2.5.0"
m.values_at(1, 2)           # => ["2.5.0", "MatchData"]


Global variables equivalence¶ ↑

Parts of last MatchData (returned by Regexp.last_match) are also aliased as global variables:

$~ is Regexp.last_match;

$& is Regexp.last_match[0];

$1, $2, and so on are Regexp.last_match[i] (captures by number);

$` is Regexp.last_match.pre_match;

$' is Regexp.last_match.post_match;

$+ is Regexp.last_match[-1] (the last capture).


See also “Special global variables” section in Regexp documentation.

  


    
Raised when a mathematical function is evaluated outside of its domain of definition.

For example, since cos returns values in the range -1..1, its inverse function acos is only defined on that interval:

Math.acos(42)


produces:

Math::DomainError: Numerical argument is out of domain - "acos"

  


    
The Matrix class represents a mathematical matrix. It provides methods for creating matrices, operating on them arithmetically and algebraically, and determining their mathematical properties such as trace, rank, inverse, determinant, or eigensystem.

  


    
Eigenvalues and eigenvectors of a real matrix.

Computes the eigenvalues and eigenvectors of a matrix A.

If A is diagonalizable, this provides matrices V and D such that A = V*D*V.inv, where D is the diagonal matrix with entries equal to the eigenvalues and V is formed by the eigenvectors.

If A is symmetric, then V is orthogonal and thus A = V*D*V.t

  


    
For an m-by-n matrix A with m >= n, the LU decomposition is an m-by-n unit lower triangular matrix L, an n-by-n upper triangular matrix U, and a m-by-m permutation matrix P so that L*U = P*A. If m < n, then L is m-by-m and U is m-by-n.

The LUP decomposition with pivoting always exists, even if the matrix is singular, so the constructor will never fail.  The primary use of the LU decomposition is in the solution of square systems of simultaneous linear equations.  This will fail if singular? returns true.

  


    
Method objects are created by Object#method, and are associated with a particular object (not just with a class). They may be used to invoke the method within the object, and as a block associated with an iterator. They may also be unbound from one object (creating an UnboundMethod) and bound to another.

class Thing
  def square(n)
    n*n
  end
end
thing = Thing.new
meth  = thing.method(:square)

meth.call(9)                 #=> 81
[ 1, 2, 3 ].collect(&meth)   #=> [1, 4, 9]

[ 1, 2, 3 ].each(&method(:puts)) #=> prints 1, 2, 3

require 'date'
%w[2017-03-01 2017-03-02].collect(&Date.method(:parse))
#=> [#<Date: 2017-03-01 ((2457814j,0s,0n),+0s,2299161j)>, #<Date: 2017-03-02 ((2457815j,0s,0n),+0s,2299161j)>]


  


    
A Module is a collection of methods and constants. The methods in a module may be instance methods or module methods. Instance methods appear as methods in a class when the module is included, module methods do not. Conversely, module methods may be called without creating an encapsulating object, while instance methods may not. (See Module#module_function.)

In the descriptions that follow, the parameter sym refers to a symbol, which is either a quoted string or a Symbol (such as :name).

module Mod
  include Math
  CONST = 1
  def meth
    #  ...
  end
end
Mod.class              #=> Module
Mod.constants          #=> [:CONST, :PI, :E]
Mod.instance_methods   #=> [:meth]


  


    
Use the Monitor class when you want to have a lock object for blocks with mutual exclusion.

require 'monitor'

lock = Monitor.new
lock.synchronize do
  # exclusive access
end


  


    
FIXME: This isn't documented in Nutshell.

Since MonitorMixin.new_cond returns a ConditionVariable, and the example above calls while_wait and signal, this class should be documented.

  


    
Mutex implements a simple semaphore that can be used to coordinate access to shared data from multiple concurrent threads.

Example:

semaphore = Mutex.new

a = Thread.new {
  semaphore.synchronize {
    # access shared resource
  }
}

b = Thread.new {
  semaphore.synchronize {
    # access shared resource
  }
}


  


    
Raised when a given name is invalid or undefined.

puts foo


raises the exception:

NameError: undefined local variable or method `foo' for main:Object

Since constant names must start with a capital:

Integer.const_set :answer, 42


raises the exception:

NameError: wrong constant name answer

  


    
This class is equivalent to POP3, except that it uses APOP authentication.

  


    
This class is equivalent to POP3, except that it uses APOP authentication.

  


    
This class implements the File Transfer Protocol.  If you have used a command-line FTP program, and are familiar with the commands, you will be able to use this class easily.  Some extra features are included to take advantage of Ruby's style and strengths.

Example¶ ↑

require 'net/ftp'


Example 1¶ ↑

ftp = Net::FTP.new('example.com')
ftp.login
files = ftp.chdir('pub/lang/ruby/contrib')
files = ftp.list('n*')
ftp.getbinaryfile('nif.rb-0.91.gz', 'nif.gz', 1024)
ftp.close


Example 2¶ ↑

Net::FTP.open('example.com') do |ftp|
  ftp.login
  files = ftp.chdir('pub/lang/ruby/contrib')
  files = ftp.list('n*')
  ftp.getbinaryfile('nif.rb-0.91.gz', 'nif.gz', 1024)
end


Major Methods¶ ↑

The following are the methods most likely to be useful to users:

FTP.open

getbinaryfile

gettextfile

putbinaryfile

puttextfile

chdir

nlst

size

rename

delete


  


    
MLSxEntry represents an entry in responses of MLST/MLSD. Each entry has the facts (e.g., size, last modification time, etc.) and the pathname.

  


    
An HTTP client API for Ruby.¶ ↑

Net::HTTP provides a rich library which can be used to build HTTP user-agents.  For more details about HTTP see [RFC2616](www.ietf.org/rfc/rfc2616.txt).

Net::HTTP is designed to work closely with URI.  URI::HTTP#host, URI::HTTP#port and URI::HTTP#request_uri are designed to work with Net::HTTP.

If you are only performing a few GET requests you should try OpenURI.

Simple Examples¶ ↑

All examples assume you have loaded Net::HTTP with:

require 'net/http'


This will also require 'uri' so you don't need to require it separately.

The Net::HTTP methods in the following section do not persist connections.  They are not recommended if you are performing many HTTP requests.

GET¶ ↑

Net::HTTP.get('example.com', '/index.html') # => String


GET by URI¶ ↑

uri = URI('http://example.com/index.html?count=10')
Net::HTTP.get(uri) # => String


GET with Dynamic Parameters¶ ↑

uri = URI('http://example.com/index.html')
params = { :limit => 10, :page => 3 }
uri.query = URI.encode_www_form(params)

res = Net::HTTP.get_response(uri)
puts res.body if res.is_a?(Net::HTTPSuccess)


POST¶ ↑

uri = URI('http://www.example.com/search.cgi')
res = Net::HTTP.post_form(uri, 'q' => 'ruby', 'max' => '50')
puts res.body


POST with Multiple Values¶ ↑

uri = URI('http://www.example.com/search.cgi')
res = Net::HTTP.post_form(uri, 'q' => ['ruby', 'perl'], 'max' => '50')
puts res.body


How to use Net::HTTP¶ ↑

The following example code can be used as the basis of an HTTP user-agent which can perform a variety of request types using persistent connections.

uri = URI('http://example.com/some_path?query=string')

Net::HTTP.start(uri.host, uri.port) do |http|
  request = Net::HTTP::Get.new uri

  response = http.request request # Net::HTTPResponse object
end


Net::HTTP::start immediately creates a connection to an HTTP server which is kept open for the duration of the block.  The connection will remain open for multiple requests in the block if the server indicates it supports persistent connections.

If you wish to re-use a connection across multiple HTTP requests without automatically closing it you can use ::new and then call start and finish manually.

The request types Net::HTTP supports are listed below in the section “HTTP Request Classes”.

For all the Net::HTTP request objects and shortcut request methods you may supply either a String for the request path or a URI from which Net::HTTP will extract the request path.

Response Data¶ ↑

uri = URI('http://example.com/index.html')
res = Net::HTTP.get_response(uri)

# Headers
res['Set-Cookie']            # => String
res.get_fields('set-cookie') # => Array
res.to_hash['set-cookie']    # => Array
puts "Headers: #{res.to_hash.inspect}"

# Status
puts res.code       # => '200'
puts res.message    # => 'OK'
puts res.class.name # => 'HTTPOK'

# Body
puts res.body if res.response_body_permitted?


Following Redirection¶ ↑

Each Net::HTTPResponse object belongs to a class for its response code.

For example, all 2XX responses are instances of a Net::HTTPSuccess subclass, a 3XX response is an instance of a Net::HTTPRedirection subclass and a 200 response is an instance of the Net::HTTPOK class.  For details of response classes, see the section “HTTP Response Classes” below.

Using a case statement you can handle various types of responses properly:

def fetch(uri_str, limit = 10)
  # You should choose a better exception.
  raise ArgumentError, 'too many HTTP redirects' if limit == 0

  response = Net::HTTP.get_response(URI(uri_str))

  case response
  when Net::HTTPSuccess then
    response
  when Net::HTTPRedirection then
    location = response['location']
    warn "redirected to #{location}"
    fetch(location, limit - 1)
  else
    response.value
  end
end

print fetch('http://www.ruby-lang.org')


POST¶ ↑

A POST can be made using the Net::HTTP::Post request class.  This example creates a URL encoded POST body:

uri = URI('http://www.example.com/todo.cgi')
req = Net::HTTP::Post.new(uri)
req.set_form_data('from' => '2005-01-01', 'to' => '2005-03-31')

res = Net::HTTP.start(uri.hostname, uri.port) do |http|
  http.request(req)
end

case res
when Net::HTTPSuccess, Net::HTTPRedirection
  # OK
else
  res.value
end


To send multipart/form-data use Net::HTTPHeader#set_form:

req = Net::HTTP::Post.new(uri)
req.set_form([['upload', File.open('foo.bar')]], 'multipart/form-data')


Other requests that can contain a body such as PUT can be created in the same way using the corresponding request class (Net::HTTP::Put).

Setting Headers¶ ↑

The following example performs a conditional GET using the If-Modified-Since header.  If the files has not been modified since the time in the header a Not Modified response will be returned.  See RFC 2616 section 9.3 for further details.

uri = URI('http://example.com/cached_response')
file = File.stat 'cached_response'

req = Net::HTTP::Get.new(uri)
req['If-Modified-Since'] = file.mtime.rfc2822

res = Net::HTTP.start(uri.hostname, uri.port) {|http|
  http.request(req)
}

open 'cached_response', 'w' do |io|
  io.write res.body
end if res.is_a?(Net::HTTPSuccess)


Basic Authentication¶ ↑

Basic authentication is performed according to [RFC2617](www.ietf.org/rfc/rfc2617.txt).

uri = URI('http://example.com/index.html?key=value')

req = Net::HTTP::Get.new(uri)
req.basic_auth 'user', 'pass'

res = Net::HTTP.start(uri.hostname, uri.port) {|http|
  http.request(req)
}
puts res.body


Streaming Response Bodies¶ ↑

By default Net::HTTP reads an entire response into memory.  If you are handling large files or wish to implement a progress bar you can instead stream the body directly to an IO.

uri = URI('http://example.com/large_file')

Net::HTTP.start(uri.host, uri.port) do |http|
  request = Net::HTTP::Get.new uri

  http.request request do |response|
    open 'large_file', 'w' do |io|
      response.read_body do |chunk|
        io.write chunk
      end
    end
  end
end


HTTPS¶ ↑

HTTPS is enabled for an HTTP connection by Net::HTTP#use_ssl=.

uri = URI('https://secure.example.com/some_path?query=string')

Net::HTTP.start(uri.host, uri.port, :use_ssl => true) do |http|
  request = Net::HTTP::Get.new uri
  response = http.request request # Net::HTTPResponse object
end


Or if you simply want to make a GET request, you may pass in an URI object that has an HTTPS URL. Net::HTTP automatically turns on TLS verification if the URI object has a 'https' URI scheme.

uri = URI('https://example.com/')
Net::HTTP.get(uri) # => String


In previous versions of Ruby you would need to require 'net/https' to use HTTPS. This is no longer true.

Proxies¶ ↑

Net::HTTP will automatically create a proxy from the http_proxy environment variable if it is present.  To disable use of http_proxy, pass nil for the proxy address.

You may also create a custom proxy:

proxy_addr = 'your.proxy.host'
proxy_port = 8080

Net::HTTP.new('example.com', nil, proxy_addr, proxy_port).start { |http|
  # always proxy via your.proxy.addr:8080
}


See Net::HTTP.new for further details and examples such as proxies that require a username and password.

Compression¶ ↑

Net::HTTP automatically adds Accept-Encoding for compression of response bodies and automatically decompresses gzip and deflate responses unless a Range header was sent.

Compression can be disabled through the Accept-Encoding: identity header.

HTTP Request Classes¶ ↑

Here is the HTTP request class hierarchy.

Net::HTTPRequest

Net::HTTP::Get

Net::HTTP::Head

Net::HTTP::Post

Net::HTTP::Patch

Net::HTTP::Put

Net::HTTP::Proppatch

Net::HTTP::Lock

Net::HTTP::Unlock

Net::HTTP::Options

Net::HTTP::Propfind

Net::HTTP::Delete

Net::HTTP::Move

Net::HTTP::Copy

Net::HTTP::Mkcol

Net::HTTP::Trace



HTTP Response Classes¶ ↑

Here is HTTP response class hierarchy.  All classes are defined in Net module and are subclasses of Net::HTTPResponse.
HTTPUnknownResponse

For unhandled HTTP extensions
HTTPInformation

1xx
HTTPContinue

100
HTTPSwitchProtocol

101
HTTPSuccess

2xx
HTTPOK

200
HTTPCreated

201
HTTPAccepted

202
HTTPNonAuthoritativeInformation

203
HTTPNoContent

204
HTTPResetContent

205
HTTPPartialContent

206
HTTPMultiStatus

207
HTTPIMUsed

226
HTTPRedirection

3xx
HTTPMultipleChoices

300
HTTPMovedPermanently

301
HTTPFound

302
HTTPSeeOther

303
HTTPNotModified

304
HTTPUseProxy

305
HTTPTemporaryRedirect

307
HTTPClientError

4xx
HTTPBadRequest

400
HTTPUnauthorized

401
HTTPPaymentRequired

402
HTTPForbidden

403
HTTPNotFound

404
HTTPMethodNotAllowed

405
HTTPNotAcceptable

406
HTTPProxyAuthenticationRequired

407
HTTPRequestTimeOut

408
HTTPConflict

409
HTTPGone

410
HTTPLengthRequired

411
HTTPPreconditionFailed

412
HTTPRequestEntityTooLarge

413
HTTPRequestURITooLong

414
HTTPUnsupportedMediaType

415
HTTPRequestedRangeNotSatisfiable

416
HTTPExpectationFailed

417
HTTPUnprocessableEntity

422
HTTPLocked

423
HTTPFailedDependency

424
HTTPUpgradeRequired

426
HTTPPreconditionRequired

428
HTTPTooManyRequests

429
HTTPRequestHeaderFieldsTooLarge

431
HTTPUnavailableForLegalReasons

451
HTTPServerError

5xx
HTTPInternalServerError

500
HTTPNotImplemented

501
HTTPBadGateway

502
HTTPServiceUnavailable

503
HTTPGatewayTimeOut

504
HTTPVersionNotSupported

505
HTTPInsufficientStorage

507
HTTPNetworkAuthenticationRequired

511


There is also the Net::HTTPBadResponse exception which is raised when there is a protocol error.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods. See Net::HTTP for usage examples.

  


    
See Net::HTTPGenericRequest for attributes and methods. See Net::HTTP for usage examples.

  


    
See Net::HTTPGenericRequest for attributes and methods. See Net::HTTP for usage examples.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods. See Net::HTTP for usage examples.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods. See Net::HTTP for usage examples.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
See Net::HTTPGenericRequest for attributes and methods.

  


    
HTTPGenericRequest is the parent of the HTTPRequest class. Do not use this directly; use a subclass of HTTPRequest.

Mixes in the HTTPHeader module to provide easier access to HTTP headers.

  


    
444 No Response - Nginx 449 Retry With - Microsoft 450 Blocked by Windows Parental Controls - Microsoft 499 Client Closed Request - Nginx

  


    
418 I'm a teapot - RFC 2324; a joke RFC 420 Enhance Your Calm - Twitter

  


    
509 Bandwidth Limit Exceeded - Apache bw/limited extension

  


    
HTTP request class. This class wraps together the request header and the request path. You cannot use this class directly. Instead, you should use one of its subclasses: Net::HTTP::Get, Net::HTTP::Post, Net::HTTP::Head.

  


    
HTTP response class.

This class wraps together the response header and the response body (the entity requested).

It mixes in the HTTPHeader module, which provides access to response header values both via hash-like methods and via individual readers.

Note that each possible HTTP response code defines its own HTTPResponse subclass.  These are listed below.

All classes are defined under the Net module. Indentation indicates inheritance.  For a list of the classes see Net::HTTP.

  


    
306 Switch Proxy - no longer unused

  


    
www.iana.org/assignments/http-status-codes/http-status-codes.xhtml

  


    
425 Unordered Collection - existed only in draft

  


    
Net::IMAP implements Internet Message Access Protocol (IMAP) client functionality.  The protocol is described in [IMAP].

IMAP Overview¶ ↑

An IMAP client connects to a server, and then authenticates itself using either authenticate() or login().  Having authenticated itself, there is a range of commands available to it.  Most work with mailboxes, which may be arranged in an hierarchical namespace, and each of which contains zero or more messages.  How this is implemented on the server is implementation-dependent; on a UNIX server, it will frequently be implemented as files in mailbox format within a hierarchy of directories.

To work on the messages within a mailbox, the client must first select that mailbox, using either select() or (for read-only access) examine().  Once the client has successfully selected a mailbox, they enter selected state, and that mailbox becomes the current mailbox, on which mail-item related commands implicitly operate.

Messages have two sorts of identifiers: message sequence numbers and UIDs.

Message sequence numbers number messages within a mailbox from 1 up to the number of items in the mailbox.  If a new message arrives during a session, it receives a sequence number equal to the new size of the mailbox.  If messages are expunged from the mailbox, remaining messages have their sequence numbers “shuffled down” to fill the gaps.

UIDs, on the other hand, are permanently guaranteed not to identify another message within the same mailbox, even if the existing message is deleted.  UIDs are required to be assigned in ascending (but not necessarily sequential) order within a mailbox; this means that if a non-IMAP client rearranges the order of mailitems within a mailbox, the UIDs have to be reassigned.  An IMAP client thus cannot rearrange message orders.

Examples of Usage¶ ↑

List sender and subject of all recent messages in the default mailbox¶ ↑

imap = Net::IMAP.new('mail.example.com')
imap.authenticate('LOGIN', 'joe_user', 'joes_password')
imap.examine('INBOX')
imap.search(["RECENT"]).each do |message_id|
  envelope = imap.fetch(message_id, "ENVELOPE")[0].attr["ENVELOPE"]
  puts "#{envelope.from[0].name}: \t#{envelope.subject}"
end


Move all messages from April 2003 from “Mail/sent-mail” to “Mail/sent-apr03”¶ ↑

imap = Net::IMAP.new('mail.example.com')
imap.authenticate('LOGIN', 'joe_user', 'joes_password')
imap.select('Mail/sent-mail')
if not imap.list('Mail/', 'sent-apr03')
  imap.create('Mail/sent-apr03')
end
imap.search(["BEFORE", "30-Apr-2003", "SINCE", "1-Apr-2003"]).each do |message_id|
  imap.copy(message_id, "Mail/sent-apr03")
  imap.store(message_id, "+FLAGS", [:Deleted])
end
imap.expunge


Thread Safety¶ ↑

Net::IMAP supports concurrent threads. For example,

imap = Net::IMAP.new("imap.foo.net", "imap2")
imap.authenticate("cram-md5", "bar", "password")
imap.select("inbox")
fetch_thread = Thread.start { imap.fetch(1..-1, "UID") }
search_result = imap.search(["BODY", "hello"])
fetch_result = fetch_thread.value
imap.disconnect


This script invokes the FETCH command and the SEARCH command concurrently.

Errors¶ ↑

An IMAP server can send three different types of responses to indicate failure:
NO

the attempted command could not be successfully completed.  For instance, the username/password used for logging in are incorrect; the selected mailbox does not exist; etc.
BAD

the request from the client does not follow the server's understanding of the IMAP protocol.  This includes attempting commands from the wrong client state; for instance, attempting to perform a SEARCH command without having SELECTed a current mailbox.  It can also signal an internal server failure (such as a disk crash) has occurred.
BYE

the server is saying goodbye.  This can be part of a normal logout sequence, and can be used as part of a login sequence to indicate that the server is (for some reason) unwilling to accept your connection.  As a response to any other command, it indicates either that the server is shutting down, or that the server is timing out the client connection due to inactivity.


These three error response are represented by the errors Net::IMAP::NoResponseError, Net::IMAP::BadResponseError, and Net::IMAP::ByeResponseError, all of which are subclasses of Net::IMAP::ResponseError.  Essentially, all methods that involve sending a request to the server can generate one of these errors. Only the most pertinent instances have been documented below.

Because the IMAP class uses Sockets for communication, its methods are also susceptible to the various errors that can occur when working with sockets.  These are generally represented as Errno errors.  For instance, any method that involves sending a request to the server and/or receiving a response from it could raise an Errno::EPIPE error if the network connection unexpectedly goes down.  See the socket(7), ip(7), tcp(7), socket(2), connect(2), and associated man pages.

Finally, a Net::IMAP::DataFormatError is thrown if low-level data is found to be in an incorrect format (for instance, when converting between UTF-8 and UTF-16), and Net::IMAP::ResponseParseError is thrown if a server response is non-parseable.

References¶ ↑
[IMAP]

Crispin, “INTERNET MESSAGE ACCESS PROTOCOL - VERSION 4rev1”,


RFC 2060, December 1996.  (Note: since obsoleted by RFC 3501)
[LANGUAGE-TAGS]

Alvestrand, H., “Tags for the Identification of Languages”, RFC 1766, March 1995.
[MD5]

Myers, J., and M. Rose, “The Content-MD5 Header Field”, RFC 1864, October 1995.
[MIME-IMB]

Freed, N., and N. Borenstein, “MIME (Multipurpose Internet Mail Extensions) Part One: Format of Internet Message Bodies”, RFC 2045, November 1996.
[RFC-822]

Crocker, D., “Standard for the Format of ARPA Internet Text Messages”, STD 11, RFC 822, University of Delaware, August 1982.
[RFC-2087]

Myers, J., “IMAP4 QUOTA extension”, RFC 2087, January 1997.
[RFC-2086]

Myers, J., “IMAP4 ACL extension”, RFC 2086, January 1997.
[RFC-2195]

Klensin, J., Catoe, R., and Krumviede, P., “IMAP/POP AUTHorize Extension for Simple Challenge/Response”, RFC 2195, September 1997.
[SORT-THREAD-EXT]

Crispin, M., “INTERNET MESSAGE ACCESS PROTOCOL - SORT and THREAD Extensions”, draft-ietf-imapext-sort, May 2003.
[OSSL]

www.openssl.org
[RSSL]

savannah.gnu.org/projects/rubypki
[UTF7]

Goldsmith, D. and Davis, M., “UTF-7: A Mail-Safe Transformation Format of Unicode”, RFC 2152, May 1997.


  


    
Error raised upon a “BAD” response from the server, indicating that the client command violated the IMAP protocol, or an internal server failure has occurred.

  


    
Net::IMAP::BodyTypeAttachment represents attachment body structures of messages.

Fields:¶ ↑
media_type

Returns the content media type name.
subtype

Returns nil.
param

Returns a hash that represents parameters.
multipart?

Returns false.


  


    
Net::IMAP::BodyTypeBasic represents basic body structures of messages.

Fields:¶ ↑
media_type

Returns the content media type name as defined in [MIME-IMB].
subtype

Returns the content subtype name as defined in [MIME-IMB].
param

Returns a hash that represents parameters as defined in [MIME-IMB].
content_id

Returns a string giving the content id as defined in [MIME-IMB].
description

Returns a string giving the content description as defined in [MIME-IMB].
encoding

Returns a string giving the content transfer encoding as defined in [MIME-IMB].
size

Returns a number giving the size of the body in octets.
md5

Returns a string giving the body MD5 value as defined in [MD5].
disposition

Returns a Net::IMAP::ContentDisposition object giving the content disposition.
language

Returns a string or an array of strings giving the body language value as defined in [LANGUAGE-TAGS].
extension

Returns extension data.
multipart?

Returns false.


  


    
Net::IMAP::BodyTypeMessage represents MESSAGE/RFC822 body structures of messages.

Fields:¶ ↑
envelope

Returns a Net::IMAP::Envelope giving the envelope structure.
body

Returns an object giving the body structure.


And Net::IMAP::BodyTypeMessage has all methods of Net::IMAP::BodyTypeText.

  


    
Net::IMAP::BodyTypeMultipart represents multipart body structures of messages.

Fields:¶ ↑
media_type

Returns the content media type name as defined in [MIME-IMB].
subtype

Returns the content subtype name as defined in [MIME-IMB].
parts

Returns multiple parts.
param

Returns a hash that represents parameters as defined in [MIME-IMB].
disposition

Returns a Net::IMAP::ContentDisposition object giving the content disposition.
language

Returns a string or an array of strings giving the body language value as defined in [LANGUAGE-TAGS].
extension

Returns extension data.
multipart?

Returns true.


  


    
Net::IMAP::BodyTypeText represents TEXT body structures of messages.

Fields:¶ ↑
lines

Returns the size of the body in text lines.


And Net::IMAP::BodyTypeText has all fields of Net::IMAP::BodyTypeBasic.

  


    
Error raised upon a “BYE” response from the server, indicating that the client is not being allowed to login, or has been timed out due to inactivity.

  


    
Authenticator for the “CRAM-MD5” authentication type.  See authenticate().

  


    
Error raised when data is in the incorrect format.

  


    
Authenticator for the “DIGEST-MD5” authentication type.  See authenticate().

  


    
Superclass of IMAP errors.

  


    
Error raised when too many flags are interned to symbols.

  


    
Authenticator for the “LOGIN” authentication type.  See authenticate().

  


    
Error raised upon a “NO” response from the server, indicating that the client command could not be completed successfully.

  


    
Authenticator for the “PLAIN” authentication type.  See authenticate().

  


    
Superclass of all errors used to encapsulate “fail” responses from the server.

  


    
Error raised when a response from the server is non-parseable.

  


    
OpenTimeout, a subclass of Timeout::Error, is raised if a connection cannot be created within the open_timeout.

  


    
What is This Library?¶ ↑

This library provides functionality for retrieving email via POP3, the Post Office Protocol version 3. For details of POP3, see [RFC1939] (www.ietf.org/rfc/rfc1939.txt).

Examples¶ ↑

Retrieving Messages¶ ↑

This example retrieves messages from the server and deletes them on the server.

Messages are written to files named 'inbox/1', 'inbox/2', .… Replace 'pop.example.com' with your POP3 server address, and 'YourAccount' and 'YourPassword' with the appropriate account details.

require 'net/pop'

pop = Net::POP3.new('pop.example.com')
pop.start('YourAccount', 'YourPassword')             # (1)
if pop.mails.empty?
  puts 'No mail.'
else
  i = 0
  pop.each_mail do |m|   # or "pop.mails.each ..."   # (2)
    File.open("inbox/#{i}", 'w') do |f|
      f.write m.pop
    end
    m.delete
    i += 1
  end
  puts "#{pop.mails.size} mails popped."
end
pop.finish                                           # (3)


Call Net::POP3#start and start POP session.

Access messages by using POP3#each_mail and/or POP3#mails.

Close POP session by calling POP3#finish or use the block form of start.


Shortened Code¶ ↑

The example above is very verbose. You can shorten the code by using some utility methods. First, the block form of Net::POP3.start can be used instead of POP3.new, POP3#start and POP3#finish.

require 'net/pop'

Net::POP3.start('pop.example.com', 110,
                'YourAccount', 'YourPassword') do |pop|
  if pop.mails.empty?
    puts 'No mail.'
  else
    i = 0
    pop.each_mail do |m|   # or "pop.mails.each ..."
      File.open("inbox/#{i}", 'w') do |f|
        f.write m.pop
      end
      m.delete
      i += 1
    end
    puts "#{pop.mails.size} mails popped."
  end
end


POP3#delete_all is an alternative for each_mail and delete.

require 'net/pop'

Net::POP3.start('pop.example.com', 110,
                'YourAccount', 'YourPassword') do |pop|
  if pop.mails.empty?
    puts 'No mail.'
  else
    i = 1
    pop.delete_all do |m|
      File.open("inbox/#{i}", 'w') do |f|
        f.write m.pop
      end
      i += 1
    end
  end
end


And here is an even shorter example.

require 'net/pop'

i = 0
Net::POP3.delete_all('pop.example.com', 110,
                     'YourAccount', 'YourPassword') do |m|
  File.open("inbox/#{i}", 'w') do |f|
    f.write m.pop
  end
  i += 1
end


Memory Space Issues¶ ↑

All the examples above get each message as one big string. This example avoids this.

require 'net/pop'

i = 1
Net::POP3.delete_all('pop.example.com', 110,
                     'YourAccount', 'YourPassword') do |m|
  File.open("inbox/#{i}", 'w') do |f|
    m.pop do |chunk|    # get a message little by little.
      f.write chunk
    end
    i += 1
  end
end


Using APOP¶ ↑

The net/pop library supports APOP authentication. To use APOP, use the Net::APOP class instead of the Net::POP3 class. You can use the utility method, Net::POP3.APOP(). For example:

require 'net/pop'

# Use APOP authentication if $isapop == true
pop = Net::POP3.APOP($isapop).new('apop.example.com', 110)
pop.start('YourAccount', 'YourPassword') do |pop|
  # Rest of the code is the same.
end


Fetch Only Selected Mail Using 'UIDL' POP Command¶ ↑

If your POP server provides UIDL functionality, you can grab only selected mails from the POP server. e.g.

def need_pop?( id )
  # determine if we need pop this mail...
end

Net::POP3.start('pop.example.com', 110,
                'Your account', 'Your password') do |pop|
  pop.mails.select { |m| need_pop?(m.unique_id) }.each do |m|
    do_something(m.pop)
  end
end


The POPMail#unique_id() method returns the unique-id of the message as a String. Normally the unique-id is a hash of the message.

  


    
POP3 authentication error.

  


    
Unexpected response from the server.

  


    
Non-authentication POP3 protocol error (reply code “-ERR”, except authentication).

  


    
This class represents a message which exists on the POP server. Instances of this class are created by the POP3 class; they should not be directly created by the user.

  


    
ReadTimeout, a subclass of Timeout::Error, is raised if a chunk of the response cannot be read within the read_timeout.

  


    
What is This Library?¶ ↑

This library provides functionality to send internet mail via SMTP, the Simple Mail Transfer Protocol. For details of SMTP itself, see [RFC2821] (www.ietf.org/rfc/rfc2821.txt).

What is This Library NOT?¶ ↑

This library does NOT provide functions to compose internet mails. You must create them by yourself. If you want better mail support, try RubyMail or TMail or search for alternatives in RubyGems.org or The Ruby Toolbox.

FYI: the official documentation on internet mail is: [RFC2822] (www.ietf.org/rfc/rfc2822.txt).

Examples¶ ↑

Sending Messages¶ ↑

You must open a connection to an SMTP server before sending messages. The first argument is the address of your SMTP server, and the second argument is the port number. Using SMTP.start with a block is the simplest way to do this. This way, the SMTP connection is closed automatically after the block is executed.

require 'net/smtp'
Net::SMTP.start('your.smtp.server', 25) do |smtp|
  # Use the SMTP object smtp only in this block.
end


Replace 'your.smtp.server' with your SMTP server. Normally your system manager or internet provider supplies a server for you.

Then you can send messages.

msgstr = <<END_OF_MESSAGE
From: Your Name <your@mail.address>
To: Destination Address <someone@example.com>
Subject: test message
Date: Sat, 23 Jun 2001 16:26:43 +0900
Message-Id: <unique.message.id.string@example.com>

This is a test message.
END_OF_MESSAGE

require 'net/smtp'
Net::SMTP.start('your.smtp.server', 25) do |smtp|
  smtp.send_message msgstr,
                    'your@mail.address',
                    'his_address@example.com'
end


Closing the Session¶ ↑

You MUST close the SMTP session after sending messages, by calling the finish method:

# using SMTP#finish
smtp = Net::SMTP.start('your.smtp.server', 25)
smtp.send_message msgstr, 'from@address', 'to@address'
smtp.finish


You can also use the block form of SMTP.start/SMTP#start.  This closes the SMTP session automatically:

# using block form of SMTP.start
Net::SMTP.start('your.smtp.server', 25) do |smtp|
  smtp.send_message msgstr, 'from@address', 'to@address'
end


I strongly recommend this scheme.  This form is simpler and more robust.

HELO domain¶ ↑

In almost all situations, you must provide a third argument to SMTP.start/SMTP#start. This is the domain name which you are on (the host to send mail from). It is called the “HELO domain”. The SMTP server will judge whether it should send or reject the SMTP session by inspecting the HELO domain.

Net::SMTP.start('your.smtp.server', 25,
                'mail.from.domain') { |smtp| ... }

SMTP Authentication¶ ↑

The Net::SMTP class supports three authentication schemes; PLAIN, LOGIN and CRAM MD5.  (SMTP Authentication: [RFC2554]) To use SMTP authentication, pass extra arguments to SMTP.start/SMTP#start.

# PLAIN
Net::SMTP.start('your.smtp.server', 25, 'mail.from.domain',
                'Your Account', 'Your Password', :plain)
# LOGIN
Net::SMTP.start('your.smtp.server', 25, 'mail.from.domain',
                'Your Account', 'Your Password', :login)

# CRAM MD5
Net::SMTP.start('your.smtp.server', 25, 'mail.from.domain',
                'Your Account', 'Your Password', :cram_md5)


  


    
This class represents a response received by the SMTP server. Instances of this class are created by the SMTP class; they should not be directly created by the user. For more information on SMTP responses, view Section 4.2 of RFC 5321

  


    
Represents an SMTP authentication error.

  


    
Represents a fatal SMTP error (error code 5xx, except for 500)

  


    
Represents SMTP error code 420 or 450, a temporary error.

  


    
Represents an SMTP command syntax error (error code 500)

  


    
Unexpected reply code returned from server.

  


    
Command is not supported on server.

  


    
The writer adapter class

  


    
WriteTimeout, a subclass of Timeout::Error, is raised if a chunk of the response cannot be written within the write_timeout.  Not raised on Windows.

  


    
The class of the singleton object nil.

  


    
Raised when memory allocation fails.

  


    
Raised when a method is called on a receiver which doesn't have it defined and also fails to respond with method_missing.

"hello".to_ary


raises the exception:

NoMethodError: undefined method `to_ary' for "hello":String

  


    
Raised when a feature is not implemented on the current platform. For example, methods depending on the fsync or fork system calls may raise this exception if the underlying operating system or Ruby runtime does not support them.

Note that if fork raises a NotImplementedError, then respond_to?(:fork) returns false.

  


    
Numeric is the class from which all higher-level numeric classes should inherit.

Numeric allows instantiation of heap-allocated objects. Other core numeric classes such as Integer are implemented as immediates, which means that each Integer is a single immutable object which is always passed by value.

a = 1
1.object_id == a.object_id   #=> true


There can only ever be one instance of the integer 1, for example. Ruby ensures this by preventing instantiation. If duplication is attempted, the same instance is returned.

Integer.new(1)                   #=> NoMethodError: undefined method `new' for Integer:Class
1.dup                            #=> 1
1.object_id == 1.dup.object_id   #=> true


For this reason, Numeric should be used when defining other numeric classes.

Classes which inherit from Numeric must implement coerce, which returns a two-member Array containing an object that has been coerced into an instance of the new class and self (see coerce).

Inheriting classes should also implement arithmetic operator methods (+, -, * and /) and the <=> operator (see Comparable). These methods may rely on coerce to ensure interoperability with instances of other numeric classes.

class Tally < Numeric
  def initialize(string)
    @string = string
  end

  def to_s
    @string
  end

  def to_i
    @string.size
  end

  def coerce(other)
    [self.class.new('|' * other.to_i), self]
  end

  def <=>(other)
    to_i <=> other.to_i
  end

  def +(other)
    self.class.new('|' * (to_i + other.to_i))
  end

  def -(other)
    self.class.new('|' * (to_i - other.to_i))
  end

  def *(other)
    self.class.new('|' * (to_i * other.to_i))
  end

  def /(other)
    self.class.new('|' * (to_i / other.to_i))
  end
end

tally = Tally.new('||')
puts tally * 2            #=> "||||"
puts tally > 1            #=> true


  


    
OLEProperty helper class of Property with arguments.

  


    
Object is the default root of all Ruby objects.  Object inherits from BasicObject which allows creating alternate object hierarchies.  Methods on Object are available to all classes unless explicitly overridden.

Object mixes in the Kernel module, making the built-in kernel functions globally accessible.  Although the instance methods of Object are defined by the Kernel module, we have chosen to document them here for clarity.

When referencing constants in classes inheriting from Object you do not need to use the full namespace.  For example, referencing File inside YourClass will find the top-level File class.

In the descriptions of Object's methods, the parameter symbol refers to a symbol, which is either a quoted string or a Symbol (such as :name).

  


    
Raised by Timeout.timeout when the block times out.

  


    
This class is used as a return value from ObjectSpace::reachable_objects_from.

When ObjectSpace::reachable_objects_from returns an object with references to an internal object, an instance of this class is returned.

You can use the type method to check the type of the internal object.

  


    
An ObjectSpace::WeakMap object holds references to any objects, but those objects can get garbage collected.

This class is mostly used internally by WeakRef, please use lib/weakref.rb for the public interface.

  


    
The top-level class representing any ASN.1 object. When parsed by ASN1.decode, tagged values are always represented by an instance of ASN1Data.

The role of ASN1Data for parsing tagged values¶ ↑

When encoding an ASN.1 type it is inherently clear what original type (e.g. INTEGER, OCTET STRING etc.) this value has, regardless of its tagging. But opposed to the time an ASN.1 type is to be encoded, when parsing them it is not possible to deduce the “real type” of tagged values. This is why tagged values are generally parsed into ASN1Data instances, but with a different outcome for implicit and explicit tagging.

Example of a parsed implicitly tagged value¶ ↑

An implicitly 1-tagged INTEGER value will be parsed as an ASN1Data with

tag equal to 1

tag_class equal to :CONTEXT_SPECIFIC

value equal to a String that carries the raw encoding of the INTEGER.


This implies that a subsequent decoding step is required to completely decode implicitly tagged values.

Example of a parsed explicitly tagged value¶ ↑

An explicitly 1-tagged INTEGER value will be parsed as an ASN1Data with

tag equal to 1

tag_class equal to :CONTEXT_SPECIFIC

value equal to an Array with one single element, an instance of OpenSSL::ASN1::Integer, i.e. the inner element is the non-tagged primitive value, and the tagging is represented in the outer ASN1Data


Example - Decoding an implicitly tagged INTEGER¶ ↑

int = OpenSSL::ASN1::Integer.new(1, 0, :IMPLICIT) # implicit 0-tagged
seq = OpenSSL::ASN1::Sequence.new( [int] )
der = seq.to_der
asn1 = OpenSSL::ASN1.decode(der)
# pp asn1 => #<OpenSSL::ASN1::Sequence:0x87326e0
#              @indefinite_length=false,
#              @tag=16,
#              @tag_class=:UNIVERSAL,
#              @tagging=nil,
#              @value=
#                [#<OpenSSL::ASN1::ASN1Data:0x87326f4
#                   @indefinite_length=false,
#                   @tag=0,
#                   @tag_class=:CONTEXT_SPECIFIC,
#                   @value="\x01">]>
raw_int = asn1.value[0]
# manually rewrite tag and tag class to make it an UNIVERSAL value
raw_int.tag = OpenSSL::ASN1::INTEGER
raw_int.tag_class = :UNIVERSAL
int2 = OpenSSL::ASN1.decode(raw_int)
puts int2.value # => 1


Example - Decoding an explicitly tagged INTEGER¶ ↑

int = OpenSSL::ASN1::Integer.new(1, 0, :EXPLICIT) # explicit 0-tagged
seq = OpenSSL::ASN1::Sequence.new( [int] )
der = seq.to_der
asn1 = OpenSSL::ASN1.decode(der)
# pp asn1 => #<OpenSSL::ASN1::Sequence:0x87326e0
#              @indefinite_length=false,
#              @tag=16,
#              @tag_class=:UNIVERSAL,
#              @tagging=nil,
#              @value=
#                [#<OpenSSL::ASN1::ASN1Data:0x87326f4
#                   @indefinite_length=false,
#                   @tag=0,
#                   @tag_class=:CONTEXT_SPECIFIC,
#                   @value=
#                     [#<OpenSSL::ASN1::Integer:0x85bf308
#                        @indefinite_length=false,
#                        @tag=2,
#                        @tag_class=:UNIVERSAL
#                        @tagging=nil,
#                        @value=1>]>]>
int2 = asn1.value[0].value[0]
puts int2.value # => 1


  


    
Generic error class for all errors raised in ASN1 and any of the classes defined in it.

  


    
The parent class for all constructed encodings. The value attribute of a Constructive is always an Array. Attributes are the same as for ASN1Data, with the addition of tagging.

SET and SEQUENCE¶ ↑

Most constructed encodings come in the form of a SET or a SEQUENCE. These encodings are represented by one of the two sub-classes of Constructive:

OpenSSL::ASN1::Set

OpenSSL::ASN1::Sequence


Please note that tagged sequences and sets are still parsed as instances of ASN1Data. Find further details on tagged values there.

Example - constructing a SEQUENCE¶ ↑

int = OpenSSL::ASN1::Integer.new(1)
str = OpenSSL::ASN1::PrintableString.new('abc')
sequence = OpenSSL::ASN1::Sequence.new( [ int, str ] )


Example - constructing a SET¶ ↑

int = OpenSSL::ASN1::Integer.new(1)
str = OpenSSL::ASN1::PrintableString.new('abc')
set = OpenSSL::ASN1::Set.new( [ int, str ] )


  


    
Represents the primitive object id for OpenSSL::ASN1

  


    
The parent class for all primitive encodings. Attributes are the same as for ASN1Data, with the addition of tagging. Primitive values can never be encoded with indefinite length form, thus it is not possible to set the indefinite_length attribute for Primitive and its sub-classes.

Primitive sub-classes and their mapping to Ruby classes¶ ↑

OpenSSL::ASN1::EndOfContent    <=> value is always nil

OpenSSL::ASN1::Boolean         <=> value is true or false

OpenSSL::ASN1::Integer         <=> value is an OpenSSL::BN

OpenSSL::ASN1::BitString       <=> value is a String

OpenSSL::ASN1::OctetString     <=> value is a String

OpenSSL::ASN1::Null            <=> value is always nil

OpenSSL::ASN1::Object          <=> value is a String

OpenSSL::ASN1::Enumerated      <=> value is an OpenSSL::BN

OpenSSL::ASN1::UTF8String      <=> value is a String

OpenSSL::ASN1::NumericString   <=> value is a String

OpenSSL::ASN1::PrintableString <=> value is a String

OpenSSL::ASN1::T61String       <=> value is a String

OpenSSL::ASN1::VideotexString  <=> value is a String

OpenSSL::ASN1::IA5String       <=> value is a String

OpenSSL::ASN1::UTCTime         <=> value is a Time

OpenSSL::ASN1::GeneralizedTime <=> value is a Time

OpenSSL::ASN1::GraphicString   <=> value is a String

OpenSSL::ASN1::ISO64String     <=> value is a String

OpenSSL::ASN1::GeneralString   <=> value is a String

OpenSSL::ASN1::UniversalString <=> value is a String

OpenSSL::ASN1::BMPString       <=> value is a String


OpenSSL::ASN1::BitString¶ ↑

Additional attributes¶ ↑

unused_bits: if the underlying BIT STRING's length is a multiple of 8 then unused_bits is 0. Otherwise unused_bits indicates the number of bits that are to be ignored in the final octet of the BitString's value.

OpenSSL::ASN1::ObjectId¶ ↑

NOTE: While OpenSSL::ASN1::ObjectId.new will allocate a new ObjectId, it is not typically allocated this way, but rather that are received from parsed ASN1 encodings.

Additional attributes¶ ↑

sn: the short name as defined in <openssl/objects.h>.

ln: the long name as defined in <openssl/objects.h>.

oid: the object identifier as a String, e.g. “1.2.3.4.5”

short_name: alias for sn.

long_name: alias for ln.


Examples¶ ↑

With the Exception of OpenSSL::ASN1::EndOfContent, each Primitive class constructor takes at least one parameter, the value.

Creating EndOfContent¶ ↑

eoc = OpenSSL::ASN1::EndOfContent.new


Creating any other Primitive¶ ↑

prim = <class>.new(value) # <class> being one of the sub-classes except EndOfContent
prim_zero_tagged_implicit = <class>.new(value, 0, :IMPLICIT)
prim_zero_tagged_explicit = <class>.new(value, 0, :EXPLICIT)

  


    
Generic Error for all of OpenSSL::BN (big num)

  


    
Provides symmetric algorithms for encryption and decryption. The algorithms that are available depend on the particular version of OpenSSL that is installed.

Listing all supported algorithms¶ ↑

A list of supported algorithms can be obtained by

puts OpenSSL::Cipher.ciphers


Instantiating a Cipher¶ ↑

There are several ways to create a Cipher instance. Generally, a Cipher algorithm is categorized by its name, the key length in bits and the cipher mode to be used. The most generic way to create a Cipher is the following

cipher = OpenSSL::Cipher.new('<name>-<key length>-<mode>')


That is, a string consisting of the hyphenated concatenation of the individual components name, key length and mode. Either all uppercase or all lowercase strings may be used, for example:

cipher = OpenSSL::Cipher.new('AES-128-CBC')


For each algorithm supported, there is a class defined under the Cipher class that goes by the name of the cipher, e.g. to obtain an instance of AES, you could also use

# these are equivalent
cipher = OpenSSL::Cipher::AES.new(128, :CBC)
cipher = OpenSSL::Cipher::AES.new(128, 'CBC')
cipher = OpenSSL::Cipher::AES.new('128-CBC')


Finally, due to its wide-spread use, there are also extra classes defined for the different key sizes of AES

cipher = OpenSSL::Cipher::AES128.new(:CBC)
cipher = OpenSSL::Cipher::AES192.new(:CBC)
cipher = OpenSSL::Cipher::AES256.new(:CBC)


Choosing either encryption or decryption mode¶ ↑

Encryption and decryption are often very similar operations for symmetric algorithms, this is reflected by not having to choose different classes for either operation, both can be done using the same class. Still, after obtaining a Cipher instance, we need to tell the instance what it is that we intend to do with it, so we need to call either

cipher.encrypt


or

cipher.decrypt


on the Cipher instance. This should be the first call after creating the instance, otherwise configuration that has already been set could get lost in the process.

Choosing a key¶ ↑

Symmetric encryption requires a key that is the same for the encrypting and for the decrypting party and after initial key establishment should be kept as private information. There are a lot of ways to create insecure keys, the most notable is to simply take a password as the key without processing the password further. A simple and secure way to create a key for a particular Cipher is

cipher = OpenSSL::AES256.new(:CFB)
cipher.encrypt
key = cipher.random_key # also sets the generated key on the Cipher


If you absolutely need to use passwords as encryption keys, you should use Password-Based Key Derivation Function 2 (PBKDF2) by generating the key with the help of the functionality provided by OpenSSL::PKCS5.pbkdf2_hmac_sha1 or OpenSSL::PKCS5.pbkdf2_hmac.

Although there is Cipher#pkcs5_keyivgen, its use is deprecated and it should only be used in legacy applications because it does not use the newer PKCS#5 v2 algorithms.

Choosing an IV¶ ↑

The cipher modes CBC, CFB, OFB and CTR all need an “initialization vector”, or short, IV. ECB mode is the only mode that does not require an IV, but there is almost no legitimate use case for this mode because of the fact that it does not sufficiently hide plaintext patterns. Therefore

You should never use ECB mode unless you are absolutely sure that you absolutely need it

Because of this, you will end up with a mode that explicitly requires an IV in any case. Although the IV can be seen as public information, i.e. it may be transmitted in public once generated, it should still stay unpredictable to prevent certain kinds of attacks. Therefore, ideally

Always create a secure random IV for every encryption of your Cipher

A new, random IV should be created for every encryption of data. Think of the IV as a nonce (number used once) - it's public but random and unpredictable. A secure random IV can be created as follows

cipher = ...
cipher.encrypt
key = cipher.random_key
iv = cipher.random_iv # also sets the generated IV on the Cipher

Although the key is generally a random value, too, it is a bad choice as an IV. There are elaborate ways how an attacker can take advantage of such an IV. As a general rule of thumb, exposing the key directly or indirectly should be avoided at all cost and exceptions only be made with good reason.

Calling Cipher#final¶ ↑

ECB (which should not be used) and CBC are both block-based modes. This means that unlike for the other streaming-based modes, they operate on fixed-size blocks of data, and therefore they require a “finalization” step to produce or correctly decrypt the last block of data by appropriately handling some form of padding. Therefore it is essential to add the output of OpenSSL::Cipher#final to your encryption/decryption buffer or you will end up with decryption errors or truncated data.

Although this is not really necessary for streaming-mode ciphers, it is still recommended to apply the same pattern of adding the output of Cipher#final there as well - it also enables you to switch between modes more easily in the future.

Encrypting and decrypting some data¶ ↑

data = "Very, very confidential data"

cipher = OpenSSL::Cipher::AES.new(128, :CBC)
cipher.encrypt
key = cipher.random_key
iv = cipher.random_iv

encrypted = cipher.update(data) + cipher.final
...
decipher = OpenSSL::Cipher::AES.new(128, :CBC)
decipher.decrypt
decipher.key = key
decipher.iv = iv

plain = decipher.update(encrypted) + decipher.final

puts data == plain #=> true

Authenticated Encryption and Associated Data (AEAD)¶ ↑

If the OpenSSL version used supports it, an Authenticated Encryption mode (such as GCM or CCM) should always be preferred over any unauthenticated mode. Currently, OpenSSL supports AE only in combination with Associated Data (AEAD) where additional associated data is included in the encryption process to compute a tag at the end of the encryption. This tag will also be used in the decryption process and by verifying its validity, the authenticity of a given ciphertext is established.

This is superior to unauthenticated modes in that it allows to detect if somebody effectively changed the ciphertext after it had been encrypted. This prevents malicious modifications of the ciphertext that could otherwise be exploited to modify ciphertexts in ways beneficial to potential attackers.

An associated data is used where there is additional information, such as headers or some metadata, that must be also authenticated but not necessarily need to be encrypted. If no associated data is needed for encryption and later decryption, the OpenSSL library still requires a value to be set - “” may be used in case none is available.

An example using the GCM (Galois/Counter Mode). You have 16 bytes key, 12 bytes (96 bits) nonce and the associated data auth_data. Be sure not to reuse the key and nonce pair. Reusing an nonce ruins the security guarantees of GCM mode.

cipher = OpenSSL::Cipher::AES.new(128, :GCM).encrypt
cipher.key = key
cipher.iv = nonce
cipher.auth_data = auth_data

encrypted = cipher.update(data) + cipher.final
tag = cipher.auth_tag # produces 16 bytes tag by default


Now you are the receiver. You know the key and have received nonce, auth_data, encrypted and tag through an untrusted network. Note that GCM accepts an arbitrary length tag between 1 and 16 bytes. You may additionally need to check that the received tag has the correct length, or you allow attackers to forge a valid single byte tag for the tampered ciphertext with a probability of 1/256.

raise "tag is truncated!" unless tag.bytesize == 16
decipher = OpenSSL::Cipher::AES.new(128, :GCM).decrypt
decipher.key = key
decipher.iv = nonce
decipher.auth_tag = tag
decipher.auth_data = auth_data

decrypted = decipher.update(encrypted) + decipher.final

puts data == decrypted #=> true


  


    
Deprecated.

This class is only provided for backwards compatibility. Use OpenSSL::Cipher.

  


    
OpenSSL::Config¶ ↑

Configuration for the openssl library.

Many system's installation of openssl library will depend on your system configuration. See the value of OpenSSL::Config::DEFAULT_CONFIG_FILE for the location of the file for your host.

See also www.openssl.org/docs/apps/config.html

  


    
General error for openssl library configuration files. Including formatting, parsing errors, etc.

  


    
OpenSSL::Digest allows you to compute message digests (sometimes interchangeably called “hashes”) of arbitrary data that are cryptographically secure, i.e. a Digest implements a secure one-way function.

One-way functions offer some useful properties. E.g. given two distinct inputs the probability that both yield the same output is highly unlikely. Combined with the fact that every message digest algorithm has a fixed-length output of just a few bytes, digests are often used to create unique identifiers for arbitrary data. A common example is the creation of a unique id for binary documents that are stored in a database.

Another useful characteristic of one-way functions (and thus the name) is that given a digest there is no indication about the original data that produced it, i.e. the only way to identify the original input is to “brute-force” through every possible combination of inputs.

These characteristics make one-way functions also ideal companions for public key signature algorithms: instead of signing an entire document, first a hash of the document is produced with a considerably faster message digest algorithm and only the few bytes of its output need to be signed using the slower public key algorithm. To validate the integrity of a signed document, it suffices to re-compute the hash and verify that it is equal to that in the signature.

Among the supported message digest algorithms are:

SHA, SHA1, SHA224, SHA256, SHA384 and SHA512

MD2, MD4, MDC2 and MD5

RIPEMD160

DSS, DSS1 (Pseudo algorithms to be used for DSA signatures. DSS is equal to SHA and DSS1 is equal to SHA1)


For each of these algorithms, there is a sub-class of Digest that can be instantiated as simply as e.g.

digest = OpenSSL::Digest::SHA1.new


Mapping between Digest class and sn/ln¶ ↑

The sn (short names) and ln (long names) are defined in <openssl/object.h> and <openssl/obj_mac.h>. They are textual representations of ASN.1 OBJECT IDENTIFIERs. Each supported digest algorithm has an OBJECT IDENTIFIER associated to it and those again have short/long names assigned to them. E.g. the OBJECT IDENTIFIER for SHA-1 is 1.3.14.3.2.26 and its sn is “SHA1” and its ln is “sha1”.

MD2¶ ↑

sn: MD2

ln: md2


MD4¶ ↑

sn: MD4

ln: md4


MD5¶ ↑

sn: MD5

ln: md5


SHA¶ ↑

sn: SHA

ln: SHA


SHA-1¶ ↑

sn: SHA1

ln: sha1


SHA-224¶ ↑

sn: SHA224

ln: sha224


SHA-256¶ ↑

sn: SHA256

ln: sha256


SHA-384¶ ↑

sn: SHA384

ln: sha384


SHA-512¶ ↑

sn: SHA512

ln: sha512


“Breaking” a message digest algorithm means defying its one-way function characteristics, i.e. producing a collision or finding a way to get to the original data by means that are more efficient than brute-forcing etc. Most of the supported digest algorithms can be considered broken in this sense, even the very popular MD5 and SHA1 algorithms. Should security be your highest concern, then you should probably rely on SHA224, SHA256, SHA384 or SHA512.

Hashing a file¶ ↑

data = File.read('document')
sha256 = OpenSSL::Digest::SHA256.new
digest = sha256.digest(data)


Hashing several pieces of data at once¶ ↑

data1 = File.read('file1')
data2 = File.read('file2')
data3 = File.read('file3')
sha256 = OpenSSL::Digest::SHA256.new
sha256 << data1
sha256 << data2
sha256 << data3
digest = sha256.digest


Reuse a Digest instance¶ ↑

data1 = File.read('file1')
sha256 = OpenSSL::Digest::SHA256.new
digest1 = sha256.digest(data1)

data2 = File.read('file2')
sha256.reset
digest2 = sha256.digest(data2)


  


    
Generic Exception class that is raised if an error occurs during a Digest operation.

  


    
This class is the access to openssl's ENGINE cryptographic module implementation.

See also, www.openssl.org/docs/crypto/engine.html

  


    
This is the generic exception for OpenSSL::Engine related errors

  


    
OpenSSL::HMAC allows computing Hash-based Message Authentication Code (HMAC). It is a type of message authentication code (MAC) involving a hash function in combination with a key. HMAC can be used to verify the integrity of a message as well as the authenticity.

OpenSSL::HMAC has a similar interface to OpenSSL::Digest.

HMAC-SHA256 using one-shot interface¶ ↑

key = "key"
data = "message-to-be-authenticated"
mac = OpenSSL::HMAC.hexdigest("SHA256", key, data)
#=> "cddb0db23f469c8bf072b21fd837149bd6ace9ab771cceef14c9e517cc93282e"


HMAC-SHA256 using incremental interface¶ ↑

data1 = File.read("file1")
data2 = File.read("file2")
key = "key"
digest = OpenSSL::Digest::SHA256.new
hmac = OpenSSL::HMAC.new(key, digest)
hmac << data1
hmac << data2
mac = hmac.digest


  


    
Document-class: OpenSSL::HMAC

OpenSSL::HMAC allows computing Hash-based Message Authentication Code (HMAC). It is a type of message authentication code (MAC) involving a hash function in combination with a key. HMAC can be used to verify the integrity of a message as well as the authenticity.

OpenSSL::HMAC has a similar interface to OpenSSL::Digest.

HMAC-SHA256 using one-shot interface¶ ↑

key = "key"
data = "message-to-be-authenticated"
mac = OpenSSL::HMAC.hexdigest("SHA256", key, data)
#=> "cddb0db23f469c8bf072b21fd837149bd6ace9ab771cceef14c9e517cc93282e"


HMAC-SHA256 using incremental interface¶ ↑

data1 = File.read("file1")
data2 = File.read("file2")
key = "key"
digest = OpenSSL::Digest::SHA256.new
hmac = OpenSSL::HMAC.new(key, digest)
hmac << data1
hmac << data2
mac = hmac.digest


  


    
Generic exception class raised if an error occurs in OpenSSL::KDF module.

  


    
A Simple Public Key Infrastructure implementation (pronounced “spooky”). The structure is defined as

PublicKeyAndChallenge ::= SEQUENCE {
  spki SubjectPublicKeyInfo,
  challenge IA5STRING
}

SignedPublicKeyAndChallenge ::= SEQUENCE {
  publicKeyAndChallenge PublicKeyAndChallenge,
  signatureAlgorithm AlgorithmIdentifier,
  signature BIT STRING
}

where the definitions of SubjectPublicKeyInfo and AlgorithmIdentifier can be found in RFC5280. SPKI is typically used in browsers for generating a public/private key pair and a subsequent certificate request, using the HTML <keygen> element.

Examples¶ ↑

Creating an SPKI¶ ↑

key = OpenSSL::PKey::RSA.new 2048
spki = OpenSSL::Netscape::SPKI.new
spki.challenge = "RandomChallenge"
spki.public_key = key.public_key
spki.sign(key, OpenSSL::Digest::SHA256.new)
#send a request containing this to a server generating a certificate


Verifying an SPKI request¶ ↑

request = #...
spki = OpenSSL::Netscape::SPKI.new request
unless spki.verify(spki.public_key)
  # signature is invalid
end
#proceed


  


    
Generic Exception class that is raised if an error occurs during an operation on an instance of OpenSSL::Netscape::SPKI.

  


    
An OpenSSL::OCSP::BasicResponse contains the status of a certificate check which is created from an OpenSSL::OCSP::Request.  A BasicResponse is more detailed than a Response.

  


    
An OpenSSL::OCSP::CertificateId identifies a certificate to the CA so that a status check can be performed.

  


    
OCSP error class.

  


    
An OpenSSL::OCSP::Request contains the certificate information for determining if a certificate has been revoked or not.  A Request can be created for a certificate or from a DER-encoded request created elsewhere.

  


    
An OpenSSL::OCSP::Response contains the status of a certificate check which is created from an OpenSSL::OCSP::Request.

  


    
An OpenSSL::OCSP::SingleResponse represents an OCSP SingleResponse structure, which contains the basic information of the status of the certificate.

  


    
Generic error, common for all classes under OpenSSL module

  


    
Defines a file format commonly used to store private keys with accompanying public key certificates, protected with a password-based symmetric key.

  


    
An implementation of the Diffie-Hellman key exchange protocol based on discrete logarithms in finite fields, the same basis that DSA is built on.

Accessor methods for the Diffie-Hellman parameters¶ ↑
DH#p

The prime (an OpenSSL::BN) of the Diffie-Hellman parameters.
DH#g

The generator (an OpenSSL::BN) g of the Diffie-Hellman parameters.
DH#pub_key

The per-session public key (an OpenSSL::BN) matching the private key. This needs to be passed to DH#compute_key.
DH#priv_key

The per-session private key, an OpenSSL::BN.


Example of a key exchange¶ ↑

dh1 = OpenSSL::PKey::DH.new(2048)
der = dh1.public_key.to_der #you may send this publicly to the participating party
dh2 = OpenSSL::PKey::DH.new(der)
dh2.generate_key! #generate the per-session key pair
symm_key1 = dh1.compute_key(dh2.pub_key)
symm_key2 = dh2.compute_key(dh1.pub_key)

puts symm_key1 == symm_key2 # => true


  


    
Generic exception that is raised if an operation on a DH PKey fails unexpectedly or in case an instantiation of an instance of DH fails due to non-conformant input data.

  


    
DSA, the Digital Signature Algorithm, is specified in NIST's FIPS 186-3. It is an asymmetric public key algorithm that may be used similar to e.g. RSA.

  


    
Generic exception that is raised if an operation on a DSA PKey fails unexpectedly or in case an instantiation of an instance of DSA fails due to non-conformant input data.

  


    
OpenSSL::PKey::EC provides access to Elliptic Curve Digital Signature Algorithm (ECDSA) and Elliptic Curve Diffie-Hellman (ECDH).

Key exchange¶ ↑

ec1 = OpenSSL::PKey::EC.generate("prime256v1")
ec2 = OpenSSL::PKey::EC.generate("prime256v1")
# ec1 and ec2 have own private key respectively
shared_key1 = ec1.dh_compute_key(ec2.public_key)
shared_key2 = ec2.dh_compute_key(ec1.public_key)

p shared_key1 == shared_key2 #=> true


  


    
An abstract class that bundles signature creation (PKey#sign) and validation (PKey#verify) that is common to all implementations except OpenSSL::PKey::DH

OpenSSL::PKey::RSA

OpenSSL::PKey::DSA

OpenSSL::PKey::EC


  


    
Raised when errors occur during PKey#sign or PKey#verify.

  


    
RSA is an asymmetric public key algorithm that has been formalized in RFC 3447. It is in widespread use in public key infrastructures (PKI) where certificates (cf. OpenSSL::X509::Certificate) often are issued on the basis of a public/private RSA key pair. RSA is used in a wide field of applications such as secure (symmetric) key exchange, e.g. when establishing a secure TLS/SSL connection. It is also used in various digital signature schemes.

  


    
Generic exception that is raised if an operation on an RSA PKey fails unexpectedly or in case an instantiation of an instance of RSA fails due to non-conformant input data.

  


    
An SSLContext is used to set various options regarding certificates, algorithms, verification, session caching, etc.  The SSLContext is used to create an SSLSocket.

All attributes must be set before creating an SSLSocket as the SSLContext will be frozen afterward.

  


    
Generic error class raised by SSLSocket and SSLContext.

  


    
SSLServer represents a TCP/IP server socket with Secure Sockets Layer.

  


    
Implementation of an X.509 certificate as specified in RFC 5280. Provides access to a certificate's attributes and allows certificates to be read from a string, but also supports the creation of new certificates from scratch.

Reading a certificate from a file¶ ↑

Certificate is capable of handling DER-encoded certificates and certificates encoded in OpenSSL's PEM format.

raw = File.read "cert.cer" # DER- or PEM-encoded
certificate = OpenSSL::X509::Certificate.new raw


Saving a certificate to a file¶ ↑

A certificate may be encoded in DER format

cert = ...
File.open("cert.cer", "wb") { |f| f.print cert.to_der }

or in PEM format

cert = ...
File.open("cert.pem", "wb") { |f| f.print cert.to_pem }

X.509 certificates are associated with a private/public key pair, typically a RSA, DSA or ECC key (see also OpenSSL::PKey::RSA, OpenSSL::PKey::DSA and OpenSSL::PKey::EC), the public key itself is stored within the certificate and can be accessed in form of an OpenSSL::PKey. Certificates are typically used to be able to associate some form of identity with a key pair, for example web servers serving pages over HTTPs use certificates to authenticate themselves to the user.

The public key infrastructure (PKI) model relies on trusted certificate authorities (“root CAs”) that issue these certificates, so that end users need to base their trust just on a selected few authorities that themselves again vouch for subordinate CAs issuing their certificates to end users.

The OpenSSL::X509 module provides the tools to set up an independent PKI, similar to scenarios where the 'openssl' command line tool is used for issuing certificates in a private PKI.

Creating a root CA certificate and an end-entity certificate¶ ↑

First, we need to create a “self-signed” root certificate. To do so, we need to generate a key first. Please note that the choice of “1” as a serial number is considered a security flaw for real certificates. Secure choices are integers in the two-digit byte range and ideally not sequential but secure random numbers, steps omitted here to keep the example concise.

root_key = OpenSSL::PKey::RSA.new 2048 # the CA's public/private key
root_ca = OpenSSL::X509::Certificate.new
root_ca.version = 2 # cf. RFC 5280 - to make it a "v3" certificate
root_ca.serial = 1
root_ca.subject = OpenSSL::X509::Name.parse "/DC=org/DC=ruby-lang/CN=Ruby CA"
root_ca.issuer = root_ca.subject # root CA's are "self-signed"
root_ca.public_key = root_key.public_key
root_ca.not_before = Time.now
root_ca.not_after = root_ca.not_before + 2 * 365 * 24 * 60 * 60 # 2 years validity
ef = OpenSSL::X509::ExtensionFactory.new
ef.subject_certificate = root_ca
ef.issuer_certificate = root_ca
root_ca.add_extension(ef.create_extension("basicConstraints","CA:TRUE",true))
root_ca.add_extension(ef.create_extension("keyUsage","keyCertSign, cRLSign", true))
root_ca.add_extension(ef.create_extension("subjectKeyIdentifier","hash",false))
root_ca.add_extension(ef.create_extension("authorityKeyIdentifier","keyid:always",false))
root_ca.sign(root_key, OpenSSL::Digest::SHA256.new)


The next step is to create the end-entity certificate using the root CA certificate.

key = OpenSSL::PKey::RSA.new 2048
cert = OpenSSL::X509::Certificate.new
cert.version = 2
cert.serial = 2
cert.subject = OpenSSL::X509::Name.parse "/DC=org/DC=ruby-lang/CN=Ruby certificate"
cert.issuer = root_ca.subject # root CA is the issuer
cert.public_key = key.public_key
cert.not_before = Time.now
cert.not_after = cert.not_before + 1 * 365 * 24 * 60 * 60 # 1 years validity
ef = OpenSSL::X509::ExtensionFactory.new
ef.subject_certificate = cert
ef.issuer_certificate = root_ca
cert.add_extension(ef.create_extension("keyUsage","digitalSignature", true))
cert.add_extension(ef.create_extension("subjectKeyIdentifier","hash",false))
cert.sign(root_key, OpenSSL::Digest::SHA256.new)


  


    
An X.509 name represents a hostname, email address or other entity associated with a public key.

You can create a Name by parsing a distinguished name String or by supplying the distinguished name as an Array.

name = OpenSSL::X509::Name.parse 'CN=nobody/DC=example'

name = OpenSSL::X509::Name.new [['CN', 'nobody'], ['DC', 'example']]


  


    
The X509 certificate store holds trusted CA certificates used to verify peer certificates.

The easiest way to create a useful certificate store is:

cert_store = OpenSSL::X509::Store.new
cert_store.set_default_paths


This will use your system's built-in certificates.

If your system does not have a default set of certificates you can obtain a set extracted from Mozilla CA certificate store by cURL maintainers here: curl.haxx.se/docs/caextract.html (You may wish to use the firefox-db2pem.sh script to extract the certificates from a local install to avoid man-in-the-middle attacks.)

After downloading or generating a cacert.pem from the above link you can create a certificate store from the pem file like this:

cert_store = OpenSSL::X509::Store.new
cert_store.add_file 'cacert.pem'


The certificate store can be used with an SSLSocket like this:

ssl_context = OpenSSL::SSL::SSLContext.new
ssl_context.verify_mode = OpenSSL::SSL::VERIFY_PEER
ssl_context.cert_store = cert_store

tcp_socket = TCPSocket.open 'example.com', 443

ssl_socket = OpenSSL::SSL::SSLSocket.new tcp_socket, ssl_context


  


    
A StoreContext is used while validating a single certificate and holds the status involved.

  


    
An OpenStruct is a data structure, similar to a Hash, that allows the definition of arbitrary attributes with their accompanying values. This is accomplished by using Ruby's metaprogramming to define methods on the class itself.

Examples¶ ↑

require "ostruct"

person = OpenStruct.new
person.name = "John Smith"
person.age  = 70

person.name      # => "John Smith"
person.age       # => 70
person.address   # => nil


An OpenStruct employs a Hash internally to store the attributes and values and can even be initialized with one:

australia = OpenStruct.new(:country => "Australia", :capital => "Canberra")
  # => #<OpenStruct country="Australia", capital="Canberra">


Hash keys with spaces or characters that could normally not be used for method calls (e.g. ()[]*) will not be immediately available on the OpenStruct object as a method for retrieval or assignment, but can still be reached through the Object#send method.

measurements = OpenStruct.new("length (in inches)" => 24)
measurements.send("length (in inches)")   # => 24

message = OpenStruct.new(:queued? => true)
message.queued?                           # => true
message.send("queued?=", false)
message.queued?                           # => false


Removing the presence of an attribute requires the execution of the delete_field method as setting the property value to nil will not remove the attribute.

first_pet  = OpenStruct.new(:name => "Rowdy", :owner => "John Smith")
second_pet = OpenStruct.new(:name => "Rowdy")

first_pet.owner = nil
first_pet                 # => #<OpenStruct name="Rowdy", owner=nil>
first_pet == second_pet   # => false

first_pet.delete_field(:owner)
first_pet                 # => #<OpenStruct name="Rowdy">
first_pet == second_pet   # => true


Implementation¶ ↑

An OpenStruct utilizes Ruby's method lookup structure to find and define the necessary methods for properties. This is accomplished through the methods method_missing and define_singleton_method.

This should be a consideration if there is a concern about the performance of the objects that are created, as there is much more overhead in the setting of these properties compared to using a Hash or a Struct.

  


    
Raised on redirection, only occurs when redirect option for HTTP is false.

  


    
OptionParser¶ ↑

Introduction¶ ↑

OptionParser is a class for command-line option analysis.  It is much more advanced, yet also easier to use, than GetoptLong, and is a more Ruby-oriented solution.

Features¶ ↑

The argument specification and the code to handle it are written in the same place.

It can output an option summary; you don't need to maintain this string separately.

Optional and mandatory arguments are specified very gracefully.

Arguments can be automatically converted to a specified class.

Arguments can be restricted to a certain set.


All of these features are demonstrated in the examples below.  See make_switch for full documentation.

Minimal example¶ ↑

require 'optparse'

options = {}
OptionParser.new do |opts|
  opts.banner = "Usage: example.rb [options]"

  opts.on("-v", "--[no-]verbose", "Run verbosely") do |v|
    options[:verbose] = v
  end
end.parse!

p options
p ARGV


Generating Help¶ ↑

OptionParser can be used to automatically generate help for the commands you write:

require 'optparse'

Options = Struct.new(:name)

class Parser
  def self.parse(options)
    args = Options.new("world")

    opt_parser = OptionParser.new do |opts|
      opts.banner = "Usage: example.rb [options]"

      opts.on("-nNAME", "--name=NAME", "Name to say hello to") do |n|
        args.name = n
      end

      opts.on("-h", "--help", "Prints this help") do
        puts opts
        exit
      end
    end

    opt_parser.parse!(options)
    return args
  end
end
options = Parser.parse %w[--help]

#=>
   # Usage: example.rb [options]
   #     -n, --name=NAME                  Name to say hello to
   #     -h, --help                       Prints this help


Required Arguments¶ ↑

For options that require an argument, option specification strings may include an option name in all caps. If an option is used without the required argument, an exception will be raised.

require 'optparse'

options = {}
OptionParser.new do |parser|
  parser.on("-r", "--require LIBRARY",
            "Require the LIBRARY before executing your script") do |lib|
    puts "You required #{lib}!"
  end
end.parse!


Used:

$ ruby optparse-test.rb -r
optparse-test.rb:9:in `<main>': missing argument: -r (OptionParser::MissingArgument)
$ ruby optparse-test.rb -r my-library
You required my-library!

Type Coercion¶ ↑

OptionParser supports the ability to coerce command line arguments into objects for us.

OptionParser comes with a few ready-to-use kinds of  type coercion. They are:

Date  – Anything accepted by Date.parse

DateTime – Anything accepted by DateTime.parse

Time – Anything accepted by Time.httpdate or Time.parse

URI  – Anything accepted by URI.parse

Shellwords – Anything accepted by Shellwords.shellwords

String – Any non-empty string

Integer – Any integer. Will convert octal. (e.g. 124, -3, 040)

Float – Any float. (e.g. 10, 3.14, -100E+13)

Numeric – Any integer, float, or rational (1, 3.4, 1/3)

DecimalInteger – Like Integer, but no octal format.

OctalInteger – Like Integer, but no decimal format.

DecimalNumeric – Decimal integer or float.

TrueClass –  Accepts '+, yes, true, -, no, false' and defaults as true

FalseClass – Same as TrueClass, but defaults to false

Array – Strings separated by ',' (e.g. 1,2,3)

Regexp – Regular expressions. Also includes options.


We can also add our own coercions, which we will cover soon.

Using Built-in Conversions¶ ↑

As an example, the built-in Time conversion is used. The other built-in conversions behave in the same way. OptionParser will attempt to parse the argument as a Time. If it succeeds, that time will be passed to the handler block. Otherwise, an exception will be raised.

require 'optparse'
require 'optparse/time'
OptionParser.new do |parser|
  parser.on("-t", "--time [TIME]", Time, "Begin execution at given time") do |time|
    p time
  end
end.parse!


Used:

$ ruby optparse-test.rb  -t nonsense
... invalid argument: -t nonsense (OptionParser::InvalidArgument)
$ ruby optparse-test.rb  -t 10-11-12
2010-11-12 00:00:00 -0500
$ ruby optparse-test.rb  -t 9:30
2014-08-13 09:30:00 -0400

Creating Custom Conversions¶ ↑

The accept method on OptionParser may be used to create converters. It specifies which conversion block to call whenever a class is specified. The example below uses it to fetch a User object before the on handler receives it.

require 'optparse'

User = Struct.new(:id, :name)

def find_user id
  not_found = ->{ raise "No User Found for id #{id}" }
  [ User.new(1, "Sam"),
    User.new(2, "Gandalf") ].find(not_found) do |u|
    u.id == id
  end
end

op = OptionParser.new
op.accept(User) do |user_id|
  find_user user_id.to_i
end

op.on("--user ID", User) do |user|
  puts user
end

op.parse!


Used:

$ ruby optparse-test.rb --user 1
#<struct User id=1, name="Sam">
$ ruby optparse-test.rb --user 2
#<struct User id=2, name="Gandalf">
$ ruby optparse-test.rb --user 3
optparse-test.rb:15:in `block in find_user': No User Found for id 3 (RuntimeError)

Store options to a Hash¶ ↑

The into option of order, parse and so on methods stores command line options into a Hash.

require 'optparse'

params = {}
OptionParser.new do |opts|
  opts.on('-a')
  opts.on('-b NUM', Integer)
  opts.on('-v', '--verbose')
end.parse!(into: params)

p params


Used:

$ ruby optparse-test.rb -a
{:a=>true}
$ ruby optparse-test.rb -a -v
{:a=>true, :verbose=>true}
$ ruby optparse-test.rb -a -b 100
{:a=>true, :b=>100}

Complete example¶ ↑

The following example is a complete Ruby program.  You can run it and see the effect of specifying various options.  This is probably the best way to learn the features of optparse.

require 'optparse'
require 'optparse/time'
require 'ostruct'
require 'pp'

class OptparseExample
  Version = '1.0.0'

  CODES = %w[iso-2022-jp shift_jis euc-jp utf8 binary]
  CODE_ALIASES = { "jis" => "iso-2022-jp", "sjis" => "shift_jis" }

  class ScriptOptions
    attr_accessor :library, :inplace, :encoding, :transfer_type,
                  :verbose, :extension, :delay, :time, :record_separator,
                  :list

    def initialize
      self.library = []
      self.inplace = false
      self.encoding = "utf8"
      self.transfer_type = :auto
      self.verbose = false
    end

    def define_options(parser)
      parser.banner = "Usage: example.rb [options]"
      parser.separator ""
      parser.separator "Specific options:"

      # add additional options
      perform_inplace_option(parser)
      delay_execution_option(parser)
      execute_at_time_option(parser)
      specify_record_separator_option(parser)
      list_example_option(parser)
      specify_encoding_option(parser)
      optional_option_argument_with_keyword_completion_option(parser)
      boolean_verbose_option(parser)

      parser.separator ""
      parser.separator "Common options:"
      # No argument, shows at tail.  This will print an options summary.
      # Try it and see!
      parser.on_tail("-h", "--help", "Show this message") do
        puts parser
        exit
      end
      # Another typical switch to print the version.
      parser.on_tail("--version", "Show version") do
        puts Version
        exit
      end
    end

    def perform_inplace_option(parser)
      # Specifies an optional option argument
      parser.on("-i", "--inplace [EXTENSION]",
                "Edit ARGV files in place",
                "(make backup if EXTENSION supplied)") do |ext|
        self.inplace = true
        self.extension = ext || ''
        self.extension.sub!(/\A\.?(?=.)/, ".")  # Ensure extension begins with dot.
      end
    end

    def delay_execution_option(parser)
      # Cast 'delay' argument to a Float.
      parser.on("--delay N", Float, "Delay N seconds before executing") do |n|
        self.delay = n
      end
    end

    def execute_at_time_option(parser)
      # Cast 'time' argument to a Time object.
      parser.on("-t", "--time [TIME]", Time, "Begin execution at given time") do |time|
        self.time = time
      end
    end

    def specify_record_separator_option(parser)
      # Cast to octal integer.
      parser.on("-F", "--irs [OCTAL]", OptionParser::OctalInteger,
                "Specify record separator (default \\0)") do |rs|
        self.record_separator = rs
      end
    end

    def list_example_option(parser)
      # List of arguments.
      parser.on("--list x,y,z", Array, "Example 'list' of arguments") do |list|
        self.list = list
      end
    end

    def specify_encoding_option(parser)
      # Keyword completion.  We are specifying a specific set of arguments (CODES
      # and CODE_ALIASES - notice the latter is a Hash), and the user may provide
      # the shortest unambiguous text.
      code_list = (CODE_ALIASES.keys + CODES).join(', ')
      parser.on("--code CODE", CODES, CODE_ALIASES, "Select encoding",
                "(#{code_list})") do |encoding|
        self.encoding = encoding
      end
    end

    def optional_option_argument_with_keyword_completion_option(parser)
      # Optional '--type' option argument with keyword completion.
      parser.on("--type [TYPE]", [:text, :binary, :auto],
                "Select transfer type (text, binary, auto)") do |t|
        self.transfer_type = t
      end
    end

    def boolean_verbose_option(parser)
      # Boolean switch.
      parser.on("-v", "--[no-]verbose", "Run verbosely") do |v|
        self.verbose = v
      end
    end
  end

  #
  # Return a structure describing the options.
  #
  def parse(args)
    # The options specified on the command line will be collected in
    # *options*.

    @options = ScriptOptions.new
    @args = OptionParser.new do |parser|
      @options.define_options(parser)
      parser.parse!(args)
    end
    @options
  end

  attr_reader :parser, :options
end  # class OptparseExample

example = OptparseExample.new
options = example.parse(ARGV)
pp options # example.options
pp ARGV


Shell Completion¶ ↑

For modern shells (e.g. bash, zsh, etc.), you can use shell completion for command line options.

Further documentation¶ ↑

The above examples should be enough to learn how to use this class.  If you have any questions, file a ticket at bugs.ruby-lang.org.

  


    
Raises when the given argument word can't be completed uniquely.

  


    
Raises when ambiguously completable string is encountered.

  


    
Hash with completion search feature. See OptionParser::Completion.

  


    
Raises when the given argument does not match required format.

  


    
Raises when switch is undefined.

  


    
Simple option list providing mapping from short and/or long option string to OptionParser::Switch and mapping from acceptable argument to matching pattern and converter pair. Also provides summary feature.

  


    
Raises when a switch with mandatory argument has no argument.

  


    
Raises when there is an argument for a switch which takes no argument.

  


    
Map from option/keyword string to object with completion.

  


    
Base class of exceptions from OptionParser.

  


    
Individual switch class.  Not important to the user.

Defined within Switch are several Switch-derived classes: NoArgument, RequiredArgument, etc.

  


    
Switch that takes no arguments.

  


    
Switch that can omit argument.

  


    
Switch that takes an argument, which does not begin with '-'.

  


    
Switch that takes an argument.

  


    
A pretty-printer for Ruby objects.

What PP Does¶ ↑

Standard output by p returns this:

#<PP:0x81fedf0 @genspace=#<Proc:0x81feda0>, @group_queue=#<PrettyPrint::GroupQueue:0x81fed3c @queue=[[#<PrettyPrint::Group:0x81fed78 @breakables=[], @depth=0, @break=false>], []]>, @buffer=[], @newline="\n", @group_stack=[#<PrettyPrint::Group:0x81fed78 @breakables=[], @depth=0, @break=false>], @buffer_width=0, @indent=0, @maxwidth=79, @output_width=2, @output=#<IO:0x8114ee4>>


Pretty-printed output returns this:

#<PP:0x81fedf0
 @buffer=[],
 @buffer_width=0,
 @genspace=#<Proc:0x81feda0>,
 @group_queue=
  #<PrettyPrint::GroupQueue:0x81fed3c
   @queue=
    [[#<PrettyPrint::Group:0x81fed78 @break=false, @breakables=[], @depth=0>],
     []]>,
 @group_stack=
  [#<PrettyPrint::Group:0x81fed78 @break=false, @breakables=[], @depth=0>],
 @indent=0,
 @maxwidth=79,
 @newline="\n",
 @output=#<IO:0x8114ee4>,
 @output_width=2>

Usage¶ ↑

pp(obj)             #=> obj
pp obj              #=> obj
pp(obj1, obj2, ...) #=> [obj1, obj2, ...]
pp()                #=> nil

Output obj(s) to $> in pretty printed format.

It returns obj(s).

Output Customization¶ ↑

To define a customized pretty printing function for your classes, redefine method #pretty_print(pp) in the class.

#pretty_print takes the pp argument, which is an instance of the PP class. The method uses text, breakable, nest, group and pp to print the object.

Pretty-Print JSON¶ ↑

To pretty-print JSON refer to JSON#pretty_generate.

Author¶ ↑

Tanaka Akira <akr@fsij.org>

  


    
PStore implements a file based persistence mechanism based on a Hash.  User code can store hierarchies of Ruby objects (values) into the data store file by name (keys).  An object hierarchy may be just a single object.  User code may later read values back from the data store or even update data, as needed.

The transactional behavior ensures that any changes succeed or fail together. This can be used to ensure that the data store is not left in a transitory state, where some values were updated but others were not.

Behind the scenes, Ruby objects are stored to the data store file with Marshal.  That carries the usual limitations.  Proc objects cannot be marshalled, for example.

Usage example:¶ ↑

require "pstore"

# a mock wiki object...
class WikiPage
  def initialize( page_name, author, contents )
    @page_name = page_name
    @revisions = Array.new

    add_revision(author, contents)
  end

  attr_reader :page_name

  def add_revision( author, contents )
    @revisions << { :created  => Time.now,
                    :author   => author,
                    :contents => contents }
  end

  def wiki_page_references
    [@page_name] + @revisions.last[:contents].scan(/\b(?:[A-Z]+[a-z]+){2,}/)
  end

  # ...
end

# create a new page...
home_page = WikiPage.new( "HomePage", "James Edward Gray II",
                          "A page about the JoysOfDocumentation..." )

# then we want to update page data and the index together, or not at all...
wiki = PStore.new("wiki_pages.pstore")
wiki.transaction do  # begin transaction; do all of this or none of it
  # store page...
  wiki[home_page.page_name] = home_page
  # ensure that an index has been created...
  wiki[:wiki_index] ||= Array.new
  # update wiki index...
  wiki[:wiki_index].push(*home_page.wiki_page_references)
end                   # commit changes to wiki data store file

### Some time later... ###

# read wiki data...
wiki.transaction(true) do  # begin read-only transaction, no changes allowed
  wiki.roots.each do |data_root_name|
    p data_root_name
    p wiki[data_root_name]
  end
end


Transaction modes¶ ↑

By default, file integrity is only ensured as long as the operating system (and the underlying hardware) doesn't raise any unexpected I/O errors. If an I/O error occurs while PStore is writing to its file, then the file will become corrupted.

You can prevent this by setting pstore.ultra_safe = true. However, this results in a minor performance loss, and only works on platforms that support atomic file renames. Please consult the documentation for ultra_safe for details.

Needless to say, if you're storing valuable data with PStore, then you should backup the PStore files from time to time.

  


    
The error type thrown by all PStore methods.

  


    
Thrown when PTY::check is called for a pid that represents a process that has exited.

  


    
Pathname represents the name of a file or directory on the filesystem, but not the file itself.

The pathname depends on the Operating System: Unix, Windows, etc. This library works with pathnames of local OS, however non-Unix pathnames are supported experimentally.

A Pathname can be relative or absolute.  It's not until you try to reference the file that it even matters whether the file exists or not.

Pathname is immutable.  It has no method for destructive update.

The goal of this class is to manipulate file path information in a neater way than standard Ruby provides.  The examples below demonstrate the difference.

All functionality from File, FileTest, and some from Dir and FileUtils is included, in an unsurprising way.  It is essentially a facade for all of these, and more.

Examples¶ ↑

Example 1: Using Pathname¶ ↑

require 'pathname'
pn = Pathname.new("/usr/bin/ruby")
size = pn.size              # 27662
isdir = pn.directory?       # false
dir  = pn.dirname           # Pathname:/usr/bin
base = pn.basename          # Pathname:ruby
dir, base = pn.split        # [Pathname:/usr/bin, Pathname:ruby]
data = pn.read
pn.open { |f| _ }
pn.each_line { |line| _ }


Example 2: Using standard Ruby¶ ↑

pn = "/usr/bin/ruby"
size = File.size(pn)        # 27662
isdir = File.directory?(pn) # false
dir  = File.dirname(pn)     # "/usr/bin"
base = File.basename(pn)    # "ruby"
dir, base = File.split(pn)  # ["/usr/bin", "ruby"]
data = File.read(pn)
File.open(pn) { |f| _ }
File.foreach(pn) { |line| _ }


Example 3: Special features¶ ↑

p1 = Pathname.new("/usr/lib")   # Pathname:/usr/lib
p2 = p1 + "ruby/1.8"            # Pathname:/usr/lib/ruby/1.8
p3 = p1.parent                  # Pathname:/usr
p4 = p2.relative_path_from(p3)  # Pathname:lib/ruby/1.8
pwd = Pathname.pwd              # Pathname:/home/gavin
pwd.absolute?                   # true
p5 = Pathname.new "."           # Pathname:.
p5 = p5 + "music/../articles"   # Pathname:music/../articles
p5.cleanpath                    # Pathname:articles
p5.realpath                     # Pathname:/home/gavin/articles
p5.children                     # [Pathname:/home/gavin/articles/linux, ...]


Breakdown of functionality¶ ↑

Core methods¶ ↑

These methods are effectively manipulating a String, because that's all a path is.  None of these access the file system except for mountpoint?, children, each_child, realdirpath and realpath.

+

join

parent

root?

absolute?

relative?

relative_path_from

each_filename

cleanpath

realpath

realdirpath

children

each_child

mountpoint?


File status predicate methods¶ ↑

These methods are a facade for FileTest:

blockdev?

chardev?

directory?

executable?

executable_real?

exist?

file?

grpowned?

owned?

pipe?

readable?

world_readable?

readable_real?

setgid?

setuid?

size

size?

socket?

sticky?

symlink?

writable?

world_writable?

writable_real?

zero?


File property and manipulation methods¶ ↑

These methods are a facade for File:

atime

birthtime

ctime

mtime

chmod(mode)

lchmod(mode)

chown(owner, group)

lchown(owner, group)

fnmatch(pattern, *args)

fnmatch?(pattern, *args)

ftype

make_link(old)

open(*args, &block)

readlink

rename(to)

stat

lstat

make_symlink(old)

truncate(length)

utime(atime, mtime)

basename(*args)

dirname

extname

expand_path(*args)

split


Directory methods¶ ↑

These methods are a facade for Dir:

Pathname.glob(*args)

Pathname.getwd / Pathname.pwd

rmdir

entries

each_entry(&block)

mkdir(*args)

opendir(*args)


IO¶ ↑

These methods are a facade for IO:

each_line(*args, &block)

read(*args)

binread(*args)

readlines(*args)

sysopen(*args)


Utilities¶ ↑

These methods are a mixture of Find, FileUtils, and others:

find(&block)

mkpath

rmtree

unlink / delete


Method documentation¶ ↑

As the above section shows, most of the methods in Pathname are facades.  The documentation for these methods generally just says, for instance, “See FileTest.writable?”, as you should be familiar with the original method anyway, and its documentation (e.g. through ri) will contain more information.  In some cases, a brief description will follow.

  


    
This class implements a pretty printing algorithm. It finds line breaks and nice indentations for grouped structure.

By default, the class assumes that primitive elements are strings and each byte in the strings have single column in width. But it can be used for other situations by giving suitable arguments for some methods:

newline object and space generation block for PrettyPrint.new

optional width argument for PrettyPrint#text

PrettyPrint#breakable


There are several candidate uses:

text formatting using proportional fonts

multibyte characters which has columns different to number of bytes

non-string formatting


Bugs¶ ↑

Box based formatting?

Other (better) model/algorithm?


Report any bugs at bugs.ruby-lang.org

References¶ ↑

Christian Lindig, Strictly Pretty, March 2000, www.st.cs.uni-sb.de/~lindig/papers/#pretty

Philip Wadler, A prettier printer, March 1998, homepages.inf.ed.ac.uk/wadler/topics/language-design.html#prettier

Author¶ ↑

Tanaka Akira <akr@fsij.org>

  


    
PrettyPrint::SingleLine is used by PrettyPrint.singleline_format

It is passed to be similar to a PrettyPrint object itself, by responding to:

text

breakable

nest

group

flush

first?


but instead, the output has no line breaks

  


    
The set of all prime numbers.

Example¶ ↑

Prime.each(100) do |prime|
  p prime  #=> 2, 3, 5, 7, 11, ...., 97
end


Prime is Enumerable:

Prime.first 5 # => [2, 3, 5, 7, 11]


Retrieving the instance¶ ↑

For convenience, each instance method of Prime.instance can be accessed as a class method of Prime.

e.g.

Prime.instance.prime?(2)  #=> true
Prime.prime?(2)           #=> true


Generators¶ ↑

A “generator” provides an implementation of enumerating pseudo-prime numbers and it remembers the position of enumeration and upper bound. Furthermore, it is an external iterator of prime enumeration which is compatible with an Enumerator.

Prime::PseudoPrimeGenerator is the base class for generators. There are few implementations of generator.
Prime::EratosthenesGenerator

Uses eratosthenes' sieve.
Prime::TrialDivisionGenerator

Uses the trial division method.
Prime::Generator23

Generates all positive integers which are not divisible by either 2 or 3. This sequence is very bad as a pseudo-prime sequence. But this is faster and uses much less memory than the other generators. So, it is suitable for factorizing an integer which is not large but has many prime factors. e.g. for Prime#prime? .


  


    
An implementation of PseudoPrimeGenerator.

Uses EratosthenesSieve.

  


    
Internal use. An implementation of Eratosthenes' sieve

  


    
Generates all integers which are greater than 2 and are not divisible by either 2 or 3.

This is a pseudo-prime generator, suitable on checking primality of an integer by brute force method.

  


    
An abstract class for enumerating pseudo-prime numbers.

Concrete subclasses should override succ, next, rewind.

  


    
Internal use. An implementation of prime table by trial division method.

  


    
An implementation of PseudoPrimeGenerator which uses a prime table generated by trial division.

  


    
A Proc object is an encapsulation of a block of code, which can be stored in a local variable, passed to a method or another Proc, and can be called. Proc is an essential concept in Ruby and a core of its functional programming features.

square = Proc.new {|x| x**2 }

square.call(3)  #=> 9
# shorthands:
square.(3)      #=> 9
square[3]       #=> 9


Proc objects are closures, meaning they remember and can use the entire context in which they were created.

def gen_times(factor)
  Proc.new {|n| n*factor } # remembers the value of factor at the moment of creation
end

times3 = gen_times(3)
times5 = gen_times(5)

times3.call(12)               #=> 36
times5.call(5)                #=> 25
times3.call(times5.call(4))   #=> 60


Creation¶ ↑

There are several methods to create a Proc

Use the Proc class constructor:

proc1 = Proc.new {|x| x**2 }


Use the Kernel#proc method as a shorthand of Proc.new:

proc2 = proc {|x| x**2 }


Receiving a block of code into proc argument (note the &):

def make_proc(&block)
  block
end

proc3 = make_proc {|x| x**2 }


Construct a proc with lambda semantics using the Kernel#lambda method (see below for explanations about lambdas):

lambda1 = lambda {|x| x**2 }


Use the Lambda literal syntax (also constructs a proc with lambda semantics):

lambda2 = ->(x) { x**2 }



Lambda and non-lambda semantics¶ ↑

Procs are coming in two flavors: lambda and non-lambda (regular procs). Differences are:

In lambdas, return means exit from this lambda;

In regular procs, return means exit from embracing method (and will throw LocalJumpError if invoked outside the method);

In lambdas, arguments are treated in the same way as in methods: strict, with ArgumentError for mismatching argument number, and no additional argument processing;

Regular procs accept arguments more generously: missing arguments are filled with nil, single Array arguments are deconstructed if the proc has multiple arguments, and there is no error raised on extra arguments.


Examples:

p = proc {|x, y| "x=#{x}, y=#{y}" }
p.call(1, 2)      #=> "x=1, y=2"
p.call([1, 2])    #=> "x=1, y=2", array deconstructed
p.call(1, 2, 8)   #=> "x=1, y=2", extra argument discarded
p.call(1)         #=> "x=1, y=", nil substituted instead of error

l = lambda {|x, y| "x=#{x}, y=#{y}" }
l.call(1, 2)      #=> "x=1, y=2"
l.call([1, 2])    # ArgumentError: wrong number of arguments (given 1, expected 2)
l.call(1, 2, 8)   # ArgumentError: wrong number of arguments (given 3, expected 2)
l.call(1)         # ArgumentError: wrong number of arguments (given 1, expected 2)

def test_return
  -> { return 3 }.call      # just returns from lambda into method body
  proc { return 4 }.call    # returns from method
  return 5
end

test_return # => 4, return from proc


Lambdas are useful as self-sufficient functions, in particular useful as arguments to higher-order functions, behaving exactly like Ruby methods.

Procs are useful for implementing iterators:

def test
  [[1, 2], [3, 4], [5, 6]].map {|a, b| return a if a + b > 10 }
                            #  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
end


Inside map, the block of code is treated as a regular (non-lambda) proc, which means that the internal arrays will be deconstructed to pairs of arguments, and return will exit from the method test. That would not be possible with a stricter lambda.

You can tell a lambda from a regular proc by using the lambda? instance method.

Lambda semantics is typically preserved during the proc lifetime, including &-deconstruction to a block of code:

p = proc {|x, y| x }
l = lambda {|x, y| x }
[[1, 2], [3, 4]].map(&p) #=> [1, 2]
[[1, 2], [3, 4]].map(&l) # ArgumentError: wrong number of arguments (given 1, expected 2)


The only exception is dynamic method definition: even if defined by passing a non-lambda proc, methods still have normal semantics of argument checking.

class C
  define_method(:e, &proc {})
end
C.new.e(1,2)       #=> ArgumentError
C.new.method(:e).to_proc.lambda?   #=> true


This exception ensures that methods never have unusual argument passing conventions, and makes it easy to have wrappers defining methods that behave as usual.

class C
  def self.def2(name, &body)
    define_method(name, &body)
  end

  def2(:f) {}
end
C.new.f(1,2)       #=> ArgumentError


The wrapper def2 receives body as a non-lambda proc, yet defines a method which has normal semantics.

Conversion of other objects to procs¶ ↑

Any object that implements the to_proc method can be converted into a proc by the & operator, and therefore con be consumed by iterators.

class Greater
  def initialize(greating)
    @greating = greating
  end

  def to_proc
    proc {|name| "#{@greating}, #{name}!" }
  end
end

hi = Greater.new("Hi")
hey = Greater.new("Hey")
["Bob", "Jane"].map(&hi)    #=> ["Hi, Bob!", "Hi, Jane!"]
["Bob", "Jane"].map(&hey)   #=> ["Hey, Bob!", "Hey, Jane!"]


Of the Ruby core classes, this method is implemented by Symbol, Method, and Hash.

:to_s.to_proc.call(1)           #=> "1"
[1, 2].map(&:to_s)              #=> ["1", "2"]

method(:puts).to_proc.call(1)   # prints 1
[1, 2].each(&method(:puts))     # prints 1, 2

{test: 1}.to_proc.call(:test)       #=> 1
%i[test many keys].map(&{test: 1})  #=> [1, nil, nil]


  


    
Process::Status encapsulates the information on the status of a running or terminated system process. The built-in variable $? is either nil or a Process::Status object.

fork { exit 99 }   #=> 26557
Process.wait       #=> 26557
$?.class           #=> Process::Status
$?.to_i            #=> 25344
$? >> 8            #=> 99
$?.stopped?        #=> false
$?.exited?         #=> true
$?.exitstatus      #=> 99


Posix systems record information on processes using a 16-bit integer.  The lower bits record the process status (stopped, exited, signaled) and the upper bits possibly contain additional information (for example the program's return code in the case of exited processes). Pre Ruby 1.8, these bits were exposed directly to the Ruby program. Ruby now encapsulates these in a Process::Status object. To maximize compatibility, however, these objects retain a bit-oriented interface. In the descriptions that follow, when we talk about the integer value of stat, we're referring to this 16 bit value.

  


    
If an object defines encode_with, then an instance of Psych::Coder will be passed to the method when the object is being serialized.  The Coder automatically assumes a Psych::Nodes::Mapping is being emitted.  Other objects like Sequence and Scalar may be emitted if seq= or scalar= are called, respectively.

  


    
Psych::Handler is an abstract base class that defines the events used when dealing with Psych::Parser.  Clients who want to use Psych::Parser should implement a class that inherits from Psych::Handler and define events that they can handle.

Psych::Handler defines all events that Psych::Parser can possibly send to event handlers.

See Psych::Parser for more details

  


    
Configuration options for dumping YAML.

  


    
This handler will capture an event and record the event.  Recorder events are available vial Psych::Handlers::Recorder#events.

For example:

recorder = Psych::Handlers::Recorder.new
parser = Psych::Parser.new recorder
parser.parse '--- foo'

recorder.events # => [list of events]

# Replay the events

emitter = Psych::Emitter.new $stdout
recorder.events.each do |m, args|
  emitter.send m, *args
end


  


    
Psych::JSON::TreeBuilder is an event based AST builder.  Events are sent to an instance of Psych::JSON::TreeBuilder and a JSON AST is constructed.

  


    
This class represents a YAML Alias. It points to an anchor.

A Psych::Nodes::Alias is a terminal node and may have no children.

  


    
This represents a YAML Document.  This node must be a child of Psych::Nodes::Stream.  A Psych::Nodes::Document must have one child, and that child may be one of the following:

Psych::Nodes::Sequence

Psych::Nodes::Mapping

Psych::Nodes::Scalar


  


    
This class represents a YAML Mapping.

A Psych::Nodes::Mapping node may have 0 or more children, but must have an even number of children.  Here are the valid children a Psych::Nodes::Mapping node may have:

Psych::Nodes::Sequence

Psych::Nodes::Mapping

Psych::Nodes::Scalar

Psych::Nodes::Alias


  


    
The base class for any Node in a YAML parse tree.  This class should never be instantiated.

  


    
This class represents a YAML Scalar.

This node type is a terminal node and should not have any children.

  


    
This class represents a YAML sequence.

A YAML sequence is basically a list, and looks like this:

%YAML 1.1
---
- I am
- a Sequence

A YAML sequence may have an anchor like this:

%YAML 1.1
---
&A [
  "This sequence",
  "has an anchor"
]

A YAML sequence may also have a tag like this:

%YAML 1.1
---
!!seq [
  "This sequence",
  "has a tag"
]

This class represents a sequence in a YAML document.  A Psych::Nodes::Sequence node may have 0 or more children.  Valid children for this node are:

Psych::Nodes::Sequence

Psych::Nodes::Mapping

Psych::Nodes::Scalar

Psych::Nodes::Alias


  


    
Represents a YAML stream.  This is the root node for any YAML parse tree.  This node must have one or more child nodes.  The only valid child node for a Psych::Nodes::Stream node is Psych::Nodes::Document.

  


    
YAML event parser class.  This class parses a YAML document and calls events on the handler that is passed to the constructor.  The events can be used for things such as constructing a YAML AST or deserializing YAML documents.  It can even be fed back to Psych::Emitter to emit the same document that was parsed.

See Psych::Handler for documentation on the events that Psych::Parser emits.

Here is an example that prints out ever scalar found in a YAML document:

# Handler for detecting scalar values
class ScalarHandler < Psych::Handler
  def scalar value, anchor, tag, plain, quoted, style
    puts value
  end
end

parser = Psych::Parser.new(ScalarHandler.new)
parser.parse(yaml_document)


Here is an example that feeds the parser back in to Psych::Emitter.  The YAML document is read from STDIN and written back out to STDERR:

parser = Psych::Parser.new(Psych::Emitter.new($stderr))
parser.parse($stdin)


Psych uses Psych::Parser in combination with Psych::TreeBuilder to construct an AST of the parsed YAML document.

  


    
Scan scalars for built in types

  


    
Psych::Stream is a streaming YAML emitter.  It will not buffer your YAML, but send it straight to an IO.

Here is an example use:

stream = Psych::Stream.new($stdout)
stream.start
stream.push({:foo => 'bar'})
stream.finish


YAML will be immediately emitted to $stdout with no buffering.

Psych::Stream#start will take a block and ensure that Psych::Stream#finish is called, so you can do this form:

stream = Psych::Stream.new($stdout)
stream.start do |em|
  em.push(:foo => 'bar')
end


  


    
This class works in conjunction with Psych::Parser to build an in-memory parse tree that represents a YAML document.

Example¶ ↑

parser = Psych::Parser.new Psych::TreeBuilder.new
parser.parse('--- foo')
tree = parser.handler.root


See Psych::Handler for documentation on the event methods used in this class.

  


    
This class walks a YAML AST, converting each node to Ruby

  


    
YAMLTree builds a YAML ast given a Ruby object.  For example:

builder = Psych::Visitors::YAMLTree.new
builder << { :foo => 'bar' }
builder.tree # => #<Psych::Nodes::Stream .. }


  


    
The Queue class implements multi-producer, multi-consumer queues. It is especially useful in threaded programming when information must be exchanged safely between multiple threads. The Queue class implements all the required locking semantics.

The class implements FIFO type of queue. In a FIFO queue, the first tasks added are the first retrieved.

Example:

queue = Queue.new

producer = Thread.new do
  5.times do |i|
     sleep rand(i) # simulate expense
     queue << i
     puts "#{i} produced"
  end
end

consumer = Thread.new do
  5.times do |i|
     value = queue.pop
     sleep rand(i/2) # simulate expense
     puts "consumed #{value}"
  end
end

consumer.join


  


    
RDoc produces documentation for Ruby source files by parsing the source and extracting the definition for classes, modules, methods, includes and requires.  It associates these with optional documentation contained in an immediately preceding comment block then renders the result using an output formatter.

For a simple introduction to writing or generating documentation using RDoc see the README.

Roadmap¶ ↑

If you think you found a bug in RDoc see Bugs at CONTRIBUTING

If you want to use RDoc to create documentation for your Ruby source files, see RDoc::Markup and refer to rdoc --help for command line usage.

If you want to set the default markup format see Supported Formats at RDoc::Markup

If you want to store rdoc configuration in your gem (such as the default markup format) see Saved Options at RDoc::Options

If you want to write documentation for Ruby files see RDoc::Parser::Ruby

If you want to write documentation for extensions written in C see RDoc::Parser::C

If you want to generate documentation using rake see RDoc::Task.

If you want to drive RDoc programmatically, see RDoc::RDoc.

If you want to use the library to format text blocks into HTML or other formats, look at RDoc::Markup.

If you want to make an RDoc plugin such as a generator or directive handler see RDoc::RDoc.

If you want to write your own output generator see RDoc::Generator.

If you want an overview of how RDoc works see Bugs at CONTRIBUTING

Credits¶ ↑

RDoc is currently being maintained by Eric Hodel <drbrain@segment7.net>.

Dave Thomas <dave@pragmaticprogrammer.com> is the original author of RDoc.

The Ruby parser in rdoc/parse.rb is based heavily on the outstanding work of Keiju ISHITSUKA of Nippon Rational Inc, who produced the Ruby parser for irb and the rtags package.


  


    
Represent an alias, which is an old_name/new_name pair associated with a particular context

  


    
An anonymous class like:

c = Class.new do end


AnonClass is currently not used.

  


    
AnyMethod is the base class for objects representing methods

  


    
An attribute created by #attr, #attr_reader, #attr_writer or #attr_accessor

  


    
ClassModule is the base class for objects representing either a class or a module.

  


    
Base class for the RDoc code tree.

We contain the common stuff for contexts (which are containers) and other elements (methods, attributes and so on)

Here's the tree of the CodeObject subclasses:

RDoc::Context

RDoc::TopLevel

RDoc::ClassModule

RDoc::AnonClass (never used so far)

RDoc::NormalClass

RDoc::NormalModule

RDoc::SingleClass



RDoc::MethodAttr

RDoc::Attr

RDoc::AnyMethod

RDoc::GhostMethod

RDoc::MetaMethod



RDoc::Alias

RDoc::Constant

RDoc::Mixin

RDoc::Require

RDoc::Include



  


    
A comment holds the text comment for a RDoc::CodeObject and provides a unified way of cleaning it up and parsing it into an RDoc::Markup::Document.

Each comment may have a different markup format set by format=.  By default 'rdoc' is used.  The :markup: directive tells RDoc which format to use.

See Other directives at RDoc::Markup for instructions on adding an alternate format.

  


    
A constant

  


    
A Context is something that can hold modules, classes, methods, attributes, aliases, requires, and includes. Classes, modules, and files are all Contexts.

  


    
RDoc::CrossReference is a reusable way to create cross references for names.

  


    
A subclass of ERB that writes directly to an IO.  Credit to Aaron Patterson and Masatoshi SEKI.

To use:

erbio = RDoc::ERBIO.new '<%= "hello world" %>', nil, nil

File.open 'hello.txt', 'w' do |io|
  erbio.result binding
end


Note that binding must enclose the io you wish to output on.

  


    
Allows an ERB template to be rendered in the context (binding) of an existing ERB template evaluation.

  


    
Exception thrown by any rdoc error.

  


    
A Module extension to a class with #extend

RDoc::Extend.new 'Enumerable', 'comment ...'


  


    
GhostMethod represents a method referenced only by a comment

  


    
A Module included in a class with #include

RDoc::Include.new 'Enumerable', 'comment ...'


  


    
RDoc::Markdown as described by the markdown syntax.

To choose Markdown as your only default format see Saved Options at RDoc::Options for instructions on setting up a .doc_options file to store your project default.

Usage¶ ↑

Here is a brief example of using this parse to read a markdown file by hand.

data = File.read("README.md")
formatter = RDoc::Markup::ToHtml.new(RDoc::Options.new, nil)
html = RDoc::Markdown.parse(data).accept(formatter)

# do something with html


Extensions¶ ↑

The following markdown extensions are supported by the parser, but not all are used in RDoc output by default.

RDoc¶ ↑

The RDoc Markdown parser has the following built-in behaviors that cannot be disabled.

Underscores embedded in words are never interpreted as emphasis. (While the markdown dingus emphasizes in-word underscores, neither the Markdown syntax nor MarkdownTest mention this behavior.)

For HTML output, RDoc always auto-links bare URLs.

Break on Newline¶ ↑

The break_on_newline extension converts all newlines into hard line breaks as in Github Flavored Markdown. This extension is disabled by default.

CSS¶ ↑

The css extension enables CSS blocks to be included in the output, but they are not used for any built-in RDoc output format. This extension is disabled by default.

Example:

<style type="text/css">
h1 { font-size: 3em }
</style>

Definition Lists¶ ↑

The definition_lists extension allows definition lists using the PHP Markdown Extra syntax, but only one label and definition are supported at this time. This extension is enabled by default.

Example:

cat
:   A small furry mammal
that seems to sleep a lot

ant
:   A little insect that is known
to enjoy picnics

Produces:
cat

A small furry mammal that seems to sleep a lot
ant

A little insect that is known to enjoy picnics


Strike¶ ↑

Example:

This is ~~striked~~.

Produces:

This is ~striked~.

Github¶ ↑

The github extension enables a partial set of Github Flavored Markdown. This extension is enabled by default.

Supported github extensions include:

Fenced code blocks¶ ↑

Use ``` around a block of code instead of indenting it four spaces.

Syntax highlighting¶ ↑

Use ``` ruby as the start of a code fence to add syntax highlighting. (Currently only ruby syntax is supported).

HTML¶ ↑

Enables raw HTML to be included in the output. This extension is enabled by default.

Example:

<table>
...
</table>

Notes¶ ↑

The notes extension enables footnote support. This extension is enabled by default.

Example:

Here is some text[^1] including an inline footnote ^[for short footnotes]

...

[^1]: With the footnote text down at the bottom

Produces:

Here is some text1 including an inline footnote 2

Limitations¶ ↑

Link titles are not used

Footnotes are collapsed into a single paragraph


Author¶ ↑

This markdown parser is a port to kpeg from peg-markdown by John MacFarlane.

It is used under the MIT license:

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the “Software”), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

The port to kpeg was performed by Eric Hodel and Evan Phoenix


1 With the footnote text down at the bottom

2 for short footnotes

  


    
RDoc::Markup parses plain text documents and attempts to decompose them into their constituent parts.  Some of these parts are high-level: paragraphs, chunks of verbatim text, list entries and the like.  Other parts happen at the character level: a piece of bold text, a word in code font.  This markup is similar in spirit to that used on WikiWiki webs, where folks create web pages using a simple set of formatting rules.

RDoc::Markup and other markup formats do no output formatting, this is handled by the RDoc::Markup::Formatter subclasses.

Supported Formats¶ ↑

Besides the RDoc::Markup format, the following formats are built in to RDoc:
markdown

The markdown format as described by daringfireball.net/projects/markdown/.  See RDoc::Markdown for details on the parser and supported extensions.
rd

The rdtool format.  See RDoc::RD for details on the parser and format.
tomdoc

The TomDoc format as described by tomdoc.org/.  See RDoc::TomDoc for details on the parser and supported extensions.


You can choose a markup format using the following methods:
per project

If you build your documentation with rake use RDoc::Task#markup.

If you build your documentation by hand run:

rdoc --markup your_favorite_format --write-options

and commit .rdoc_options and ship it with your packaged gem.
per file

At the top of the file use the :markup: directive to set the default format for the rest of the file.
per comment

Use the :markup: directive at the top of a comment you want to write in a different format.


RDoc::Markup¶ ↑

RDoc::Markup is extensible at runtime: you can add new markup elements to be recognized in the documents that RDoc::Markup parses.

RDoc::Markup is intended to be the basis for a family of tools which share the common requirement that simple, plain-text should be rendered in a variety of different output formats and media.  It is envisaged that RDoc::Markup could be the basis for formatting RDoc style comment blocks, Wiki entries, and online FAQs.

Synopsis¶ ↑

This code converts input_string to HTML.  The conversion takes place in the convert method, so you can use the same RDoc::Markup converter to convert multiple input strings.

require 'rdoc'

h = RDoc::Markup::ToHtml.new(RDoc::Options.new)

puts h.convert(input_string)


You can extend the RDoc::Markup parser to recognize new markup sequences, and to add regexp handling. Here we make WikiWords significant to the parser, and also make the sequences {word} and <no>text…</no> signify strike-through text.  We then subclass the HTML output class to deal with these:

require 'rdoc'

class WikiHtml < RDoc::Markup::ToHtml
  def handle_regexp_WIKIWORD(target)
    "<font color=red>" + target.text + "</font>"
  end
end

markup = RDoc::Markup.new
markup.add_word_pair("{", "}", :STRIKE)
markup.add_html("no", :STRIKE)

markup.add_regexp_handling(/\b([A-Z][a-z]+[A-Z]\w+)/, :WIKIWORD)

wh = WikiHtml.new RDoc::Options.new, markup
wh.add_tag(:STRIKE, "<strike>", "</strike>")

puts "<body>#{wh.convert ARGF.read}</body>"


Encoding¶ ↑

Where Encoding support is available, RDoc will automatically convert all documents to the same output encoding.  The output encoding can be set via RDoc::Options#encoding and defaults to Encoding.default_external.

RDoc Markup Reference¶ ↑

Block Markup¶ ↑

Paragraphs and Verbatim¶ ↑

The markup engine looks for a document's natural left margin.  This is used as the initial margin for the document.

Consecutive lines starting at this margin are considered to be a paragraph. Empty lines separate paragraphs.

Any line that starts to the right of the current margin is treated as verbatim text.  This is useful for code listings:

3.times { puts "Ruby" }


In verbatim text, two or more blank lines are collapsed into one, and trailing blank lines are removed:

This is the first line

This is the second non-blank line,
after 2 blank lines in the source markup.

There were two trailing blank lines right above this paragraph, that have been removed. In addition, the verbatim text has been shifted left, so the amount of indentation of verbatim text is unimportant.

For HTML output RDoc makes a small effort to determine if a verbatim section contains Ruby source code.  If so, the verbatim block will be marked up as HTML.  Triggers include “def”, “class”, “module”, “require”, the “hash rocket”# (=>) or a block call with a parameter.

Headers¶ ↑

A line starting with an equal sign (=) is treated as a heading.  Level one headings have one equals sign, level two headings have two, and so on until level six, which is the maximum (seven hyphens or more result in a level six heading).

For example, the above header was obtained with:

=== Headers

In HTML output headers have an id matching their name.  The above example's HTML is:

<h3 id="label-Headers">Headers</h3>

If a heading is inside a method body the id will be prefixed with the method's id.  If the above header where in the documentation for a method such as:

##
# This method does fun things
#
# = Example
#
#   Example of fun things goes here ...

def do_fun_things
end


The header's id would be:

<h1 id="method-i-do_fun_things-label-Example">Example</h1>

The label can be linked-to using SomeClass@Headers.  See Links for further details.

Rules¶ ↑

A line starting with three or more hyphens (at the current indent) generates a horizontal rule.

---

produces:


Simple Lists¶ ↑

If a paragraph starts with a “*”, “-”, “<digit>.” or “<letter>.”, then it is taken to be the start of a list.  The margin is increased to be the first non-space following the list start flag.  Subsequent lines should be indented to this new margin until the list ends.  For example:

* this is a list with three paragraphs in
  the first item.  This is the first paragraph.

  And this is the second paragraph.

  1. This is an indented, numbered list.
  2. This is the second item in that list

  This is the third conventional paragraph in the
  first list item.

* This is the second item in the original list

produces:

this is a list with three paragraphs in the first item.  This is the first paragraph.

And this is the second paragraph.

This is an indented, numbered list.

This is the second item in that list


This is the third conventional paragraph in the first list item.

This is the second item in the original list


Labeled Lists¶ ↑

You can also construct labeled lists, sometimes called description or definition lists.  Do this by putting the label in square brackets and indenting the list body:

[cat]  a small furry mammal
       that seems to sleep a lot

[ant]  a little insect that is known
       to enjoy picnics

produces:
cat

a small furry mammal that seems to sleep a lot
ant

a little insect that is known to enjoy picnics


If you want the list bodies to line up to the left of the labels, use two colons:

cat::  a small furry mammal
       that seems to sleep a lot

ant::  a little insect that is known
       to enjoy picnics


produces:
cat

a small furry mammal that seems to sleep a lot
ant

a little insect that is known to enjoy picnics


Notice that blank lines right after the label are ignored in labeled lists:

[one]

    definition 1

[two]

    definition 2


produces the same output as

[one]  definition 1
[two]  definition 2

Lists and Verbatim¶ ↑

If you want to introduce a verbatim section right after a list, it has to be less indented than the list item bodies, but more indented than the list label, letter, digit or bullet. For instance:

*   point 1

*   point 2, first paragraph

    point 2, second paragraph
      verbatim text inside point 2
    point 2, third paragraph
  verbatim text outside of the list (the list is therefore closed)
regular paragraph after the list

produces:

point 1

point 2, first paragraph

point 2, second paragraph

verbatim text inside point 2


point 2, third paragraph


verbatim text outside of the list (the list is therefore closed)


regular paragraph after the list

Text Markup¶ ↑

Bold, Italic, Typewriter Text¶ ↑

You can use markup within text (except verbatim) to change the appearance of parts of that text.  Out of the box, RDoc::Markup supports word-based and general markup.

Word-based markup uses flag characters around individual words:
*word*

displays word in a bold font
_word_

displays word in an emphasized font
+word+

displays word in a code font


General markup affects text between a start delimiter and an end delimiter.  Not surprisingly, these delimiters look like HTML markup.
<b>text</b>

displays text in a bold font
<em>text</em>

displays text in an emphasized font (alternate tag: <i>)
<tt>text</tt>

displays text in a code font (alternate tag: <code>)


Unlike conventional Wiki markup, general markup can cross line boundaries.  You can turn off the interpretation of markup by preceding the first character with a backslash (see Escaping Text Markup, below).

Links¶ ↑

Links to starting with http:, https:, mailto:, ftp: or www. are recognized.  An HTTP url that references an external image is converted into an inline image element.

Classes and methods will be automatically linked to their definition.  For example, RDoc::Markup will link to this documentation.  By default methods will only be automatically linked if they contain an _ (all methods can be automatically linked through the --hyperlink-all command line option).

Single-word methods can be linked by using the # character for instance methods or :: for class methods.  For example, #convert links to convert.  A class or method may be combined like RDoc::Markup#convert.

A heading inside the documentation can be linked by following the class or method by an @ then the heading name. RDoc::Markup@Links will link to this section like this: Links at RDoc::Markup.  Spaces in headings with multiple words must be escaped with + like RDoc::Markup@Escaping+Text+Markup. Punctuation and other special characters must be escaped like CGI.escape.

The @ can also be used to link to sections.  If a section and a heading share the same name the section is preferred for the link.

Links can also be of the form label[url], in which case label is used in the displayed text, and url is used as the target.  If label contains multiple words, put it in braces: {multi word label}[url]. The url may be an http:-type link or a cross-reference to a class, module or method with a label.

Links with the rdoc-image: scheme will create an image tag for HTML output.  Only fully-qualified URLs are supported.

Links with the rdoc-ref: scheme will link to the referenced class, module, method, file, etc.  If the referenced item is does not exist no link will be generated and rdoc-ref: will be removed from the resulting text.

Links starting with rdoc-label:label_name will link to the label_name.  You can create a label for the current link (for bidirectional links) by supplying a name for the current link like rdoc-label:label-other:label-mine.

Links starting with link: refer to local files whose path is relative to the --op directory.  Use rdoc-ref: instead of link: to link to files generated by RDoc as the link target may be different across RDoc generators.

Example links:

https://github.com/ruby/rdoc
mailto:user@example.com
{RDoc Documentation}[http://rdoc.rubyforge.org]
{RDoc Markup}[rdoc-ref:RDoc::Markup]

Escaping Text Markup¶ ↑

Text markup can be escaped with a backslash, as in <tt>, which was obtained with \<tt>.  Except in verbatim sections and between <tt> tags, to produce a backslash you have to double it unless it is followed by a space, tab or newline. Otherwise, the HTML formatter will discard it, as it is used to escape potential links:

* The \ must be doubled if not followed by white space: \\.
* But not in \<tt> tags: in a Regexp, <tt>\S</tt> matches non-space.
* This is a link to {ruby-lang}[www.ruby-lang.org].
* This is not a link, however: \{ruby-lang.org}[www.ruby-lang.org].
* This will not be linked to \RDoc::RDoc#document

generates:

The \ must be doubled if not followed by white space: \.

But not in <tt> tags: in a Regexp, \S matches non-space.

This is a link to ruby-lang

This is not a link, however: {ruby-lang.org}[www.ruby-lang.org]

This will not be linked to RDoc::RDoc#document


Inside <tt> tags, more precisely, leading backslashes are removed only if followed by a markup character (<*_+), a backslash, or a known link reference (a known class or method). So in the example above, the backslash of \S would be removed if there was a class or module named S in the current context.

This behavior is inherited from RDoc version 1, and has been kept for compatibility with existing RDoc documentation.

Conversion of characters¶ ↑

HTML will convert two/three dashes to an em-dash. Other common characters are converted as well:

em-dash::  -- or ---
ellipsis:: ...

single quotes:: 'text' or `text'
double quotes:: "text" or ``text''

copyright:: (c)
registered trademark:: (r)

produces:
em-dash

– or —
ellipsis

…
single quotes

'text' or `text'
double quotes

“text” or “text''
copyright

©
registered trademark

®


Documenting Source Code¶ ↑

Comment blocks can be written fairly naturally, either using # on successive lines of the comment, or by including the comment in a =begin/=end block.  If you use the latter form, the =begin line must be flagged with an rdoc tag:

=begin rdoc
Documentation to be processed by RDoc.

...
=end


RDoc stops processing comments if it finds a comment line starting with -- right after the # character (otherwise, it will be treated as a rule if it has three dashes or more). This can be used to separate external from internal comments, or to stop a comment being associated with a method, class, or module. Commenting can be turned back on with a line that starts with ++.

##
# Extract the age and calculate the date-of-birth.
#--
# FIXME: fails if the birthday falls on February 29th
#++
# The DOB is returned as a Time object.

def get_dob(person)
  # ...
end


Names of classes, files, and any method names containing an underscore or preceded by a hash character are automatically linked from comment text to their description. This linking works inside the current class or module, and with ancestor methods (in included modules or in the superclass).

Method parameter lists are extracted and displayed with the method description.  If a method calls yield, then the parameters passed to yield will also be displayed:

def fred
  ...
  yield line, address

This will get documented as:

fred() { |line, address| ... }

You can override this using a comment containing ':yields: …' immediately after the method definition

def fred # :yields: index, position
  # ...

  yield line, address

which will get documented as

fred() { |index, position| ... }

:yields: is an example of a documentation directive.  These appear immediately after the start of the document element they are modifying.

RDoc automatically cross-references words with underscores or camel-case. To suppress cross-references, prefix the word with a \ character.  To include special characters like “\n”, you'll need to use two \ characters in normal text, but only one in <tt> text:

"\\n" or "<tt>\n</tt>"


produces:

“\n” or “\n”

Directives¶ ↑

Directives are keywords surrounded by “:” characters.

Controlling what is documented¶ ↑
:nodoc: / :nodoc: all

This directive prevents documentation for the element from being generated.  For classes and modules, methods, aliases, constants, and attributes directly within the affected class or module also will be omitted.  By default, though, modules and classes within that class or module will be documented.  This is turned off by adding the all modifier.

module MyModule # :nodoc:
  class Input
  end
end

module OtherModule # :nodoc: all
  class Output
  end
end


In the above code, only class MyModule::Input will be documented.

The :nodoc: directive, like :enddoc:, :stopdoc: and :startdoc: presented below, is local to the current file: if you do not want to document a module that appears in several files, specify :nodoc: on each appearance, at least once per file.
:stopdoc: / :startdoc:

Stop and start adding new documentation elements to the current container. For example, if a class has a number of constants that you don't want to document, put a :stopdoc: before the first, and a :startdoc: after the last.  If you don't specify a :startdoc: by the end of the container, disables documentation for the rest of the current file.
:doc:

Forces a method or attribute to be documented even if it wouldn't be otherwise.  Useful if, for example, you want to include documentation of a particular private method.
:enddoc:

Document nothing further at the current level: directives :startdoc: and :doc: that appear after this will not be honored for the current container (file, class or module), in the current file.
:notnew: / :not_new: / :not-new: 

Only applicable to the initialize instance method.  Normally RDoc assumes that the documentation and parameters for initialize are actually for the new method, and so fakes out a new for the class. The :notnew: directive stops this.  Remember that initialize is private, so you won't see the documentation unless you use the -a command line option.


Method arguments¶ ↑
:arg: or :args: parameters

Overrides the default argument handling with exactly these parameters.

##
#  :args: a, b

def some_method(*a)
end

:yield: or :yields: parameters

Overrides the default yield discovery with these parameters.

##
# :yields: key, value

def each_thing &block
  @things.each(&block)
end

:call-seq:

Lines up to the next blank line or lines with a common prefix in the comment are treated as the method's calling sequence, overriding the default parsing of method parameters and yield arguments.

Multiple lines may be used.

# :call-seq:
#   ARGF.readlines(sep=$/)     -> array
#   ARGF.readlines(limit)      -> array
#   ARGF.readlines(sep, limit) -> array
#
#   ARGF.to_a(sep=$/)     -> array
#   ARGF.to_a(limit)      -> array
#   ARGF.to_a(sep, limit) -> array
#
# The remaining lines are documentation ...



Sections¶ ↑

Sections allow you to group methods in a class into sensible containers.  If you use the sections 'Public', 'Internal' and 'Deprecated' (the three allowed method statuses from TomDoc) the sections will be displayed in that order placing the most useful methods at the top.  Otherwise, sections will be displayed in alphabetical order.
:category: section

Adds this item to the named section overriding the current section.  Use this to group methods by section in RDoc output while maintaining a sensible ordering (like alphabetical).

# :category: Utility Methods
#
# CGI escapes +text+

def convert_string text
  CGI.escapeHTML text
end


An empty category will place the item in the default category:

# :category:
#
# This method is in the default category

def some_method
  # ...
end


Unlike the :section: directive, :category: is not sticky.  The category only applies to the item immediately following the comment.

Use the :section: directive to provide introductory text for a section of documentation.
:section: title

Provides section introductory text in RDoc output.  The title following :section: is used as the section name and the remainder of the comment containing the section is used as introductory text.  A section's comment block must be separated from following comment blocks.  Use an empty title to switch to the default section.

The :section: directive is sticky, so subsequent methods, aliases, attributes, and classes will be contained in this section until the section is changed.  The :category: directive will override the :section: directive.

A :section: comment block may have one or more lines before the :section: directive.  These will be removed, and any identical lines at the end of the block are also removed.  This allows you to add visual cues to the section.

Example:

# ----------------------------------------
# :section: My Section
# This is the section that I wrote.
# See it glisten in the noon-day sun.
# ----------------------------------------

##
# Comment for some_method

def some_method
  # ...
end



Other directives¶ ↑
:markup: type

Overrides the default markup type for this comment with the specified markup type.  For Ruby files, if the first comment contains this directive it is applied automatically to all comments in the file.

Unless you are converting between markup formats you should use a .rdoc_options file to specify the default documentation format for your entire project.  See Saved Options at RDoc::Options for instructions.

At the top of a file the :markup: directive applies to the entire file:

# coding: UTF-8
# :markup: TomDoc

# TomDoc comment here ...

class MyClass
  # ...

For just one comment:

  # ...
end

# :markup: RDoc
#
# This is a comment in RDoc markup format ...

def some_method
  # ...

See CONTRIBUTING at Markup for instructions on adding a new markup format.
:include: filename

Include the contents of the named file at this point. This directive must appear alone on one line, possibly preceded by spaces. In this position, it can be escaped with a \ in front of the first colon.

The file will be searched for in the directories listed by the --include option, or in the current directory by default.  The contents of the file will be shifted to have the same indentation as the ':' at the start of the :include: directive.
:title: text

Sets the title for the document.  Equivalent to the --title command line parameter.  (The command line parameter overrides any :title: directive in the source).
:main: name

Equivalent to the --main command line parameter.


  


    
MetaMethod represents a meta-programmed method

  


    
Abstract class representing either a method or an attribute.

  


    
A Mixin adds features from a module into another context.  RDoc::Include and RDoc::Extend are both mixins.

  


    
A normal class, neither singleton nor anonymous

  


    
A normal module, like NormalClass

  


    
RDoc::Options handles the parsing and storage of options

Saved Options¶ ↑

You can save some options like the markup format in the .rdoc_options file in your gem.  The easiest way to do this is:

rdoc --markup tomdoc --write-options

Which will automatically create the file and fill it with the options you specified.

The following options will not be saved since they interfere with the user's preferences or with the normal operation of RDoc:

--coverage-report

--dry-run

--encoding

--force-update

--format

--pipe

--quiet

--template

--verbose


Custom Options¶ ↑

Generators can hook into RDoc::Options to add generator-specific command line options.

When --format is encountered in ARGV, RDoc calls ::setup_options on the generator class to add extra options to the option parser.  Options for custom generators must occur after --format.  rdoc --help will list options for all installed generators.

Example:

class RDoc::Generator::Spellcheck
  RDoc::RDoc.add_generator self

  def self.setup_options rdoc_options
    op = rdoc_options.option_parser

    op.on('--spell-dictionary DICTIONARY',
          RDoc::Options::Path) do |dictionary|
      rdoc_options.spell_dictionary = dictionary
    end
  end
end


Of course, RDoc::Options does not respond to spell_dictionary by default so you will need to add it:

class RDoc::Options

  ##
  # The spell dictionary used by the spell-checking plugin.

  attr_accessor :spell_dictionary

end


Option Validators¶ ↑

OptionParser validators will validate and cast user input values.  In addition to the validators that ship with OptionParser (String, Integer, Float, TrueClass, FalseClass, Array, Regexp, Date, Time, URI, etc.), RDoc::Options adds Path, PathArray and Template.

  


    
A parser is simple a class that subclasses RDoc::Parser and implements scan to fill in an RDoc::TopLevel with parsed data.

The initialize method takes an RDoc::TopLevel to fill with parsed content, the name of the file to be parsed, the content of the file, an RDoc::Options object and an RDoc::Stats object to inform the user of parsed items.  The scan method is then called to parse the file and must return the RDoc::TopLevel object.  By calling super these items will be set for you.

In order to be used by RDoc the parser needs to register the file extensions it can parse.  Use ::parse_files_matching to register extensions.

require 'rdoc'

class RDoc::Parser::Xyz < RDoc::Parser
  parse_files_matching /\.xyz$/

  def initialize top_level, file_name, content, options, stats
    super

    # extra initialization if needed
  end

  def scan
    # parse file and fill in @top_level
  end
end


  


    
RDoc::RD implements the RD format from the rdtool gem.

To choose RD as your only default format see Saved Options at RDoc::Options for instructions on setting up a .doc_options file to store your project default.

LICENSE¶ ↑

The grammar that produces RDoc::RD::BlockParser and RDoc::RD::InlineParser is included in RDoc under the Ruby License.

You can find the original source for rdtool at github.com/uwabami/rdtool/

You can use, re-distribute or change these files under Ruby's License or GPL.

You may make and give away verbatim copies of the source form of the software without restriction, provided that you duplicate all of the original copyright notices and associated disclaimers.

You may modify your copy of the software in any way, provided that you do at least ONE of the following:

place your modifications in the Public Domain or otherwise make them Freely Available, such as by posting said modifications to Usenet or an equivalent medium, or by allowing the author to include your modifications in the software.

use the modified software only within your corporation or organization.

give non-standard binaries non-standard names, with instructions on where to get the original software distribution.

make other distribution arrangements with the author.


You may distribute the software in object code or binary form, provided that you do at least ONE of the following:

distribute the binaries and library files of the software, together with instructions (in the manual page or equivalent) on where to get the original distribution.

accompany the distribution with the machine-readable source of the software.

give non-standard binaries non-standard names, with instructions on where to get the original software distribution.

make other distribution arrangements with the author.


You may modify and include the part of the software into any other software (possibly commercial).  But some files in the distribution are not written by the author, so that they are not under these terms.

For the list of those files and their copying conditions, see the file LEGAL.

The scripts and library files supplied as input to or produced as output from the software do not automatically fall under the copyright of the software, but belong to whomever generated them, and may be sold commercially, and may be aggregated with this software.

THIS SOFTWARE IS PROVIDED “AS IS” AND WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.


  


    
This is the driver for generating RDoc output.  It handles file parsing and generation of output.

To use this class to generate RDoc output via the API, the recommended way is:

rdoc = RDoc::RDoc.new
options = rdoc.load_options # returns an RDoc::Options instance
# set extra options
rdoc.document options


You can also generate output like the rdoc executable:

rdoc = RDoc::RDoc.new
rdoc.document argv


Where argv is an array of strings, each corresponding to an argument you'd give rdoc on the command line.  See <tt>rdoc –help<tt> for details.

  


    
Base RI error class

  


    
A file loaded by #require

  


    
Gem::RDoc provides methods to generate RDoc and ri data for installed gems upon gem installation.

This file is automatically required by RubyGems 1.9 and newer.

  


    
This is a WEBrick servlet that allows you to browse ri documentation.

You can show documentation through either `ri –server` or, with RubyGems 2.0 or newer, `gem server`.  For ri, the server runs on port 8214 by default.  For RubyGems the server runs on port 8808 by default.

You can use this servlet in your own project by mounting it on a WEBrick server:

require 'webrick'

server = WEBrick::HTTPServer.new Port: 8000

server.mount '/', RDoc::Servlet


If you want to mount the servlet some other place than the root, provide the base path when mounting:

server.mount '/rdoc', RDoc::Servlet, '/rdoc'


  


    
A singleton class

  


    
RDoc statistics collector which prints a summary and report of a project's documentation totals.

  


    
A set of rdoc data for a single project (gem, path, etc.).

The store manages reading and writing ri data for a project and maintains a cache of methods, classes and ancestors in the store.

The store maintains a cache of its contents for faster lookup.  After adding items to the store it must be flushed using save_cache.  The cache contains the following structures:

@cache = {
  :ancestors        => {}, # class name => ancestor names
  :attributes       => {}, # class name => attributes
  :class_methods    => {}, # class name => class methods
  :instance_methods => {}, # class name => instance methods
  :modules          => [], # classes and modules in this store
  :pages            => [], # page names
}


  


    
Errors raised from loading or saving the store

  


    
Raised when a stored file for a class, module, page or method is missing.

  


    
RDoc::Task creates the following rake tasks to generate and clean up RDoc output:
rdoc

Main task for this RDoc task.
clobber_rdoc

Delete all the rdoc files.  This target is automatically added to the main clobber target.
rerdoc

Rebuild the rdoc files from scratch, even if they are not out of date.


Simple Example:

require 'rdoc/task'

RDoc::Task.new do |rdoc|
  rdoc.main = "README.rdoc"
  rdoc.rdoc_files.include("README.rdoc", "lib   /*.rb")
end


The rdoc object passed to the block is an RDoc::Task object. See the attributes list for the RDoc::Task class for available customization options.

Specifying different task names¶ ↑

You may wish to give the task a different name, such as if you are generating two sets of documentation.  For instance, if you want to have a development set of documentation including private methods:

require 'rdoc/task'

RDoc::Task.new :rdoc_dev do |rdoc|
  rdoc.main = "README.doc"
  rdoc.rdoc_files.include("README.rdoc", "lib/   *.rb")
  rdoc.options << "--all"
end


The tasks would then be named :rdoc_dev, :clobber_rdoc_dev, and :rerdoc_dev.

If you wish to have completely different task names, then pass a Hash as first argument. With the :rdoc, :clobber_rdoc and :rerdoc options, you can customize the task names to your liking.

For example:

require 'rdoc/task'

RDoc::Task.new(:rdoc => "rdoc", :clobber_rdoc => "rdoc:clean",
               :rerdoc => "rdoc:force")


This will create the tasks :rdoc, :rdoc:clean and :rdoc:force.

  


    
A parser for TomDoc based on TomDoc 1.0.0-rc1 (02adef9b5a)

The TomDoc specification can be found at:

tomdoc.org

The latest version of the TomDoc specification can be found at:

github.com/mojombo/tomdoc/blob/master/tomdoc.md

To choose TomDoc as your only default format see Saved Options at RDoc::Options for instructions on setting up a .rdoc_options file to store your project default.

There are a few differences between this parser and the specification.  A best-effort was made to follow the specification as closely as possible but some choices to deviate were made.

A future version of RDoc will warn when a MUST or MUST NOT is violated and may warn when a SHOULD or SHOULD NOT is violated.  RDoc will always try to emit documentation even if given invalid TomDoc.

Here are some implementation choices this parser currently makes:

This parser allows rdoc-style inline markup but you should not depended on it.

This parser allows a space between the comment and the method body.

This parser does not require the default value to be described for an optional argument.

This parser does not examine the order of sections.  An Examples section may precede the Arguments section.

This class is documented in TomDoc format.  Since this is a subclass of the RDoc markup parser there isn't much to see here, unfortunately.

  


    
A TopLevel context is a representation of the contents of a single file

  


    
RDoc::Task creates the following rake tasks to generate and clean up RDoc output:
rdoc

Main task for this RDoc task.
clobber_rdoc

Delete all the rdoc files.  This target is automatically added to the main clobber target.
rerdoc

Rebuild the rdoc files from scratch, even if they are not out of date.


Simple Example:

require 'rdoc/task'

RDoc::Task.new do |rdoc|
  rdoc.main = "README.rdoc"
  rdoc.rdoc_files.include("README.rdoc", "lib   /*.rb")
end


The rdoc object passed to the block is an RDoc::Task object. See the attributes list for the RDoc::Task class for available customization options.

Specifying different task names¶ ↑

You may wish to give the task a different name, such as if you are generating two sets of documentation.  For instance, if you want to have a development set of documentation including private methods:

require 'rdoc/task'

RDoc::Task.new :rdoc_dev do |rdoc|
  rdoc.main = "README.doc"
  rdoc.rdoc_files.include("README.rdoc", "lib/   *.rb")
  rdoc.options << "--all"
end


The tasks would then be named :rdoc_dev, :clobber_rdoc_dev, and :rerdoc_dev.

If you wish to have completely different task names, then pass a Hash as first argument. With the :rdoc, :clobber_rdoc and :rerdoc options, you can customize the task names to your liking.

For example:

require 'rdoc/task'

RDoc::Task.new(:rdoc => "rdoc", :clobber_rdoc => "rdoc:clean",
               :rerdoc => "rdoc:force")


This will create the tasks :rdoc, :rdoc:clean and :rdoc:force.

  


    
This class needs:

Documentation

Work!  Not all types of attlists are intelligently parsed, so we just


spew back out what we get in.  This works, but it would be better if we formatted the output ourselves.

AttlistDecls provide just enough support to allow namespace declarations.  If you need some sort of generalized support, or have an interesting idea about how to map the hideous, terrible design of DTD AttlistDecls onto an intuitive Ruby interface, let me know.  I'm desperate for anything to make DTDs more palateable.

  


    
Defines an Element Attribute; IE, a attribute=value pair, as in: <element attribute=“value”/>.  Attributes can be in their own namespaces.  General users of REXML will not interact with the Attribute class much.

  


    
A class that defines the set of Attributes of an Element and provides operations for accessing elements in that set.

  


    
A Child object is something contained by a parent, and this class contains methods to support that.  Most user code will not use this class directly.

  


    
Represents an XML comment; that is, text between <!– … –>

  


    
This is an abstract class.  You never use this directly; it serves as a parent class for the specific declarations.

  


    
Represents an XML DOCTYPE declaration; that is, the contents of <!DOCTYPE … >.  DOCTYPES can be used to declare the DTD of a document, as well as being used to declare entities used in the document.

  


    
Represents a full XML document, including PIs, a doctype, etc.  A Document has a single child that can be accessed by root(). Note that if you want to have an XML declaration written for a document you create, you must add one; REXML documents do not write a default declaration for you.  See |DECLARATION| and |write|.

  


    
Represents a tagged XML element.  Elements are characterized by having children, attributes, and names, and can themselves be children.

  


    
A class which provides filtering of children for Elements, and XPath search support.  You are expected to only encounter this class as the element.elements object.  Therefore, you are not expected to instantiate this yourself.

  


    
Pretty-prints an XML document.  This destroys whitespace in text nodes and will insert carriage returns and indentations.

TODO: Add an option to print attributes on new lines

  


    
The Transitive formatter writes an XML document that parses to an identical document as the source document.  This means that no extra whitespace nodes are inserted, and whitespace within text nodes is preserved.  Within these constraints, the document is pretty-printed, with whitespace inserted into the metadata to introduce formatting.

Note that this is only useful if the original XML is not already formatted.  Since this formatter does not alter whitespace nodes, the results of formatting already formatted XML will be odd.

  


    
A Source that wraps an IO.  See the Source class for method documentation

  


    
Represents an XML Instruction; IE, <? … ?> TODO: Add parent arg (3rd arg) to constructor

  


    
Represents a tagged XML element.  Elements are characterized by having children, attributes, and names, and can themselves be children.

  


    
A parent has children, and has methods for accessing them.  The Parent class is never encountered except as the superclass for some other object.

  


    
Using the Pull Parser¶ ↑

This API is experimental, and subject to change.

parser = PullParser.new( "<a>text<b att='val'/>txet</a>" )
while parser.has_next?
  res = parser.next
  puts res[1]['att'] if res.start_tag? and res[0] == 'b'
end


See the PullEvent class for information on the content of the results. The data is identical to the arguments passed for the various events to the StreamListener API.

Notice that:

parser = PullParser.new( "<a>BAD DOCUMENT" )
while parser.has_next?
  res = parser.next
  raise res[1] if res.error?
end


Nat Price gave me some good ideas for the API.

  


    
A parsing event.  The contents of the event are accessed as an +Array?, and the type is given either by the …? methods, or by accessing the type accessor.  The contents of this object vary from event to event, but are identical to the arguments passed to +StreamListener+s for each event.

  


    
Using the Pull Parser¶ ↑

This API is experimental, and subject to change.

parser = PullParser.new( "<a>text<b att='val'/>txet</a>" )
while parser.has_next?
  res = parser.next
  puts res[1]['att'] if res.start_tag? and res[0] == 'b'
end


See the PullEvent class for information on the content of the results. The data is identical to the arguments passed for the various events to the StreamListener API.

Notice that:

parser = PullParser.new( "<a>BAD DOCUMENT" )
while parser.has_next?
  res = parser.next
  raise res[1] if res.error?
end


Nat Price gave me some good ideas for the API.

  


    
SAX2Parser

  


    
You don't want to use this class.  Really.  Use XPath, which is a wrapper for this class.  Believe me.  You don't want to poke around in here. There is strange, dark magic at work in this code.  Beware.  Go back!  Go back while you still can!

  


    
A Source can be searched for patterns, and wraps buffers and other objects and provides consumption of text

  


    
Generates Source-s.  USE THIS CLASS.

  


    
Represents text nodes in an XML document

  


    
Implemented:

empty

element

attribute

text

optional

choice

oneOrMore

zeroOrMore

group

value

interleave

mixed

ref

grammar

start

define


Not implemented:

data

param

include

externalRef

notAllowed

anyName

nsName

except

name


  


    
NEEDS DOCUMENTATION

  


    
Wrapper class.  Use this class to access the XPath functions.

  


    
@private

  


    
You don't want to use this class.  Really.  Use XPath, which is a wrapper for this class.  Believe me.  You don't want to poke around in here. There is strange, dark magic at work in this code.  Beware.  Go back!  Go back while you still can!

  


    
Defines a top-level Atom Entry element, used as the document element of a stand-alone Atom Entry Document. It has the following attributes:

author

category

categories

content

contributor

id

link

published

rights

source

summary

title

updated


Reference: validator.w3.org/feed/docs/rfc4287.html#element.entry]

  


    
Defines the top-level element of an Atom Feed Document. It consists of a number of children Entry elements, and has the following attributes:

author

categories

category

content

contributor

entries (aliased as items)

entry

generator

icon

id

link

logo

rights

subtitle

title

updated


Reference: validator.w3.org/feed/docs/rfc4287.html#element.feed

  


    
PersonConstruct that contains information regarding the author of a Feed or Entry.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.author

  


    
Contains information about a category associated with a Feed or Entry. It has the following attributes:

term

scheme

label


Reference: validator.w3.org/feed/docs/rfc4287.html#element.category

  


    
PersonConstruct that contains information regarding the contributors of a Feed or Entry.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.contributor

  


    
Defines a child Atom Entry element of an Atom Feed element. It has the following attributes:

author

category

categories

content

contributor

id

link

published

rights

source

summary

title

updated


Reference: validator.w3.org/feed/docs/rfc4287.html#element.entry

  


    
Contains or links to the content of the Entry. It has the following attributes:

type

src


Reference: validator.w3.org/feed/docs/rfc4287.html#element.content

  


    
DateConstruct that usually indicates the time of the initial creation of an Entry.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.published

  


    
Defines a Atom Source element. It has the following attributes:

author

category

categories

content

contributor

generator

icon

id

link

logo

rights

subtitle

title

updated


Reference: validator.w3.org/feed/docs/rfc4287.html#element.source

  


    
TextConstruct that describes a summary of the Entry.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.summary

  


    
Contains information on the agent used to generate the feed.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.generator

  


    
Defines an image that provides a visual identification for a eed. The image should have an aspect ratio of 1:1.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.icon

  


    
Defines the Universally Unique Identifier (UUID) for a Feed or Entry.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.id

  


    
Defines a reference to a Web resource. It has the following attributes:

href

rel

type

hreflang

title

length


Reference: validator.w3.org/feed/docs/rfc4287.html#element.link

  


    
Defines an image that provides a visual identification for the Feed. The image should have an aspect ratio of 2:1 (horizontal:vertical).

Reference: validator.w3.org/feed/docs/rfc4287.html#element.logo

  


    
TextConstruct that contains copyright information regarding the content in an Entry or Feed. It should not be used to convey machine readable licensing information.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.rights

  


    
TextConstruct that conveys a description or subtitle for a Feed.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.subtitle

  


    
TextConstruct that conveys a description or title for a Feed or Entry.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.title

  


    
DateConstruct indicating the most recent time when a Feed or Entry was modified in a way the publisher considers significant.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.updated

  


    
The email of the person or entity.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.email

  


    
The name of the person or entity.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.name

  


    
The URI of the person or entity.

Reference: validator.w3.org/feed/docs/rfc4287.html#element.uri

  


    
Raised when a conversion failure occurs.

  


    
The basic error all other RSS errors stem from. Rescue this error if you want to handle any given RSS error and you don't care about the details.

  


    
The InvalidRSSError error is the base class for a variety of errors related to a poorly-formed RSS feed. Rescue this error if you only care that a file could be invalid, but don't care how it is invalid.

  


    
Certain attributes are required on specific tags in an RSS feed. If a feed is missing one of these attributes, a MissingAttributeError is raised.

  


    
Since RSS is based on XML, it must have opening and closing tags that match. If they don't, a MissingTagError will be raised.

  


    
Attributes are in key-value form, and if there's no value provided for an attribute, a NotAvailableValueError will be raised.

  


    
Raised when an unexpected tag is encountered.

  


    
Raised when a required variable is not set.

  


    
RSS, being an XML-based format, has namespace support. If two namespaces are declared with the same name, an OverlappedPrefixError will be raised.

  


    
Some tags must only exist a specific number of times in a given RSS feed. If a feed has too many occurrences of one of these tags, a TooMuchTagError will be raised.

  


    
Raised when an unknown conversion error occurs.

  


    
RSS does not allow for free-form tag names, so if an RSS feed contains a tag that we don't know about, an UnknownTagError is raised.

  


    
Raised when a RSS::Maker attempts to use an unknown maker.

  


    
Random provides an interface to Ruby's pseudo-random number generator, or PRNG.  The PRNG produces a deterministic sequence of bits which approximate true randomness. The sequence may be represented by integers, floats, or binary strings.

The generator may be initialized with either a system-generated or user-supplied seed value by using Random.srand.

The class method Random.rand provides the base functionality of Kernel.rand along with better handling of floating point values. These are both interfaces to Random::DEFAULT, the Ruby system PRNG.

Random.new will create a new PRNG with a state independent of Random::DEFAULT, allowing multiple generators with different seed values or sequence positions to exist simultaneously. Random objects can be marshaled, allowing sequences to be saved and resumed.

PRNGs are currently implemented as a modified Mersenne Twister with a period of 2**19937-1.

  


    
A Range represents an interval—a set of values with a beginning and an end. Ranges may be constructed using the s..e and s...e literals, or with Range::new. Ranges constructed using .. run from the beginning to the end inclusively. Those created using ... exclude the end value. When used as an iterator, ranges return each value in the sequence.

(-1..-5).to_a      #=> []
(-5..-1).to_a      #=> [-5, -4, -3, -2, -1]
('a'..'e').to_a    #=> ["a", "b", "c", "d", "e"]
('a'...'e').to_a   #=> ["a", "b", "c", "d"]


Endless Ranges¶ ↑

An “endless range” represents a semi-infinite range. Literal notation for an endless range is:

(1..)
# or similarly
(1...)

Which is equivalent to

(1..nil)  # or similarly (1...nil)
Range.new(1, nil) # or Range.new(1, nil, true)


Endless ranges are useful, for example, for idiomatic slicing of arrays:

[1, 2, 3, 4, 5][2...]   # => [3, 4, 5]

Some implementation details:

end of endless range is nil;

each of endless range enumerates infinite sequence (may be useful in combination with Enumerable#take_while or similar methods);

(1..) and (1...) are not equal, although technically representing the same sequence.


Custom Objects in Ranges¶ ↑

Ranges can be constructed using any objects that can be compared using the <=> operator. Methods that treat the range as a sequence (#each and methods inherited from Enumerable) expect the begin object to implement a succ method to return the next object in sequence. The step and include? methods require the begin object to implement succ or to be numeric.

In the Xs class below both <=> and succ are implemented so Xs can be used to construct ranges. Note that the Comparable module is included so the == method is defined in terms of <=>.

class Xs                # represent a string of 'x's
  include Comparable
  attr :length
  def initialize(n)
    @length = n
  end
  def succ
    Xs.new(@length + 1)
  end
  def <=>(other)
    @length <=> other.length
  end
  def to_s
    sprintf "%2d #{inspect}", @length
  end
  def inspect
    'x' * @length
  end
end


An example of using Xs to construct a range:

r = Xs.new(3)..Xs.new(6)   #=> xxx..xxxxxx
r.to_a                     #=> [xxx, xxxx, xxxxx, xxxxxx]
r.member?(Xs.new(5))       #=> true


  


    
Raised when a given numerical value is out of range.

[1, 2, 3].drop(1 << 100)


raises the exception:

RangeError: bignum too big to convert into `long'

  


    
A rational number can be represented as a pair of integer numbers: a/b (b>0), where a is the numerator and b is the denominator. Integer a equals rational a/1 mathematically.

In Ruby, you can create rational objects with the Kernel#Rational, to_r, or rationalize methods or by suffixing r to a literal. The return values will be irreducible fractions.

Rational(1)      #=> (1/1)
Rational(2, 3)   #=> (2/3)
Rational(4, -6)  #=> (-2/3)
3.to_r           #=> (3/1)
2/3r             #=> (2/3)


You can also create rational objects from floating-point numbers or strings.

Rational(0.3)    #=> (5404319552844595/18014398509481984)
Rational('0.3')  #=> (3/10)
Rational('2/3')  #=> (2/3)

0.3.to_r         #=> (5404319552844595/18014398509481984)
'0.3'.to_r       #=> (3/10)
'2/3'.to_r       #=> (2/3)
0.3.rationalize  #=> (3/10)


A rational object is an exact number, which helps you to write programs without any rounding errors.

10.times.inject(0) {|t| t + 0.1 }              #=> 0.9999999999999999
10.times.inject(0) {|t| t + Rational('0.1') }  #=> (1/1)


However, when an expression includes an inexact component (numerical value or operation), it will produce an inexact result.

Rational(10) / 3   #=> (10/3)
Rational(10) / 3.0 #=> 3.3333333333333335

Rational(-8) ** Rational(1, 3)
                   #=> (1.0000000000000002+1.7320508075688772i)


  


    
A Regexp holds a regular expression, used to match a pattern against strings. Regexps are created using the /.../ and %r{...} literals, and by the Regexp::new constructor.

Regular expressions (regexps) are patterns which describe the contents of a string. They're used for testing whether a string contains a given pattern, or extracting the portions that match. They are created with the /pat/ and %r{pat} literals or the Regexp.new constructor.

A regexp is usually delimited with forward slashes (/). For example:

/hay/ =~ 'haystack'   #=> 0
/y/.match('haystack') #=> #<MatchData "y">


If a string contains the pattern it is said to match. A literal string matches itself.

Here 'haystack' does not contain the pattern 'needle', so it doesn't match:

/needle/.match('haystack') #=> nil


Here 'haystack' contains the pattern 'hay', so it matches:

/hay/.match('haystack')    #=> #<MatchData "hay">


Specifically, /st/ requires that the string contains the letter s followed by the letter t, so it matches haystack, also.

=~ and Regexp#match¶ ↑

Pattern matching may be achieved by using =~ operator or Regexp#match method.

=~ operator¶ ↑

=~ is Ruby's basic pattern-matching operator.  When one operand is a regular expression and the other is a string then the regular expression is used as a pattern to match against the string.  (This operator is equivalently defined by Regexp and String so the order of String and Regexp do not matter. Other classes may have different implementations of =~.)  If a match is found, the operator returns index of first match in string, otherwise it returns nil.

/hay/ =~ 'haystack'   #=> 0
'haystack' =~ /hay/   #=> 0
/a/   =~ 'haystack'   #=> 1
/u/   =~ 'haystack'   #=> nil


Using =~ operator with a String and Regexp the $~ global variable is set after a successful match.  $~ holds a MatchData object. Regexp.last_match is equivalent to $~.

Regexp#match method¶ ↑

The match method returns a MatchData object:

/st/.match('haystack')   #=> #<MatchData "st">


Metacharacters and Escapes¶ ↑

The following are metacharacters (, ), [, ], {, }, ., ?, +, *. They have a specific meaning when appearing in a pattern. To match them literally they must be backslash-escaped. To match a backslash literally, backslash-escape it: \\.

/1 \+ 2 = 3\?/.match('Does 1 + 2 = 3?') #=> #<MatchData "1 + 2 = 3?">
/a\\\\b/.match('a\\\\b')                    #=> #<MatchData "a\\b">


Patterns behave like double-quoted strings so can contain the same backslash escapes.

/\s\u{6771 4eac 90fd}/.match("Go to 東京都")
    #=> #<MatchData " 東京都">


Arbitrary Ruby expressions can be embedded into patterns with the #{...} construct.

place = "東京都"
/#{place}/.match("Go to 東京都")
    #=> #<MatchData "東京都">


Character Classes¶ ↑

A character class is delimited with square brackets ([, ]) and lists characters that may appear at that point in the match. /[ab]/ means a or b, as opposed to /ab/ which means a followed by b.

/W[aeiou]rd/.match("Word") #=> #<MatchData "Word">


Within a character class the hyphen (-) is a metacharacter denoting an inclusive range of characters. [abcd] is equivalent to [a-d]. A range can be followed by another range, so [abcdwxyz] is equivalent to [a-dw-z]. The order in which ranges or individual characters appear inside a character class is irrelevant.

/[0-9a-f]/.match('9f') #=> #<MatchData "9">
/[9f]/.match('9f')     #=> #<MatchData "9">


If the first character of a character class is a caret (^) the class is inverted: it matches any character except those named.

/[^a-eg-z]/.match('f') #=> #<MatchData "f">


A character class may contain another character class. By itself this isn't useful because [a-z[0-9]] describes the same set as [a-z0-9]. However, character classes also support the && operator which performs set intersection on its arguments. The two can be combined as follows:

/[a-w&&[^c-g]z]/ # ([a-w] AND ([^c-g] OR z))


This is equivalent to:

/[abh-w]/


The following metacharacters also behave like character classes:

/./ - Any character except a newline.

/./m - Any character (the m modifier enables multiline mode)

/\w/ - A word character ([a-zA-Z0-9_])

/\W/ - A non-word character ([^a-zA-Z0-9_]). Please take a look at Bug #4044 if using /\W/ with the /i modifier.

/\d/ - A digit character ([0-9])

/\D/ - A non-digit character ([^0-9])

/\h/ - A hexdigit character ([0-9a-fA-F])

/\H/ - A non-hexdigit character ([^0-9a-fA-F])

/\s/ - A whitespace character: /[ \t\r\n\f\v]/

/\S/ - A non-whitespace character: /[^ \t\r\n\f\v]/


POSIX bracket expressions are also similar to character classes. They provide a portable alternative to the above, with the added benefit that they encompass non-ASCII characters. For instance, /\d/ matches only the ASCII decimal digits (0-9); whereas /[[:digit:]]/ matches any character in the Unicode Nd category.

/[[:alnum:]]/ - Alphabetic and numeric character

/[[:alpha:]]/ - Alphabetic character

/[[:blank:]]/ - Space or tab

/[[:cntrl:]]/ - Control character

/[[:digit:]]/ - Digit

/[[:graph:]]/ - Non-blank character (excludes spaces, control characters, and similar)

/[[:lower:]]/ - Lowercase alphabetical character

/[[:print:]]/ - Like [:graph:], but includes the space character

/[[:punct:]]/ - Punctuation character

/[[:space:]]/ - Whitespace character ([:blank:], newline, carriage return, etc.)

/[[:upper:]]/ - Uppercase alphabetical

/[[:xdigit:]]/ - Digit allowed in a hexadecimal number (i.e., 0-9a-fA-F)


Ruby also supports the following non-POSIX character classes:

/[[:word:]]/ - A character in one of the following Unicode general categories Letter, Mark, Number, Connector_Punctuation

/[[:ascii:]]/ - A character in the ASCII character set

# U+06F2 is "EXTENDED ARABIC-INDIC DIGIT TWO"
/[[:digit:]]/.match("\u06F2")    #=> #<MatchData "\u{06F2}">
/[[:upper:]][[:lower:]]/.match("Hello") #=> #<MatchData "He">
/[[:xdigit:]][[:xdigit:]]/.match("A6")  #=> #<MatchData "A6">



Repetition¶ ↑

The constructs described so far match a single character. They can be followed by a repetition metacharacter to specify how many times they need to occur. Such metacharacters are called quantifiers.

* - Zero or more times

+ - One or more times

? - Zero or one times (optional)

{n} - Exactly n times

{n,} - n or more times

{,m} - m or less times

{n,m} - At least n and at most m times


At least one uppercase character ('H'), at least one lowercase character ('e'), two 'l' characters, then one 'o':

"Hello".match(/[[:upper:]]+[[:lower:]]+l{2}o/) #=> #<MatchData "Hello">


Repetition is greedy by default: as many occurrences as possible are matched while still allowing the overall match to succeed. By contrast, lazy matching makes the minimal amount of matches necessary for overall success. A greedy metacharacter can be made lazy by following it with ?.

Both patterns below match the string. The first uses a greedy quantifier so '.+' matches '<a><b>'; the second uses a lazy quantifier so '.+?' matches '<a>':

/<.+>/.match("<a><b>")  #=> #<MatchData "<a><b>">
/<.+?>/.match("<a><b>") #=> #<MatchData "<a>">


A quantifier followed by + matches possessively: once it has matched it does not backtrack. They behave like greedy quantifiers, but having matched they refuse to “give up” their match even if this jeopardises the overall match.

Capturing¶ ↑

Parentheses can be used for capturing. The text enclosed by the n<sup>th</sup> group of parentheses can be subsequently referred to with n. Within a pattern use the backreference \n; outside of the pattern use MatchData[n].

'at' is captured by the first group of parentheses, then referred to later with \1:

/[csh](..) [csh]\1 in/.match("The cat sat in the hat")
    #=> #<MatchData "cat sat in" 1:"at">


Regexp#match returns a MatchData object which makes the captured text available with its [] method:

/[csh](..) [csh]\1 in/.match("The cat sat in the hat")[1] #=> 'at'


Capture groups can be referred to by name when defined with the (?<name>) or (?'name') constructs.

/\$(?<dollars>\d+)\.(?<cents>\d+)/.match("$3.67")
    #=> #<MatchData "$3.67" dollars:"3" cents:"67">
/\$(?<dollars>\d+)\.(?<cents>\d+)/.match("$3.67")[:dollars] #=> "3"


Named groups can be backreferenced with \k<name>, where name is the group name.

/(?<vowel>[aeiou]).\k<vowel>.\k<vowel>/.match('ototomy')
    #=> #<MatchData "ototo" vowel:"o">


Note: A regexp can't use named backreferences and numbered backreferences simultaneously.

When named capture groups are used with a literal regexp on the left-hand side of an expression and the =~ operator, the captured text is also assigned to local variables with corresponding names.

/\$(?<dollars>\d+)\.(?<cents>\d+)/ =~ "$3.67" #=> 0
dollars #=> "3"


Grouping¶ ↑

Parentheses also group the terms they enclose, allowing them to be quantified as one atomic whole.

The pattern below matches a vowel followed by 2 word characters:

/[aeiou]\w{2}/.match("Caenorhabditis elegans") #=> #<MatchData "aen">


Whereas the following pattern matches a vowel followed by a word character, twice, i.e. [aeiou]\w[aeiou]\w: 'enor'.

/([aeiou]\w){2}/.match("Caenorhabditis elegans")
    #=> #<MatchData "enor" 1:"or">


The (?:…) construct provides grouping without capturing. That is, it combines the terms it contains into an atomic whole without creating a backreference. This benefits performance at the slight expense of readability.

The first group of parentheses captures 'n' and the second 'ti'. The second group is referred to later with the backreference \2:

/I(n)ves(ti)ga\2ons/.match("Investigations")
    #=> #<MatchData "Investigations" 1:"n" 2:"ti">


The first group of parentheses is now made non-capturing with '?:', so it still matches 'n', but doesn't create the backreference. Thus, the backreference \1 now refers to 'ti'.

/I(?:n)ves(ti)ga\1ons/.match("Investigations")
    #=> #<MatchData "Investigations" 1:"ti">


Atomic Grouping¶ ↑

Grouping can be made atomic with (?>pat). This causes the subexpression pat to be matched independently of the rest of the expression such that what it matches becomes fixed for the remainder of the match, unless the entire subexpression must be abandoned and subsequently revisited. In this way pat is treated as a non-divisible whole. Atomic grouping is typically used to optimise patterns so as to prevent the regular expression engine from backtracking needlessly.

The " in the pattern below matches the first character of the string, then .* matches Quote“. This causes the overall match to fail, so the text matched by .* is backtracked by one position, which leaves the final character of the string available to match "

/".*"/.match('"Quote"')     #=> #<MatchData "\"Quote\"">


If .* is grouped atomically, it refuses to backtrack Quote“, even though this means that the overall match fails

/"(?>.*)"/.match('"Quote"') #=> nil


Subexpression Calls¶ ↑

The \g<name> syntax matches the previous subexpression named name, which can be a group name or number, again. This differs from backreferences in that it re-executes the group rather than simply trying to re-match the same text.

This pattern matches a ( character and assigns it to the paren group, tries to call that the paren sub-expression again but fails, then matches a literal ):

/\A(?<paren>\(\g<paren>*\))*\z/ =~ '()'

/\A(?<paren>\(\g<paren>*\))*\z/ =~ '(())' #=> 0
# ^1
#      ^2
#           ^3
#                 ^4
#      ^5
#           ^6
#                      ^7
#                       ^8
#                       ^9
#                           ^10


Matches at the beginning of the string, i.e. before the first character.

Enters a named capture group called paren

Matches a literal (, the first character in the string

Calls the paren group again, i.e. recurses back to the second step

Re-enters the paren group

Matches a literal (, the second character in the string

Try to call paren a third time, but fail because doing so would prevent an overall successful match

Match a literal ), the third character in the string. Marks the end of the second recursive call

Match a literal ), the fourth character in the string

Match the end of the string


Alternation¶ ↑

The vertical bar metacharacter (|) combines two expressions into a single one that matches either of the expressions. Each expression is an alternative.

/\w(and|or)\w/.match("Feliformia") #=> #<MatchData "form" 1:"or">
/\w(and|or)\w/.match("furandi")    #=> #<MatchData "randi" 1:"and">
/\w(and|or)\w/.match("dissemblance") #=> nil


Character Properties¶ ↑

The \p{} construct matches characters with the named property, much like POSIX bracket classes.

/\p{Alnum}/ - Alphabetic and numeric character

/\p{Alpha}/ - Alphabetic character

/\p{Blank}/ - Space or tab

/\p{Cntrl}/ - Control character

/\p{Digit}/ - Digit

/\p{Graph}/ - Non-blank character (excludes spaces, control characters, and similar)

/\p{Lower}/ - Lowercase alphabetical character

/\p{Print}/ - Like \p{Graph}, but includes the space character

/\p{Punct}/ - Punctuation character

/\p{Space}/ - Whitespace character ([:blank:], newline, carriage return, etc.)

/\p{Upper}/ - Uppercase alphabetical

/\p{XDigit}/ - Digit allowed in a hexadecimal number (i.e., 0-9a-fA-F)

/\p{Word}/ - A member of one of the following Unicode general category Letter, Mark, Number, Connector_Punctuation

/\p{ASCII}/ - A character in the ASCII character set

/\p{Any}/ - Any Unicode character (including unassigned characters)

/\p{Assigned}/ - An assigned character


A Unicode character's General Category value can also be matched with \p{Ab} where Ab is the category's abbreviation as described below:

/\p{L}/ - 'Letter'

/\p{Ll}/ - 'Letter: Lowercase'

/\p{Lm}/ - 'Letter: Mark'

/\p{Lo}/ - 'Letter: Other'

/\p{Lt}/ - 'Letter: Titlecase'

/\p{Lu}/ - 'Letter: Uppercase

/\p{Lo}/ - 'Letter: Other'

/\p{M}/ - 'Mark'

/\p{Mn}/ - 'Mark: Nonspacing'

/\p{Mc}/ - 'Mark: Spacing Combining'

/\p{Me}/ - 'Mark: Enclosing'

/\p{N}/ - 'Number'

/\p{Nd}/ - 'Number: Decimal Digit'

/\p{Nl}/ - 'Number: Letter'

/\p{No}/ - 'Number: Other'

/\p{P}/ - 'Punctuation'

/\p{Pc}/ - 'Punctuation: Connector'

/\p{Pd}/ - 'Punctuation: Dash'

/\p{Ps}/ - 'Punctuation: Open'

/\p{Pe}/ - 'Punctuation: Close'

/\p{Pi}/ - 'Punctuation: Initial Quote'

/\p{Pf}/ - 'Punctuation: Final Quote'

/\p{Po}/ - 'Punctuation: Other'

/\p{S}/ - 'Symbol'

/\p{Sm}/ - 'Symbol: Math'

/\p{Sc}/ - 'Symbol: Currency'

/\p{Sc}/ - 'Symbol: Currency'

/\p{Sk}/ - 'Symbol: Modifier'

/\p{So}/ - 'Symbol: Other'

/\p{Z}/ - 'Separator'

/\p{Zs}/ - 'Separator: Space'

/\p{Zl}/ - 'Separator: Line'

/\p{Zp}/ - 'Separator: Paragraph'

/\p{C}/ - 'Other'

/\p{Cc}/ - 'Other: Control'

/\p{Cf}/ - 'Other: Format'

/\p{Cn}/ - 'Other: Not Assigned'

/\p{Co}/ - 'Other: Private Use'

/\p{Cs}/ - 'Other: Surrogate'


Lastly, \p{} matches a character's Unicode script. The following scripts are supported: Arabic, Armenian, Balinese, Bengali, Bopomofo, Braille, Buginese, Buhid, Canadian_Aboriginal, Carian, Cham, Cherokee, Common, Coptic, Cuneiform, Cypriot, Cyrillic, Deseret, Devanagari, Ethiopic, Georgian, Glagolitic, Gothic, Greek, Gujarati, Gurmukhi, Han, Hangul, Hanunoo, Hebrew, Hiragana, Inherited, Kannada, Katakana, Kayah_Li, Kharoshthi, Khmer, Lao, Latin, Lepcha, Limbu, Linear_B, Lycian, Lydian, Malayalam, Mongolian, Myanmar, New_Tai_Lue, Nko, Ogham, Ol_Chiki, Old_Italic, Old_Persian, Oriya, Osmanya, Phags_Pa, Phoenician, Rejang, Runic, Saurashtra, Shavian, Sinhala, Sundanese, Syloti_Nagri, Syriac, Tagalog, Tagbanwa, Tai_Le, Tamil, Telugu, Thaana, Thai, Tibetan, Tifinagh, Ugaritic, Vai, and Yi.

Unicode codepoint U+06E9 is named “ARABIC PLACE OF SAJDAH” and belongs to the Arabic script:

/\p{Arabic}/.match("\u06E9") #=> #<MatchData "\u06E9">


All character properties can be inverted by prefixing their name with a caret (^).

Letter 'A' is not in the Unicode Ll (Letter; Lowercase) category, so this match succeeds:

/\p{^Ll}/.match("A") #=> #<MatchData "A">


Anchors¶ ↑

Anchors are metacharacter that match the zero-width positions between characters, anchoring the match to a specific position.

^ - Matches beginning of line

$ - Matches end of line

\A - Matches beginning of string.

\Z - Matches end of string. If string ends with a newline, it matches just before newline

\z - Matches end of string

\G - Matches first matching position:

In methods like String#gsub and String#scan, it changes on each iteration. It initially matches the beginning of subject, and in each following iteration it matches where the last match finished.

"    a b c".gsub(/ /, '_')    #=> "____a_b_c"
"    a b c".gsub(/\G /, '_')  #=> "____a b c"


In methods like Regexp#match and String#match that take an (optional) offset, it matches where the search begins.

"hello, world".match(/,/, 3)    #=> #<MatchData ",">
"hello, world".match(/\G,/, 3)  #=> nil


\b - Matches word boundaries when outside brackets; backspace (0x08) when inside brackets

\B - Matches non-word boundaries

(?=pat) - Positive lookahead assertion: ensures that the following characters match pat, but doesn't include those characters in the matched text

(?!pat) - Negative lookahead assertion: ensures that the following characters do not match pat, but doesn't include those characters in the matched text

(?<=pat) - Positive lookbehind assertion: ensures that the preceding characters match pat, but doesn't include those characters in the matched text

(?<!pat) - Negative lookbehind assertion: ensures that the preceding characters do not match pat, but doesn't include those characters in the matched text


If a pattern isn't anchored it can begin at any point in the string:

/real/.match("surrealist") #=> #<MatchData "real">


Anchoring the pattern to the beginning of the string forces the match to start there. 'real' doesn't occur at the beginning of the string, so now the match fails:

/\Areal/.match("surrealist") #=> nil


The match below fails because although 'Demand' contains 'and', the pattern does not occur at a word boundary.

/\band/.match("Demand")


Whereas in the following example 'and' has been anchored to a non-word boundary so instead of matching the first 'and' it matches from the fourth letter of 'demand' instead:

/\Band.+/.match("Supply and demand curve") #=> #<MatchData "and curve">


The pattern below uses positive lookahead and positive lookbehind to match text appearing in  tags without including the tags in the match:

/(?<=<b>)\w+(?=<\/b>)/.match("Fortune favours the <b>bold</b>")
    #=> #<MatchData "bold">


Options¶ ↑

The end delimiter for a regexp can be followed by one or more single-letter options which control how the pattern can match.

/pat/i - Ignore case

/pat/m - Treat a newline as a character matched by .

/pat/x - Ignore whitespace and comments in the pattern

/pat/o - Perform #{} interpolation only once


i, m, and x can also be applied on the subexpression level with the (?on-off) construct, which enables options on, and disables options off for the expression enclosed by the parentheses:

/a(?i:b)c/.match('aBc')   #=> #<MatchData "aBc">
/a(?-i:b)c/i.match('ABC') #=> nil


Additionally, these options can also be toggled for the remainder of the pattern:

/a(?i)bc/.match('abC') #=> #<MatchData "abC">


Options may also be used with Regexp.new:

Regexp.new("abc", Regexp::IGNORECASE)                     #=> /abc/i
Regexp.new("abc", Regexp::MULTILINE)                      #=> /abc/m
Regexp.new("abc # Comment", Regexp::EXTENDED)             #=> /abc # Comment/x
Regexp.new("abc", Regexp::IGNORECASE | Regexp::MULTILINE) #=> /abc/mi


Free-Spacing Mode and Comments¶ ↑

As mentioned above, the x option enables free-spacing mode. Literal white space inside the pattern is ignored, and the octothorpe (#) character introduces a comment until the end of the line. This allows the components of the pattern to be organized in a potentially more readable fashion.

A contrived pattern to match a number with optional decimal places:

float_pat = /\A
    [[:digit:]]+ # 1 or more digits before the decimal point
    (\.          # Decimal point
        [[:digit:]]+ # 1 or more digits after the decimal point
    )? # The decimal point and following digits are optional
\Z/x
float_pat.match('3.14') #=> #<MatchData "3.14" 1:".14">


There are a number of strategies for matching whitespace:

Use a pattern such as \s or \p{Space}.

Use escaped whitespace such as \ , i.e. a space preceded by a backslash.

Use a character class such as [ ].


Comments can be included in a non-x pattern with the (?#comment) construct, where comment is arbitrary text ignored by the regexp engine.

Comments in regexp literals cannot include unescaped terminator characters.

Encoding¶ ↑

Regular expressions are assumed to use the source encoding. This can be overridden with one of the following modifiers.

/pat/u - UTF-8

/pat/e - EUC-JP

/pat/s - Windows-31J

/pat/n - ASCII-8BIT


A regexp can be matched against a string when they either share an encoding, or the regexp's encoding is US-ASCII and the string's encoding is ASCII-compatible.

If a match between incompatible encodings is attempted an Encoding::CompatibilityError exception is raised.

The Regexp#fixed_encoding? predicate indicates whether the regexp has a fixed encoding, that is one incompatible with ASCII. A regexp's encoding can be explicitly fixed by supplying Regexp::FIXEDENCODING as the second argument of Regexp.new:

r = Regexp.new("a".force_encoding("iso-8859-1"),Regexp::FIXEDENCODING)
r =~ "a\u3042"
   # raises Encoding::CompatibilityError: incompatible encoding regexp match
   #         (ISO-8859-1 regexp with UTF-8 string)


Special global variables¶ ↑

Pattern matching sets some global variables :

$~ is equivalent to Regexp.last_match;

$& contains the complete matched text;

$` contains string before match;

$' contains string after match;

$1, $2 and so on contain text matching first, second, etc capture group;

$+ contains last capture group.


Example:

m = /s(\w{2}).*(c)/.match('haystack') #=> #<MatchData "stac" 1:"ta" 2:"c">
$~                                    #=> #<MatchData "stac" 1:"ta" 2:"c">
Regexp.last_match                     #=> #<MatchData "stac" 1:"ta" 2:"c">

$&      #=> "stac"
        # same as m[0]
$`      #=> "hay"
        # same as m.pre_match
$'      #=> "k"
        # same as m.post_match
$1      #=> "ta"
        # same as m[1]
$2      #=> "c"
        # same as m[2]
$3      #=> nil
        # no third group in pattern
$+      #=> "c"
        # same as m[-1]


These global variables are thread-local and method-local variables.

Performance¶ ↑

Certain pathological combinations of constructs can lead to abysmally bad performance.

Consider a string of 25 as, a d, 4 as, and a c.

s = 'a' * 25 + 'd' + 'a' * 4 + 'c'
#=> "aaaaaaaaaaaaaaaaaaaaaaaaadaaaac"


The following patterns match instantly as you would expect:

/(b|a)/ =~ s #=> 0
/(b|a+)/ =~ s #=> 0
/(b|a+)*/ =~ s #=> 0


However, the following pattern takes appreciably longer:

/(b|a+)*c/ =~ s #=> 26


This happens because an atom in the regexp is quantified by both an immediate + and an enclosing * with nothing to differentiate which is in control of any particular character. The nondeterminism that results produces super-linear performance. (Consult Mastering Regular Expressions (3rd ed.), pp 222, by Jeffery Friedl, for an in-depth analysis). This particular case can be fixed by use of atomic grouping, which prevents the unnecessary backtracking:

(start = Time.now) && /(b|a+)*c/ =~ s && (Time.now - start)
   #=> 24.702736882
(start = Time.now) && /(?>b|a+)*c/ =~ s && (Time.now - start)
   #=> 0.000166571


A similar case is typified by the following example, which takes approximately 60 seconds to execute for me:

Match a string of 29 as against a pattern of 29 optional as followed by 29 mandatory as:

Regexp.new('a?' * 29 + 'a' * 29) =~ 'a' * 29


The 29 optional as match the string, but this prevents the 29 mandatory as that follow from matching. Ruby must then backtrack repeatedly so as to satisfy as many of the optional matches as it can while still matching the mandatory 29. It is plain to us that none of the optional matches can succeed, but this fact unfortunately eludes Ruby.

The best way to improve performance is to significantly reduce the amount of backtracking needed.  For this case, instead of individually matching 29 optional as, a range of optional as can be matched all at once with a{0,29}:

Regexp.new('a{0,29}' + 'a' * 29) =~ 'a' * 29


  


    
Raised when given an invalid regexp expression.

Regexp.new("?")


raises the exception:

RegexpError: target of repeat operator is not specified: /?/

  


    
Resolv is a thread-aware DNS resolver library written in Ruby.  Resolv can handle multiple DNS requests concurrently without blocking the entire Ruby interpreter.

See also resolv-replace.rb to replace the libc resolver with Resolv.

Resolv can look up various DNS resources using the DNS module directly.

Examples:

p Resolv.getaddress "www.ruby-lang.org"
p Resolv.getname "210.251.121.214"

Resolv::DNS.open do |dns|
  ress = dns.getresources "www.ruby-lang.org", Resolv::DNS::Resource::IN::A
  p ress.map(&:address)
  ress = dns.getresources "ruby-lang.org", Resolv::DNS::Resource::IN::MX
  p ress.map { |r| [r.exchange.to_s, r.preference] }
end


Bugs¶ ↑

NIS is not supported.

/etc/nsswitch.conf is not supported.


  


    
Resolv::DNS is a DNS stub resolver.

Information taken from the following places:

STD0013

RFC 1035

ftp.isi.edu/in-notes/iana/assignments/dns-parameters

etc.


  


    
Indicates no such domain was found.

  


    
Indicates some other unhandled resolver error was encountered.

  


    
Indicates that the DNS response was unable to be decoded.

  


    
Indicates that the DNS request was unable to be encoded.

  


    
A representation of a DNS name.

  


    
A DNS query abstract class.

  


    
Indicates a problem with the DNS request.

  


    
A DNS resource abstract class.

  


    
A Query type requesting any RR.

  


    
The canonical name for an alias.

  


    
Domain Name resource abstract class.

  


    
A generic resource abstract class.

  


    
Host Information resource.

  


    
IPv4 Address resource

  


    
An IPv6 address record.

  


    
SRV resource record defined in RFC 2782

These records identify the hostname and port that a service is available at.

  


    
Well Known Service resource.

  


    
Location resource

  


    
Mailing list or mailbox information.

  


    
Mail Exchanger resource.

  


    
An authoritative name server.

  


    
A Pointer to another DNS name.

  


    
Start Of Authority resource.

  


    
Unstructured text resource.

  


    
Resolv::Hosts is a hostname resolver that uses the system hosts file.

  


    
A Resolv::DNS IPv4 address.

  


    
A Resolv::DNS IPv6 address.

  


    
A Resolv::LOC::Alt

  


    
A Resolv::LOC::Coord

  


    
A Resolv::LOC::Size

  


    
Resolv::MDNS is a one-shot Multicast DNS (mDNS) resolver.  It blindly makes queries to the mDNS addresses without understanding anything about multicast ports.

Information taken form the following places:

RFC 6762


  


    
Indicates a failure to resolve a name or address.

  


    
Indicates a timeout resolving a name or address.

  


    
Documentation?

  


    
Raised when a hash-based tuple has an invalid key.

  


    
A NotifyTemplateEntry is returned by TupleSpace#notify and is notified of TupleSpace changes.  You may receive either your subscribed event or the 'close' event when iterating over notifications.

See TupleSpace#notify_event for valid notification types.

Example¶ ↑

ts = Rinda::TupleSpace.new
observer = ts.notify 'write', [nil]

Thread.start do
  observer.each { |t| p t }
end

3.times { |i| ts.write [i] }


Outputs:

['write', [0]]
['write', [1]]
['write', [2]]


  


    
Raised when trying to use a canceled tuple.

  


    
Raised when trying to use an expired tuple.

  


    
Rinda error base class

  


    
RingFinger is used by RingServer clients to discover the RingServer's TupleSpace.  Typically, all a client needs to do is call RingFinger.primary to retrieve the remote TupleSpace, which it can then begin using.

To find the first available remote TupleSpace:

Rinda::RingFinger.primary


To create a RingFinger that broadcasts to a custom list:

rf = Rinda::RingFinger.new  ['localhost', '192.0.2.1']
rf.primary


Rinda::RingFinger also understands multicast addresses and sets them up properly.  This allows you to run multiple RingServers on the same host:

rf = Rinda::RingFinger.new ['239.0.0.1']
rf.primary


You can set the hop count (or TTL) for multicast searches using multicast_hops.

If you use IPv6 multicast you may need to set both an address and the outbound interface index:

rf = Rinda::RingFinger.new ['ff02::1']
rf.multicast_interface = 1
rf.primary


At this time there is no easy way to get an interface index by name.

  


    
RingProvider uses a RingServer advertised TupleSpace as a name service. TupleSpace clients can register themselves with the remote TupleSpace and look up other provided services via the remote TupleSpace.

Services are registered with a tuple of the format [:name, klass, DRbObject, description].

  


    
A RingServer allows a Rinda::TupleSpace to be located via UDP broadcasts. Default service location uses the following steps:

A RingServer begins listening on the network broadcast UDP address.

A RingFinger sends a UDP packet containing the DRb URI where it will listen for a reply.

The RingServer receives the UDP packet and connects back to the provided DRb URI with the DRb service.


A RingServer requires a TupleSpace:

ts = Rinda::TupleSpace.new
rs = Rinda::RingServer.new


RingServer can also listen on multicast addresses for announcements.  This allows multiple RingServers to run on the same host.  To use network broadcast and multicast:

ts = Rinda::TupleSpace.new
rs = Rinda::RingServer.new ts, %w[Socket::INADDR_ANY, 239.0.0.1 ff02::1]


  


    
An SimpleRenewer allows a TupleSpace to check if a TupleEntry is still alive.

  


    
Templates are used to match tuples in Rinda.

  


    
A TemplateEntry is a Template together with expiry and cancellation data.

  


    
A tuple is the elementary object in Rinda programming. Tuples may be matched against templates if the tuple and the template are the same size.

  


    
TupleBag is an unordered collection of tuples. It is the basis of Tuplespace.

  


    
A TupleEntry is a Tuple (i.e. a possible entry in some Tuplespace) together with expiry and cancellation data.

  


    
The Tuplespace manages access to the tuples it contains, ensuring mutual exclusion requirements are met.

The sec option for the write, take, move, read and notify methods may either be a number of seconds or a Renewer object.

  


    
TupleSpaceProxy allows a remote Tuplespace to appear as local.

  


    
Documentation?

  


    
Ripper is a Ruby script parser.

You can get information from the parser with event-based style. Information such as abstract syntax trees or simple lexical analysis of the Ruby program.

Usage¶ ↑

Ripper provides an easy interface for parsing your program into a symbolic expression tree (or S-expression).

Understanding the output of the parser may come as a challenge, it's recommended you use PP to format the output for legibility.

require 'ripper'
require 'pp'

pp Ripper.sexp('def hello(world) "Hello, #{world}!"; end')
  #=> [:program,
       [[:def,
         [:@ident, "hello", [1, 4]],
         [:paren,
          [:params, [[:@ident, "world", [1, 10]]], nil, nil, nil, nil, nil, nil]],
         [:bodystmt,
          [[:string_literal,
            [:string_content,
             [:@tstring_content, "Hello, ", [1, 18]],
             [:string_embexpr, [[:var_ref, [:@ident, "world", [1, 27]]]]],
             [:@tstring_content, "!", [1, 33]]]]],
          nil,
          nil,
          nil]]]]

You can see in the example above, the expression starts with :program.

From here, a method definition at :def, followed by the method's identifier :@ident. After the method's identifier comes the parentheses :paren and the method parameters under :params.

Next is the method body, starting at :bodystmt (stmt meaning statement), which contains the full definition of the method.

In our case, we're simply returning a String, so next we have the :string_literal expression.

Within our :string_literal you'll notice two @tstring_content, this is the literal part for Hello,  and !. Between the two @tstring_content statements is a :string_embexpr, where embexpr is an embedded expression. Our expression consists of a local variable, or var_ref, with the identifier (@ident) of world.

Resources¶ ↑

Ruby Inside


Requirements¶ ↑

ruby 1.9 (support CVS HEAD only)

bison 1.28 or later (Other yaccs do not work)


License¶ ↑

Ruby License.

Minero Aoki

aamine@loveruby.net

i.loveruby.net


  


    
This class handles only scanner events, which are dispatched in the 'right' order (same with input).

  


    
The RubyVM module provides some access to Ruby internals. This module is for very limited purposes, such as debugging, prototyping, and research.  Normal users must not use it.

  


    
RubyVM::AbstractSyntaxTree::Node instances are created by parse methods in RubyVM::AbstractSyntaxTree.

  


    
The InstructionSequence class represents a compiled sequence of instructions for the Ruby Virtual Machine.

With it, you can get a handle to the instructions that make up a method or a proc, compile strings of Ruby code down to VM instructions, and disassemble instruction sequences to strings for easy inspection. It is mostly useful if you want to learn how the Ruby VM works, but it also lets you control various settings for the Ruby iseq compiler.

You can find the source for the VM instructions in insns.def in the Ruby source.

The instruction sequence results will almost certainly change as Ruby changes, so example output in this documentation may be different from what you see.

  


    
A generic error class raised when an invalid operation is attempted. Kernel#raise will raise a RuntimeError if no Exception class is specified.

raise "ouch"


raises the exception:

RuntimeError: ouch

  


    
SDBM provides a simple file-based key-value store, which can only store String keys and values.

Note that Ruby comes with the source code for SDBM, while the DBM and GDBM standard libraries rely on external libraries and headers.

Examples¶ ↑

Insert values:

require 'sdbm'

SDBM.open 'my_database' do |db|
  db['apple'] = 'fruit'
  db['pear'] = 'fruit'
  db['carrot'] = 'vegetable'
  db['tomato'] = 'vegetable'
end


Bulk update:

require 'sdbm'

SDBM.open 'my_database' do |db|
  db.update('peach' => 'fruit', 'tomato' => 'fruit')
end


Retrieve values:

require 'sdbm'

SDBM.open 'my_database' do |db|
  db.each do |key, value|
    puts "Key: #{key}, Value: #{value}"
  end
end


Outputs:

Key: apple, Value: fruit
Key: pear, Value: fruit
Key: carrot, Value: vegetable
Key: peach, Value: fruit
Key: tomato, Value: fruit

  


    
Exception class used to return errors from the sdbm library.

  


    
SOCKS is an Internet protocol that routes packets between a client and a server through a proxy server.  SOCKS5, if supported, additionally provides authentication so only authorized users may access a server.

  


    
ScriptError is the superclass for errors raised when a script can not be executed because of a LoadError, NotImplementedError or a SyntaxError. Note these type of ScriptErrors are not StandardError and will not be rescued unless it is specified explicitly (or its ancestor Exception).

  


    
Raised when attempting a potential unsafe operation, typically when the $SAFE level is raised above 0.

foo = "bar"
proc = Proc.new do
  $SAFE = 3
  foo.untaint
end
proc.call


raises the exception:

SecurityError: Insecure: Insecure operation `untaint' at level 3

  


    
Set implements a collection of unordered values with no duplicates. This is a hybrid of Array's intuitive inter-operation facilities and Hash's fast lookup.

Set is easy to use with Enumerable objects (implementing each). Most of the initializer methods and binary operators accept generic Enumerable objects besides sets and arrays.  An Enumerable object can be converted to Set using the to_set method.

Set uses Hash as storage, so you must note the following points:

Equality of elements is determined according to Object#eql? and Object#hash.  Use Set#compare_by_identity to make a set compare its elements by their identity.

Set assumes that the identity of each element does not change while it is stored.  Modifying an element of a set will render the set to an unreliable state.

When a string is to be stored, a frozen copy of the string is stored instead unless the original string is already frozen.


Comparison¶ ↑

The comparison operators <, >, <=, and >= are implemented as shorthand for the {proper_,}{subset?,superset?} methods.  However, the <=> operator is intentionally left out because not every pair of sets is comparable ({x, y} vs. {x, z} for example).

Example¶ ↑

require 'set'
s1 = Set[1, 2]                        #=> #<Set: {1, 2}>
s2 = [1, 2].to_set                    #=> #<Set: {1, 2}>
s1 == s2                              #=> true
s1.add("foo")                         #=> #<Set: {1, 2, "foo"}>
s1.merge([2, 6])                      #=> #<Set: {1, 2, "foo", 6}>
s1.subset?(s2)                        #=> false
s2.subset?(s1)                        #=> true


Contact¶ ↑

- Akinori MUSHA <knu@iDaemons.org> (current maintainer)

  


    
Shell implements an idiomatic Ruby interface for common UNIX shell commands.

It provides users the ability to execute commands with filters and pipes, like sh/csh by using native facilities of Ruby.

Examples¶ ↑

Temp file creation¶ ↑

In this example we will create three tmpFile's in three different folders under the /tmp directory.

sh = Shell.cd("/tmp") # Change to the /tmp directory
sh.mkdir "shell-test-1" unless sh.exists?("shell-test-1")
# make the 'shell-test-1' directory if it doesn't already exist
sh.cd("shell-test-1") # Change to the /tmp/shell-test-1 directory
for dir in ["dir1", "dir3", "dir5"]
  if !sh.exists?(dir)
    sh.mkdir dir # make dir if it doesn't already exist
    sh.cd(dir) do
      # change to the `dir` directory
      f = sh.open("tmpFile", "w") # open a new file in write mode
      f.print "TEST\n"            # write to the file
      f.close                     # close the file handler
    end
    print sh.pwd                  # output the process working directory
  end
end


Temp file creation with self¶ ↑

This example is identical to the first, except we're using CommandProcessor#transact.

CommandProcessor#transact executes the given block against self, in this case sh; our Shell object. Within the block we can substitute sh.cd to cd, because the scope within the block uses sh already.

sh = Shell.cd("/tmp")
sh.transact do
  mkdir "shell-test-1" unless exists?("shell-test-1")
  cd("shell-test-1")
  for dir in ["dir1", "dir3", "dir5"]
    if !exists?(dir)
      mkdir dir
      cd(dir) do
        f = open("tmpFile", "w")
        f.print "TEST\n"
        f.close
      end
      print pwd
    end
  end
end


Pipe /etc/printcap into a file¶ ↑

In this example we will read the operating system file /etc/printcap, generated by cupsd, and then output it to a new file relative to the pwd of sh.

sh = Shell.new
sh.cat("/etc/printcap") | sh.tee("tee1") > "tee2"
(sh.cat < "/etc/printcap") | sh.tee("tee11") > "tee12"
sh.cat("/etc/printcap") | sh.tee("tee1") >> "tee2"
(sh.cat < "/etc/printcap") | sh.tee("tee11") >> "tee12"


  


    
In order to execute a command on your OS, you need to define it as a Shell method.

Alternatively, you can execute any command via Shell::CommandProcessor#system even if it is not defined.

  


    
Any result of command execution is a Filter.

This class includes Enumerable, therefore a Filter object can use all Enumerable facilities.

  


    
Raised when a signal is received.

begin
  Process.kill('HUP',Process.pid)
  sleep # wait for receiver to handle signal sent by Process.kill
rescue SignalException => e
  puts "received Exception #{e}"
end


produces:

received Exception SIGHUP


  


    
A concrete implementation of Delegator, this class provides the means to delegate all supported method calls to the object passed into the constructor and even to change the object being delegated to at a later time with #__setobj__.

class User
  def born_on
    Date.new(1989, 9, 10)
  end
end

class UserDecorator < SimpleDelegator
  def birth_year
    born_on.year
  end
end

decorated_user = UserDecorator.new(User.new)
decorated_user.birth_year  #=> 1989
decorated_user.__getobj__  #=> #<User: ...>


A SimpleDelegator instance can take advantage of the fact that SimpleDelegator is a subclass of Delegator to call super to have methods called on the object being delegated to.

class SuperArray < SimpleDelegator
  def [](*args)
    super + 1
  end
end

SuperArray.new([1])[0]  #=> 2


Here's a simple example that takes advantage of the fact that SimpleDelegator's delegation object can be changed at any time.

class Stats
  def initialize
    @source = SimpleDelegator.new([])
  end

  def stats(records)
    @source.__setobj__(records)

    "Elements:  #{@source.size}\n" +
    " Non-Nil:  #{@source.compact.size}\n" +
    "  Unique:  #{@source.uniq.size}\n"
  end
end

s = Stats.new
puts s.stats(%w{James Edward Gray II})
puts
puts s.stats([1, 2, 3, nil, 4, 5, 1, 2])


Prints:

Elements:  4
 Non-Nil:  4
  Unique:  4

Elements:  8
 Non-Nil:  7
  Unique:  6

  


    
This class represents queues of specified size capacity.  The push operation may be blocked if the capacity is full.

See Queue for an example of how a SizedQueue works.

  


    
Class Socket provides access to the underlying operating system socket implementations.  It can be used to provide more operating system specific functionality than the protocol-specific socket classes.

The constants defined under Socket::Constants are also defined under Socket.  For example, Socket::AF_INET is usable as well as Socket::Constants::AF_INET.  See Socket::Constants for the list of constants.

What's a socket?¶ ↑

Sockets are endpoints of a bidirectional communication channel. Sockets can communicate within a process, between processes on the same machine or between different machines.  There are many types of socket: TCPSocket, UDPSocket or UNIXSocket for example.

Sockets have their own vocabulary:

domain: The family of protocols:

Socket::PF_INET

Socket::PF_INET6

Socket::PF_UNIX

etc.


type: The type of communications between the two endpoints, typically

Socket::SOCK_STREAM

Socket::SOCK_DGRAM.


protocol: Typically zero. This may be used to identify a variant of a protocol.

hostname: The identifier of a network interface:

a string (hostname, IPv4 or IPv6 address or broadcast which specifies a broadcast address)

a zero-length string which specifies INADDR_ANY

an integer (interpreted as binary address in host byte order).


Quick start¶ ↑

Many of the classes, such as TCPSocket, UDPSocket or UNIXSocket, ease the use of sockets comparatively to the equivalent C programming interface.

Let's create an internet socket using the IPv4 protocol in a C-like manner:

require 'socket'

s = Socket.new Socket::AF_INET, Socket::SOCK_STREAM
s.connect Socket.pack_sockaddr_in(80, 'example.com')


You could also use the TCPSocket class:

s = TCPSocket.new 'example.com', 80


A simple server might look like this:

require 'socket'

server = TCPServer.new 2000 # Server bound to port 2000

loop do
  client = server.accept    # Wait for a client to connect
  client.puts "Hello !"
  client.puts "Time is #{Time.now}"
  client.close
end


A simple client may look like this:

require 'socket'

s = TCPSocket.new 'localhost', 2000

while line = s.gets # Read lines from socket
  puts line         # and print them
end

s.close             # close socket when done


Exception Handling¶ ↑

Ruby's Socket implementation raises exceptions based on the error generated by the system dependent implementation.  This is why the methods are documented in a way that isolate Unix-based system exceptions from Windows based exceptions. If more information on a particular exception is needed, please refer to the Unix manual pages or the Windows WinSock reference.

Convenience methods¶ ↑

Although the general way to create socket is Socket.new, there are several methods of socket creation for most cases.
TCP client socket

Socket.tcp, TCPSocket.open
TCP server socket

Socket.tcp_server_loop, TCPServer.open
UNIX client socket

Socket.unix, UNIXSocket.open
UNIX server socket

Socket.unix_server_loop, UNIXServer.open


Documentation by¶ ↑

Zach Dennis

Sam Roberts

Programming Ruby from The Pragmatic Bookshelf.


Much material in this documentation is taken with permission from Programming Ruby from The Pragmatic Bookshelf.

  


    
Socket::AncillaryData represents the ancillary data (control information) used by sendmsg and recvmsg system call.  It contains socket family, control message (cmsg) level, cmsg type and cmsg data.

  


    
Socket::Ifaddr represents a result of getifaddrs() function.

  


    
Socket::Option represents a socket option used by BasicSocket#getsockopt and BasicSocket#setsockopt.  A socket option contains the socket family, protocol level, option name optname and option value data.

  


    
UDP/IP address information used by Socket.udp_server_loop.

  


    
SocketError is the error class for socket.

  


    
SortedSet implements a Set that guarantees that its elements are yielded in sorted order (according to the return values of their #<=> methods) when iterating over them.

All elements that are added to a SortedSet must respond to the <=> method for comparison.

Also, all elements must be mutually comparable: el1 <=> el2 must not return nil for any elements el1 and el2, else an ArgumentError will be raised when iterating over the SortedSet.

Example¶ ↑

require "set"

set = SortedSet.new([2, 1, 5, 6, 4, 5, 3, 3, 3])
ary = []

set.each do |obj|
  ary << obj
end

p ary # => [1, 2, 3, 4, 5, 6]

set2 = SortedSet.new([1, 2, "3"])
set2.each { |obj| } # => raises ArgumentError: comparison of Fixnum with String failed


  


    
The most standard error types are subclasses of StandardError. A rescue clause without an explicit Exception class will rescue all StandardErrors (and only those).

def foo
  raise "Oups"
end
foo rescue "Hello"   #=> "Hello"


On the other hand:

require 'does/not/exist' rescue "Hi"


raises the exception:

LoadError: no such file to load -- does/not/exist

  


    
Raised to stop the iteration, in particular by Enumerator#next. It is rescued by Kernel#loop.

loop do
  puts "Hello"
  raise StopIteration
  puts "World"
end
puts "Done!"


produces:

Hello
Done!


  


    
A String object holds and manipulates an arbitrary sequence of bytes, typically representing characters. String objects may be created using String::new or as literals.

Because of aliasing issues, users of strings should be aware of the methods that modify the contents of a String object.  Typically, methods with names ending in “!'' modify their receiver, while those without a “!'' return a new String.  However, there are exceptions, such as String#[]=.

  


    
Pseudo I/O on String object.

Commonly used to simulate `$stdio` or `$stderr`

Examples¶ ↑

require 'stringio'

io = StringIO.new
io.puts "Hello World"
io.string #=> "Hello World\n"


  


    
StringScanner provides for lexical scanning operations on a String.  Here is an example of its usage:

s = StringScanner.new('This is an example string')
s.eos?               # -> false

p s.scan(/\w+/)      # -> "This"
p s.scan(/\w+/)      # -> nil
p s.scan(/\s+/)      # -> " "
p s.scan(/\s+/)      # -> nil
p s.scan(/\w+/)      # -> "is"
s.eos?               # -> false

p s.scan(/\s+/)      # -> " "
p s.scan(/\w+/)      # -> "an"
p s.scan(/\s+/)      # -> " "
p s.scan(/\w+/)      # -> "example"
p s.scan(/\s+/)      # -> " "
p s.scan(/\w+/)      # -> "string"
s.eos?               # -> true

p s.scan(/\s+/)      # -> nil
p s.scan(/\w+/)      # -> nil


Scanning a string means remembering the position of a scan pointer, which is just an index.  The point of scanning is to move forward a bit at a time, so matches are sought after the scan pointer; usually immediately after it.

Given the string “test string”, here are the pertinent scan pointer positions:

  t e s t   s t r i n g
0 1 2 ...             1
                      0

When you scan for a pattern (a regular expression), the match must occur at the character after the scan pointer.  If you use scan_until, then the match can occur anywhere after the scan pointer.  In both cases, the scan pointer moves just beyond the last character of the match, ready to scan again from the next character onwards.  This is demonstrated by the example above.

Method Categories¶ ↑

There are other methods besides the plain scanners.  You can look ahead in the string without actually scanning.  You can access the most recent match. You can modify the string being scanned, reset or terminate the scanner, find out or change the position of the scan pointer, skip ahead, and so on.

Advancing the Scan Pointer¶ ↑

getch

get_byte

scan

scan_until

skip

skip_until


Looking Ahead¶ ↑

check

check_until

exist?

match?

peek


Finding Where we Are¶ ↑

beginning_of_line? (#bol?)

eos?

rest?

rest_size

pos


Setting Where we Are¶ ↑

reset

terminate

pos=


Match Data¶ ↑

matched

matched?

matched_size



pre_match

post_match


Miscellaneous¶ ↑

<<

concat

string

string=

unscan


There are aliases to several of the methods.

  


    
A Struct is a convenient way to bundle a number of attributes together, using accessor methods, without having to write an explicit class.

The Struct class generates new subclasses that hold a set of members and their values.  For each member a reader and writer method is created similar to Module#attr_accessor.

Customer = Struct.new(:name, :address) do
  def greeting
    "Hello #{name}!"
  end
end

dave = Customer.new("Dave", "123 Main")
dave.name     #=> "Dave"
dave.greeting #=> "Hello Dave!"


See Struct::new for further examples of creating struct subclasses and instances.

In the method descriptions that follow, a “member” parameter refers to a struct member which is either a quoted string ("name") or a Symbol (:name).

  


    
Symbol objects represent names and some strings inside the Ruby interpreter. They are generated using the :name and :"string" literals syntax, and by the various to_sym methods. The same Symbol object will be created for a given name or string for the duration of a program's execution, regardless of the context or meaning of that name. Thus if Fred is a constant in one context, a method in another, and a class in a third, the Symbol :Fred will be the same object in all three contexts.

module One
  class Fred
  end
  $f1 = :Fred
end
module Two
  Fred = 1
  $f2 = :Fred
end
def Fred()
end
$f3 = :Fred
$f1.object_id   #=> 2514190
$f2.object_id   #=> 2514190
$f3.object_id   #=> 2514190


  


    
A class that provides two-phase lock with a counter.  See Sync_m for details.

  


    
exceptions

  


    
A class that provides two-phase lock with a counter.  See Sync_m for details.

  


    
Raised when encountering Ruby code with an invalid syntax.

eval("1+1=2")


raises the exception:

SyntaxError: (eval):1: syntax error, unexpected '=', expecting $end

  


    
Syslog::Logger is a Logger work-alike that logs via syslog instead of to a file.  You can use Syslog::Logger to aggregate logs between multiple machines.

By default, Syslog::Logger uses the program name 'ruby', but this can be changed via the first argument to Syslog::Logger.new.

NOTE! You can only set the Syslog::Logger program name when you initialize Syslog::Logger for the first time.  This is a limitation of the way Syslog::Logger uses syslog (and in some ways, a limitation of the way syslog(3) works).  Attempts to change Syslog::Logger's program name after the first initialization will be ignored.

Example¶ ↑

The following will log to syslogd on your local machine:

require 'syslog/logger'

log = Syslog::Logger.new 'my_program'
log.info 'this line will be logged via syslog(3)'


Also the facility may be set to specify the facility level which will be used:

log.info 'this line will be logged using Syslog default facility level'

log_local1 = Syslog::Logger.new 'my_program', Syslog::LOG_LOCAL1
log_local1.info 'this line will be logged using local1 facility level'


You may need to perform some syslog.conf setup first.  For a BSD machine add the following lines to /etc/syslog.conf:

!my_program
*.*                                             /var/log/my_program.log

Then touch /var/log/my_program.log and signal syslogd with a HUP (killall -HUP syslogd, on FreeBSD).

If you wish to have logs automatically roll over and archive, see the newsyslog.conf(5) and newsyslog(8) man pages.

  


    
Default formatter for log messages.

  


    
SystemCallError is the base class for all low-level platform-dependent errors.

The errors available on the current platform are subclasses of SystemCallError and are defined in the Errno module.

File.open("does/not/exist")


raises the exception:

Errno::ENOENT: No such file or directory - does/not/exist

  


    
Raised by exit to initiate the termination of the script.

  


    
Raised in case of a stack overflow.

def me_myself_and_i
  me_myself_and_i
end
me_myself_and_i


raises the exception:

SystemStackError: stack level too deep

  


    
TCPServer represents a TCP/IP server socket.

A simple TCP server may look like:

require 'socket'

server = TCPServer.new 2000 # Server bind to port 2000
loop do
  client = server.accept    # Wait for a client to connect
  client.puts "Hello !"
  client.puts "Time is #{Time.now}"
  client.close
end


A more usable server (serving multiple clients):

require 'socket'

server = TCPServer.new 2000
loop do
  Thread.start(server.accept) do |client|
    client.puts "Hello !"
    client.puts "Time is #{Time.now}"
    client.close
  end
end


  


    
TCPSocket represents a TCP/IP client socket.

A simple client may look like:

require 'socket'

s = TCPSocket.new 'localhost', 2000

while line = s.gets # Read lines from socket
  puts line         # and print them
end

s.close             # close socket when done


  


    
A StringIO duck-typed class that uses Tempfile instead of String as the backing store.

This is available when rubygems/test_utilities is required.

  


    
A utility class for managing temporary files. When you create a Tempfile object, it will create a temporary file with a unique filename. A Tempfile objects behaves just like a File object, and you can perform all the usual file operations on it: reading data, writing data, changing its permissions, etc. So although this class does not explicitly document all instance methods supported by File, you can in fact call any File instance method on a Tempfile object.

Synopsis¶ ↑

require 'tempfile'

file = Tempfile.new('foo')
file.path      # => A unique filename in the OS's temp directory,
               #    e.g.: "/tmp/foo.24722.0"
               #    This filename contains 'foo' in its basename.
file.write("hello world")
file.rewind
file.read      # => "hello world"
file.close
file.unlink    # deletes the temp file


Good practices¶ ↑

Explicit close¶ ↑

When a Tempfile object is garbage collected, or when the Ruby interpreter exits, its associated temporary file is automatically deleted. This means that's it's unnecessary to explicitly delete a Tempfile after use, though it's good practice to do so: not explicitly deleting unused Tempfiles can potentially leave behind large amounts of tempfiles on the filesystem until they're garbage collected. The existence of these temp files can make it harder to determine a new Tempfile filename.

Therefore, one should always call unlink or close in an ensure block, like this:

file = Tempfile.new('foo')
begin
   # ...do something with file...
ensure
   file.close
   file.unlink   # deletes the temp file
end


Unlink after creation¶ ↑

On POSIX systems, it's possible to unlink a file right after creating it, and before closing it. This removes the filesystem entry without closing the file handle, so it ensures that only the processes that already had the file handle open can access the file's contents. It's strongly recommended that you do this if you do not want any other processes to be able to read from or write to the Tempfile, and you do not need to know the Tempfile's filename either.

For example, a practical use case for unlink-after-creation would be this: you need a large byte buffer that's too large to comfortably fit in RAM, e.g. when you're writing a web server and you want to buffer the client's file upload data.

Please refer to unlink for more information and a code example.

Minor notes¶ ↑

Tempfile's filename picking method is both thread-safe and inter-process-safe: it guarantees that no other threads or processes will pick the same filename.

Tempfile itself however may not be entirely thread-safe. If you access the same Tempfile object from multiple threads then you should protect it with a mutex.

  


    
This class watches for termination of multiple threads.  Basic functionality (wait until specified threads have terminated) can be accessed through the class method ThreadsWait::all_waits.  Finer control can be gained using instance methods.

Example:

ThreadsWait.all_waits(thr1, thr2, ...) do |t|
  STDERR.puts "Thread #{t} has terminated."
end

th = ThreadsWait.new(thread1,...)
th.next_wait # next one to be done

  


    
Threads are the Ruby implementation for a concurrent programming model.

Programs that require multiple threads of execution are a perfect candidate for Ruby's Thread class.

For example, we can create a new thread separate from the main thread's execution using ::new.

thr = Thread.new { puts "Whats the big deal" }


Then we are able to pause the execution of the main thread and allow our new thread to finish, using join:

thr.join #=> "Whats the big deal"


If we don't call thr.join before the main thread terminates, then all other threads including thr will be killed.

Alternatively, you can use an array for handling multiple threads at once, like in the following example:

threads = []
threads << Thread.new { puts "Whats the big deal" }
threads << Thread.new { 3.times { puts "Threads are fun!" } }


After creating a few threads we wait for them all to finish consecutively.

threads.each { |thr| thr.join }


Thread initialization¶ ↑

In order to create new threads, Ruby provides ::new, ::start, and ::fork. A block must be provided with each of these methods, otherwise a ThreadError will be raised.

When subclassing the Thread class, the initialize method of your subclass will be ignored by ::start and ::fork. Otherwise, be sure to call super in your initialize method.

Thread termination¶ ↑

For terminating threads, Ruby provides a variety of ways to do this.

The class method ::kill, is meant to exit a given thread:

thr = Thread.new { ... }
Thread.kill(thr) # sends exit() to thr

Alternatively, you can use the instance method exit, or any of its aliases kill or terminate.

thr.exit


Thread status¶ ↑

Ruby provides a few instance methods for querying the state of a given thread. To get a string with the current thread's state use status

thr = Thread.new { sleep }
thr.status # => "sleep"
thr.exit
thr.status # => false


You can also use alive? to tell if the thread is running or sleeping, and stop? if the thread is dead or sleeping.

Thread variables and scope¶ ↑

Since threads are created with blocks, the same rules apply to other Ruby blocks for variable scope. Any local variables created within this block are accessible to only this thread.

Fiber-local vs. Thread-local¶ ↑

Each fiber has its own bucket for Thread#[] storage. When you set a new fiber-local it is only accessible within this Fiber. To illustrate:

Thread.new {
  Thread.current[:foo] = "bar"
  Fiber.new {
    p Thread.current[:foo] # => nil
  }.resume
}.join


This example uses [] for getting and []= for setting fiber-locals, you can also use keys to list the fiber-locals for a given thread and key? to check if a fiber-local exists.

When it comes to thread-locals, they are accessible within the entire scope of the thread. Given the following example:

Thread.new{
  Thread.current.thread_variable_set(:foo, 1)
  p Thread.current.thread_variable_get(:foo) # => 1
  Fiber.new{
    Thread.current.thread_variable_set(:foo, 2)
    p Thread.current.thread_variable_get(:foo) # => 2
  }.resume
  p Thread.current.thread_variable_get(:foo)   # => 2
}.join


You can see that the thread-local :foo carried over into the fiber and was changed to 2 by the end of the thread.

This example makes use of thread_variable_set to create new thread-locals, and thread_variable_get to reference them.

There is also thread_variables to list all thread-locals, and thread_variable? to check if a given thread-local exists.

Exception handling¶ ↑

Any thread can raise an exception using the raise instance method, which operates similarly to Kernel#raise.

However, it's important to note that an exception that occurs in any thread except the main thread depends on abort_on_exception. This option is false by default, meaning that any unhandled exception will cause the thread to terminate silently when waited on by either join or value. You can change this default by either abort_on_exception= true or setting $DEBUG to true.

With the addition of the class method ::handle_interrupt, you can now handle exceptions asynchronously with threads.

Scheduling¶ ↑

Ruby provides a few ways to support scheduling threads in your program.

The first way is by using the class method ::stop, to put the current running thread to sleep and schedule the execution of another thread.

Once a thread is asleep, you can use the instance method wakeup to mark your thread as eligible for scheduling.

You can also try ::pass, which attempts to pass execution to another thread but is dependent on the OS whether a running thread will switch or not. The same goes for priority, which lets you hint to the thread scheduler which threads you want to take precedence when passing execution. This method is also dependent on the OS and may be ignored on some platforms.

  


    
An object representation of a stack frame, initialized by Kernel#caller_locations.

For example:

# caller_locations.rb
def a(skip)
  caller_locations(skip)
end
def b(skip)
  a(skip)
end
def c(skip)
  b(skip)
end

c(0..2).map do |call|
  puts call.to_s
end


Running ruby caller_locations.rb will produce:

caller_locations.rb:2:in `a'
caller_locations.rb:5:in `b'
caller_locations.rb:8:in `c'

Here's another example with a slightly different result:

# foo.rb
class Foo
  attr_accessor :locations
  def initialize(skip)
    @locations = caller_locations(skip)
  end
end

Foo.new(0..2).locations.map do |call|
  puts call.to_s
end


Now run ruby foo.rb and you should see:

init.rb:4:in `initialize'
init.rb:8:in `new'
init.rb:8:in `<main>'

  


    
Raised when an invalid operation is attempted on a thread.

For example, when no other thread has been started:

Thread.stop


This will raises the following exception:

ThreadError: stopping only thread
note: use sleep to stop forever

  


    
ThreadGroup provides a means of keeping track of a number of threads as a group.

A given Thread object can only belong to one ThreadGroup at a time; adding a thread to a new group will remove it from any previous group.

Newly created threads belong to the same group as the thread from which they were created.

  


    
This class watches for termination of multiple threads.  Basic functionality (wait until specified threads have terminated) can be accessed through the class method ThreadsWait::all_waits.  Finer control can be gained using instance methods.

Example:

ThreadsWait.all_waits(thr1, thr2, ...) do |t|
  STDERR.puts "Thread #{t} has terminated."
end

th = ThreadsWait.new(thread1,...)
th.next_wait # next one to be done

  


    
Time is an abstraction of dates and times. Time is stored internally as the number of seconds with fraction since the Epoch, January 1, 1970 00:00 UTC. Also see the library module Date. The Time class treats GMT (Greenwich Mean Time) and UTC (Coordinated Universal Time) as equivalent. GMT is the older way of referring to these baseline times but persists in the names of calls on POSIX systems.

All times may have fraction. Be aware of this fact when comparing times with each other – times that are apparently equal when displayed may be different when compared.

Since Ruby 1.9.2, Time implementation uses a signed 63 bit integer, Bignum or Rational. The integer is a number of nanoseconds since the Epoch which can represent 1823-11-12 to 2116-02-20. When Bignum or Rational is used (before 1823, after 2116, under nanosecond), Time works slower as when integer is used.

Examples¶ ↑

All of these examples were done using the EST timezone which is GMT-5.

Creating a new Time instance¶ ↑

You can create a new instance of Time with Time::new. This will use the current system time. Time::now is an alias for this. You can also pass parts of the time to Time::new such as year, month, minute, etc. When you want to construct a time this way you must pass at least a year. If you pass the year with nothing else time will default to January 1 of that year at 00:00:00 with the current system timezone. Here are some examples:

Time.new(2002)         #=> 2002-01-01 00:00:00 -0500
Time.new(2002, 10)     #=> 2002-10-01 00:00:00 -0500
Time.new(2002, 10, 31) #=> 2002-10-31 00:00:00 -0500


You can pass a UTC offset:

Time.new(2002, 10, 31, 2, 2, 2, "+02:00") #=> 2002-10-31 02:02:02 +0200


Or a timezone object:

tz = timezone("Europe/Athens") # Eastern European Time, UTC+2
Time.new(2002, 10, 31, 2, 2, 2, tz) #=> 2002-10-31 02:02:02 +0200


You can also use Time::gm, Time::local and Time::utc to infer GMT, local and UTC timezones instead of using the current system setting.

You can also create a new time using Time::at which takes the number of seconds (or fraction of seconds) since the Unix Epoch.

Time.at(628232400) #=> 1989-11-28 00:00:00 -0500


Working with an instance of Time¶ ↑

Once you have an instance of Time there is a multitude of things you can do with it. Below are some examples. For all of the following examples, we will work on the assumption that you have done the following:

t = Time.new(1993, 02, 24, 12, 0, 0, "+09:00")


Was that a monday?

t.monday? #=> false


What year was that again?

t.year #=> 1993


Was it daylight savings at the time?

t.dst? #=> false


What's the day a year later?

t + (60*60*24*365) #=> 1994-02-24 12:00:00 +0900


How many seconds was that since the Unix Epoch?

t.to_i #=> 730522800


You can also do standard functions like compare two times.

t1 = Time.new(2010)
t2 = Time.new(2011)

t1 == t2 #=> false
t1 == t1 #=> true
t1 <  t2 #=> true
t1 >  t2 #=> false

Time.new(2010,10,31).between?(t1, t2) #=> true


Timezone argument¶ ↑

A timezone argument must have local_to_utc and utc_to_local methods, and may have name and abbr methods.

The local_to_utc method should convert a Time-like object from the timezone to UTC, and utc_to_local is the opposite.  The result also should be a Time or Time-like object (not necessary to be the same class).  The zone of the result is just ignored. Time-like argument to these methods is similar to a Time object in UTC without sub-second; it has attribute readers for the parts, e.g. year, month, and so on, and epoch time readers, to_i.  The sub-second attributes are fixed as 0, and utc_offset, zone, isdst, and their aliases are same as a Time object in UTC. Also to_time, +, and - methods are defined.

The name method is used for marshaling. If this method is not defined on a timezone object, Time objects using that timezone object can not be dumped by Marshal.

The abbr method is used by '%Z' in strftime.

Auto conversion to Timezone¶ ↑

At loading marshaled data, a timezone name will be converted to a timezone object by find_timezone class method, if the method is defined.

Similary, that class method will be called when a timezone argument does not have the necessary methods mentioned above.

  


    
Raised by Timeout.timeout when the block times out.

  


    
Raised by Timeout.timeout when the block times out.

  


    
A class that provides the functionality of Kernel#set_trace_func in a nice Object-Oriented API.

Example¶ ↑

We can use TracePoint to gather information specifically for exceptions:

trace = TracePoint.new(:raise) do |tp|
    p [tp.lineno, tp.event, tp.raised_exception]
end
#=> #<TracePoint:disabled>

trace.enable
#=> false

0 / 0
#=> [5, :raise, #<ZeroDivisionError: divided by 0>]


Events¶ ↑

If you don't specify the type of events you want to listen for, TracePoint will include all available events.

Note do not depend on current event set, as this list is subject to change. Instead, it is recommended you specify the type of events you want to use.

To filter what is traced, you can pass any of the following as events:
:line

execute code on a new line
:class

start a class or module definition
:end

finish a class or module definition
:call

call a Ruby method
:return

return from a Ruby method
:c_call

call a C-language routine
:c_return

return from a C-language routine
:raise

raise an exception
:b_call

event hook at block entry
:b_return

event hook at block ending
:thread_begin

event hook at thread beginning
:thread_end

event hook at thread ending
:fiber_switch

event hook at fiber switch


  


    
Outputs a source level execution trace of a Ruby program.

It does this by registering an event handler with Kernel#set_trace_func for processing incoming events.  It also provides methods for filtering unwanted trace output (see Tracer.add_filter, Tracer.on, and Tracer.off).

Example¶ ↑

Consider the following Ruby script

class A
  def square(a)
    return a*a
  end
end

a = A.new
a.square(5)


Running the above script using ruby -r tracer example.rb will output the following trace to STDOUT (Note you can also explicitly require 'tracer')

#0:<internal:lib/rubygems/custom_require>:38:Kernel:<: -
#0:example.rb:3::-: class A
#0:example.rb:3::C: class A
#0:example.rb:4::-:   def square(a)
#0:example.rb:7::E: end
#0:example.rb:9::-: a = A.new
#0:example.rb:10::-: a.square(5)
#0:example.rb:4:A:>:   def square(a)
#0:example.rb:5:A:-:     return a*a
#0:example.rb:6:A:<:   end
 |  |         | |  |
 |  |         | |   ---------------------+ event
 |  |         |  ------------------------+ class
 |  |          --------------------------+ line
 |   ------------------------------------+ filename
  ---------------------------------------+ thread

Symbol table used for displaying incoming events:
+}+

call a C-language routine
+{+

return from a C-language routine
+>+

call a Ruby method
C

start a class or module definition
E

finish a class or module definition
-

execute code on a new line
+^+

raise an exception
+<+

return from a Ruby method


Copyright¶ ↑

by Keiju ISHITSUKA(keiju@ishitsuka.com)

  


    
The global value true is the only instance of class TrueClass and represents a logically true value in boolean expressions. The class provides operators allowing true to be used in logical expressions.

  


    
Raised when encountering an object that is not of the expected type.

[1, 2, 3].first("two")


raises the exception:

TypeError: no implicit conversion of String into Integer

  


    
UDPSocket represents a UDP/IP socket.

  


    
UNIXServer represents a UNIX domain stream server socket.

  


    
UNIXSocket represents a UNIX domain stream client socket.

  


    
URI is valid, bad usage is not.

  


    
Base class for all URI exceptions.

  


    
FTP URI syntax is defined by RFC1738 section 3.2.

This class will be redesigned because of difference of implementations; the structure of its path. draft-hoffman-ftp-uri-04 is a draft but it is a good summary about the de facto spec. tools.ietf.org/html/draft-hoffman-ftp-uri-04

  


    
The “file” URI is defined by RFC8089.

  


    
Base class for all URI classes. Implements generic URI syntax as per RFC 2396.

  


    
The syntax of HTTP URIs is defined in RFC1738 section 3.3.

Note that the Ruby URI library allows HTTP URLs containing usernames and passwords. This is not legal as per the RFC, but used to be supported in Internet Explorer 5 and 6, before the MS04-004 security update. See <URL:support.microsoft.com/kb/834489>.

  


    
The default port for HTTPS URIs is 443, and the scheme is 'https:' rather than 'http:'. Other than that, HTTPS URIs are identical to HTTP URIs; see URI::HTTP.

  


    
Not a URI component.

  


    
Not a URI.

  


    
LDAP URI SCHEMA (described in RFC2255).

  


    
The default port for LDAPS URIs is 636, and the scheme is 'ldaps:' rather than 'ldap:'. Other than that, LDAPS URIs are identical to LDAP URIs; see URI::LDAP.

  


    
RFC6068, the mailto URL scheme.

  


    
Class that parses String's into URI's.

It contains a Hash set of patterns and Regexp's that match and validate.

  


    
Class that parses String's into URI's.

It contains a Hash set of patterns and Regexp's that match and validate.

  


    
Ruby supports two forms of objectified methods. Class Method is used to represent methods that are associated with a particular object: these method objects are bound to that object. Bound method objects for an object can be created using Object#method.

Ruby also supports unbound methods; methods objects that are not associated with a particular object. These can be created either by calling Module#instance_method or by calling unbind on a bound method object. The result of both of these is an UnboundMethod object.

Unbound methods can only be called after they are bound to an object. That object must be a kind_of? the method's original class.

class Square
  def area
    @side * @side
  end
  def initialize(side)
    @side = side
  end
end

area_un = Square.instance_method(:area)

s = Square.new(12)
area = area_un.bind(s)
area.call   #=> 144


Unbound methods are a reference to the method at the time it was objectified: subsequent changes to the underlying class will not affect the unbound method.

class Test
  def test
    :original
  end
end
um = Test.instance_method(:test)
class Test
  def test
    :modified
  end
end
t = Test.new
t.test            #=> :modified
um.bind(t).call   #=> :original


  


    
Raised when throw is called with a tag which does not have corresponding catch block.

throw "foo", "bar"


raises the exception:

UncaughtThrowError: uncaught throw "foo"

  


    
The Vector class represents a mathematical vector, which is useful in its own right, and also constitutes a row or column of a Matrix.

Method Catalogue¶ ↑

To create a Vector:

Vector.[](*array)

Vector.elements(array, copy = true)

Vector.basis(size: n, index: k)

Vector.zero(n)


To access elements:

[](i)


To set elements:

[]=(i, v)


To enumerate the elements:

each2(v)

collect2(v)


Properties of vectors:

angle_with(v)

Vector.independent?(*vs)

independent?(*vs)

zero?


Vector arithmetic:

*(x) “is matrix or number”

+(v)

-(v)

#/(v)

+@

-@


Vector functions:

inner_product(v), dot(v)

cross_product(v), cross(v)

collect

collect!

magnitude

map

map!

map2(v)

norm

normalize

r

round

size


Conversion to other data types:

covector

to_a

coerce(other)


String representations:

to_s

inspect


  


    
Raised if a parameter such as %e, %i, %o or %n is used without fetching a specific field.

  


    
A generic logging class

  


    
A CGI library using WEBrick requests and responses.

Example:

class MyCGI < WEBrick::CGI
  def do_GET req, res
    res.body = 'it worked!'
    res.status = 200
  end
end

MyCGI.new.start


  


    
Processes HTTP cookies

  


    
A generic module for daemonizing a process

  


    
Base TCP server class.  You must subclass GenericServer and provide a run method.

  


    
Basic Authentication for WEBrick

Use this class to add basic authentication to a WEBrick servlet.

Here is an example of how to set up a BasicAuth:

config = { :Realm => 'BasicAuth example realm' }

htpasswd = WEBrick::HTTPAuth::Htpasswd.new 'my_password_file', password_hash: :bcrypt
htpasswd.set_passwd config[:Realm], 'username', 'password'
htpasswd.flush

config[:UserDB] = htpasswd

basic_auth = WEBrick::HTTPAuth::BasicAuth.new config


  


    
RFC 2617 Digest Access Authentication for WEBrick

Use this class to add digest authentication to a WEBrick servlet.

Here is an example of how to set up DigestAuth:

config = { :Realm => 'DigestAuth example realm' }

htdigest = WEBrick::HTTPAuth::Htdigest.new 'my_password_file'
htdigest.set_passwd config[:Realm], 'username', 'password'
htdigest.flush

config[:UserDB] = htdigest

digest_auth = WEBrick::HTTPAuth::DigestAuth.new config


When using this as with a servlet be sure not to create a new DigestAuth object in the servlet's initialize.  By default WEBrick creates a new servlet instance for every request and the DigestAuth object must be used across requests.

  


    
Htdigest accesses apache-compatible digest password files.  Passwords are matched to a realm where they are valid.  For security, the path for a digest password database should be stored outside of the paths available to the HTTP server.

Htdigest is intended for use with WEBrick::HTTPAuth::DigestAuth and stores passwords using cryptographic hashes.

htpasswd = WEBrick::HTTPAuth::Htdigest.new 'my_password_file'
htpasswd.set_passwd 'my realm', 'username', 'password'
htpasswd.flush


  


    
Htgroup accesses apache-compatible group files.  Htgroup can be used to provide group-based authentication for users.  Currently Htgroup is not directly integrated with any authenticators in WEBrick.  For security, the path for a digest password database should be stored outside of the paths available to the HTTP server.

Example:

htgroup = WEBrick::HTTPAuth::Htgroup.new 'my_group_file'
htgroup.add 'superheroes', %w[spiderman batman]

htgroup.members('superheroes').include? 'magneto' # => false


  


    
Htpasswd accesses apache-compatible password files.  Passwords are matched to a realm where they are valid.  For security, the path for a password database should be stored outside of the paths available to the HTTP server.

Htpasswd is intended for use with WEBrick::HTTPAuth::BasicAuth.

To create an Htpasswd database with a single user:

htpasswd = WEBrick::HTTPAuth::Htpasswd.new 'my_password_file'
htpasswd.set_passwd 'my realm', 'username', 'password'
htpasswd.flush


  


    
Basic authentication for proxy servers.  See BasicAuth for details.

  


    
Digest authentication for proxy servers.  See DigestAuth for details.

  


    
An HTTP Proxy server which proxies GET, HEAD and POST requests.

To create a simple proxy server:

require 'webrick'
require 'webrick/httpproxy'

proxy = WEBrick::HTTPProxyServer.new Port: 8000

trap 'INT'  do proxy.shutdown end
trap 'TERM' do proxy.shutdown end

proxy.start


See ::new for proxy-specific configuration items.

Modifying proxied responses¶ ↑

To modify content the proxy server returns use the :ProxyContentHandler option:

handler = proc do |req, res|
  if res['content-type'] == 'text/plain' then
    res.body << "\nThis content was proxied!\n"
  end
end

proxy =
  WEBrick::HTTPProxyServer.new Port: 8000, ProxyContentHandler: handler


  


    
An HTTP request.  This is consumed by service and do_* methods in WEBrick servlets

  


    
An HTTP response.  This is filled in by the service or do_* methods of a WEBrick HTTP Servlet.

  


    
An HTTP Server

  


    
AbstractServlet allows HTTP server modules to be reused across multiple servers and allows encapsulation of functionality.

By default a servlet will respond to GET, HEAD (through an alias to GET) and OPTIONS requests.

By default a new servlet is initialized for every request.  A servlet instance can be reused by overriding ::get_instance in the AbstractServlet subclass.

A Simple Servlet¶ ↑

class Simple < WEBrick::HTTPServlet::AbstractServlet
  def do_GET request, response
    status, content_type, body = do_stuff_with request

    response.status = status
    response['Content-Type'] = content_type
    response.body = body
  end

  def do_stuff_with request
    return 200, 'text/plain', 'you got a page'
  end
end


This servlet can be mounted on a server at a given path:

server.mount '/simple', Simple


Servlet Configuration¶ ↑

Servlets can be configured via initialize.  The first argument is the HTTP server the servlet is being initialized for.

class Configurable < Simple
  def initialize server, color, size
    super server
    @color = color
    @size = size
  end

  def do_stuff_with request
    content = "<p " \
              %q{style="color: #{@color}; font-size: #{@size}"} \
              ">Hello, World!"

    return 200, "text/html", content
  end
end

This servlet must be provided two arguments at mount time:

server.mount '/configurable', Configurable, 'red', '2em'


  


    
Servlet for handling CGI scripts

Example:

server.mount('/cgi/my_script', WEBrick::HTTPServlet::CGIHandler,
             '/path/to/my_script')


  


    
Servlet for serving a single file.  You probably want to use the FileHandler servlet instead as it handles directories and fancy indexes.

Example:

server.mount('/my_page.txt', WEBrick::HTTPServlet::DefaultFileHandler,
             '/path/to/my_page.txt')


This servlet handles If-Modified-Since and Range requests.

  


    
ERBHandler evaluates an ERB file and returns the result.  This handler is automatically used if there are .rhtml files in a directory served by the FileHandler.

ERBHandler supports GET and POST methods.

The ERB file is evaluated with the local variables servlet_request and servlet_response which are a WEBrick::HTTPRequest and WEBrick::HTTPResponse respectively.

Example .rhtml file:

Request to <%= servlet_request.request_uri %>

Query params <%= servlet_request.query.inspect %>

  


    
Serves a directory including fancy indexing and a variety of other options.

Example:

server.mount('/assets', WEBrick::HTTPServlet::FileHandler,
             '/path/to/assets')


  


    
Mounts a proc at a path that accepts a request and response.

Instead of mounting this servlet with WEBrick::HTTPServer#mount use WEBrick::HTTPServer#mount_proc:

server.mount_proc '/' do |req, res|
  res.body = 'it worked!'
  res.status = 200
end


  


    
Root of the HTTP client error statuses

  


    
Root of the HTTP error statuses

  


    
Root of the HTTP info statuses

  


    
Root of the HTTP redirect statuses

  


    
Root of the HTTP server error statuses

  


    
Root of the HTTP status class hierarchy

  


    
Root of the HTTP success statuses

  


    
Stores multipart form data.  FormData objects are created when WEBrick::HTTPUtils.parse_form_data is called.

  


    
Represents an HTTP protocol version

  


    
A logging class that prepends a timestamp to each message.

  


    
Server error exception

  


    
Base server class

  


    
Class used to manage timeout handlers across multiple threads.

Timeout handlers should be managed by using the class methods which are synchronized.

id = TimeoutHandler.register(10, Timeout::Error)
begin
  sleep 20
  puts 'foo'
ensure
  TimeoutHandler.cancel(id)
end


will raise Timeout::Error

id = TimeoutHandler.register(10, Timeout::Error)
begin
  sleep 5
  puts 'foo'
ensure
  TimeoutHandler.cancel(id)
end


will print 'foo'

  


    
WIN32OLE

WIN32OLE objects represent OLE Automation object in Ruby.

By using WIN32OLE, you can access OLE server like VBScript.

Here is sample script.

require 'win32ole'

excel = WIN32OLE.new('Excel.Application')
excel.visible = true
workbook = excel.Workbooks.Add();
worksheet = workbook.Worksheets(1);
worksheet.Range("A1:D1").value = ["North","South","East","West"];
worksheet.Range("A2:B2").value = [5.2, 10];
worksheet.Range("C2").value = 8;
worksheet.Range("D2").value = 20;

range = worksheet.Range("A1:D2");
range.select
chart = workbook.Charts.Add;

workbook.saved = true;

excel.ActiveWorkbook.Close(0);
excel.Quit();


Unfortunately, Win32OLE doesn't support the argument passed by reference directly. Instead, Win32OLE provides WIN32OLE::ARGV or WIN32OLE_VARIANT object. If you want to get the result value of argument passed by reference, you can use WIN32OLE::ARGV or WIN32OLE_VARIANT.

oleobj.method(arg1, arg2, refargv3)
puts WIN32OLE::ARGV[2]   # the value of refargv3 after called oleobj.method


or

refargv3 = WIN32OLE_VARIANT.new(XXX,
            WIN32OLE::VARIANT::VT_BYREF|WIN32OLE::VARIANT::VT_XXX)
oleobj.method(arg1, arg2, refargv3)
p refargv3.value # the value of refargv3 after called oleobj.method.


  


    
Raised when OLE processing failed.

EX:

obj = WIN32OLE.new("NonExistProgID")


raises the exception:

WIN32OLERuntimeError: unknown OLE server: `NonExistProgID'
    HRESULT error code:0x800401f3
      Invalid class string

  


    
WIN32OLE_EVENT objects controls OLE event.

  


    
WIN32OLE_METHOD objects represent OLE method information.

  


    
WIN32OLE_PARAM objects represent param information of the OLE method.

  


    
WIN32OLE_RECORD objects represents VT_RECORD OLE variant. Win32OLE returns WIN32OLE_RECORD object if the result value of invoking OLE methods.

If COM server in VB.NET ComServer project is the following:

Imports System.Runtime.InteropServices
Public Class ComClass
    Public Structure Book
        <MarshalAs(UnmanagedType.BStr)> _
        Public title As String
        Public cost As Integer
    End Structure
    Public Function getBook() As Book
        Dim book As New Book
        book.title = "The Ruby Book"
        book.cost = 20
        Return book
    End Function
End Class

then, you can retrieve getBook return value from the following Ruby script:

require 'win32ole'
obj = WIN32OLE.new('ComServer.ComClass')
book = obj.getBook
book.class # => WIN32OLE_RECORD
book.title # => "The Ruby Book"
book.cost  # => 20


  


    
WIN32OLE_TYPE objects represent OLE type libarary information.

  


    
WIN32OLE_TYPELIB objects represent OLE tyblib information.

  


    
WIN32OLE_VARIABLE objects represent OLE variable information.

  


    
WIN32OLE_VARIANT objects represents OLE variant.

Win32OLE converts Ruby object into OLE variant automatically when invoking OLE methods. If OLE method requires the argument which is different from the variant by automatic conversion of Win32OLE, you can convert the specfied variant type by using WIN32OLE_VARIANT class.

param = WIN32OLE_VARIANT.new(10, WIN32OLE::VARIANT::VT_R4)
oleobj.method(param)


WIN32OLE_VARIANT does not support VT_RECORD variant. Use WIN32OLE_RECORD class instead of WIN32OLE_VARIANT if the VT_RECORD variant is needed.

  


    
Weak Reference class that allows a referenced object to be garbage-collected.

A WeakRef may be used exactly like the object it references.

Usage:

foo = Object.new            # create a new object instance
p foo.to_s                  # original's class
foo = WeakRef.new(foo)      # reassign foo with WeakRef instance
p foo.to_s                  # should be same class
GC.start                    # start the garbage collector
p foo.to_s                  # should raise exception (recycled)


  


    
RefError is raised when a referenced object has been recycled by the garbage collector

  


    
An example printer for irb.

It's much like the standard library PrettyPrint, that shows the value of each expression as it runs.

In order to use this library, you must first require it:

require 'irb/xmp'


Now, you can take advantage of the Object#xmp convenience method.

xmp <<END
  foo = "bar"
  baz = 42
END
#=> foo = "bar"
  #==>"bar"
#=> baz = 42
  #==>42


You can also create an XMP object, with an optional binding to print expressions in the given binding:

ctx = binding
x = XMP.new ctx
x.puts
#=> today = "a good day"
  #==>"a good day"
ctx.eval 'today # is what?'
#=> "a good day"


  


    
A custom InputMethod class used by XMP for evaluating string io.

  


    
YAML + DBM = YDBM

YAML::DBM provides the same interface as ::DBM.

However, while DBM only allows strings for both keys and values, this library allows one to use most Ruby objects for values by first converting them to YAML. Keys must be strings.

Conversion to and from YAML is performed automatically.

See the documentation for ::DBM and ::YAML for more information.

  


    
YAML::Store provides the same functionality as PStore, except it uses YAML to dump objects instead of Marshal.

Example¶ ↑

require 'yaml/store'

Person = Struct.new :first_name, :last_name

people = [Person.new("Bob", "Smith"), Person.new("Mary", "Johnson")]

store = YAML::Store.new "test.store"

store.transaction do
  store["people"] = people
  store["greeting"] = { "hello" => "world" }
end


After running the above code, the contents of “test.store” will be:

---
people:
- !ruby/struct:Person
  first_name: Bob
  last_name: Smith
- !ruby/struct:Person
  first_name: Mary
  last_name: Johnson
greeting:
  hello: world

  


    
Raised when attempting to divide an integer by 0.

42 / 0   #=> ZeroDivisionError: divided by 0


Note that only division by an exact 0 will raise the exception:

42 /  0.0   #=> Float::INFINITY
42 / -0.0   #=> -Float::INFINITY
0  /  0.0   #=> NaN


  


    
Subclass of Zlib::Error when zlib returns a Z_BUF_ERROR.

Usually if no progress is possible.

  


    
Subclass of Zlib::Error when zlib returns a Z_DATA_ERROR.

Usually if a stream was prematurely freed.

  


    
Zlib::Deflate is the class for compressing data.  See Zlib::ZStream for more information.

  


    
The superclass for all exceptions raised by Ruby/zlib.

The following exceptions are defined as subclasses of Zlib::Error. These exceptions are raised when zlib library functions return with an error status.

Zlib::StreamEnd

Zlib::NeedDict

Zlib::DataError

Zlib::StreamError

Zlib::MemError

Zlib::BufError

Zlib::VersionError


  


    
Zlib::GzipFile is an abstract class for handling a gzip formatted compressed file. The operations are defined in the subclasses, Zlib::GzipReader for reading, and Zlib::GzipWriter for writing.

GzipReader should be used by associating an IO, or IO-like, object.

Method Catalogue¶ ↑

::wrap

::open (Zlib::GzipReader::open and Zlib::GzipWriter::open)

close

closed?

comment

comment= (Zlib::GzipWriter#comment=)

crc

eof? (Zlib::GzipReader#eof?)

finish

level

lineno (Zlib::GzipReader#lineno)

lineno= (Zlib::GzipReader#lineno=)

mtime

mtime= (Zlib::GzipWriter#mtime=)

orig_name

orig_name (Zlib::GzipWriter#orig_name=)

os_code

path (when the underlying IO supports path)

sync

sync=

to_io


(due to internal structure, documentation may appear under Zlib::GzipReader or Zlib::GzipWriter)

  


    
Raised when the CRC checksum recorded in gzip file footer is not equivalent to the CRC checksum of the actual uncompressed data.

  


    
Base class of errors that occur when processing GZIP files.

  


    
Raised when the data length recorded in the gzip file footer is not equivalent to the length of the actual uncompressed data.

  


    
Raised when gzip file footer is not found.

  


    
Zlib::GzipReader is the class for reading a gzipped file.  GzipReader should be used as an IO, or -IO-like, object.

Zlib::GzipReader.open('hoge.gz') {|gz|
  print gz.read
}

File.open('hoge.gz') do |f|
  gz = Zlib::GzipReader.new(f)
  print gz.read
  gz.close
end


Method Catalogue¶ ↑

The following methods in Zlib::GzipReader are just like their counterparts in IO, but they raise Zlib::Error or Zlib::GzipFile::Error exception if an error was found in the gzip file.

each

each_line

each_byte

gets

getc

lineno

lineno=

read

readchar

readline

readlines

ungetc


Be careful of the footer of the gzip file. A gzip file has the checksum of pre-compressed data in its footer. GzipReader checks all uncompressed data against that checksum at the following cases, and if it fails, raises Zlib::GzipFile::NoFooter, Zlib::GzipFile::CRCError, or Zlib::GzipFile::LengthError exception.

When an reading request is received beyond the end of file (the end of compressed data). That is, when Zlib::GzipReader#read, Zlib::GzipReader#gets, or some other methods for reading returns nil.

When Zlib::GzipFile#close method is called after the object reaches the end of file.

When Zlib::GzipReader#unused method is called after the object reaches the end of file.


The rest of the methods are adequately described in their own documentation.

  


    
Zlib::GzipWriter is a class for writing gzipped files.  GzipWriter should be used with an instance of IO, or IO-like, object.

Following two example generate the same result.

Zlib::GzipWriter.open('hoge.gz') do |gz|
  gz.write 'jugemu jugemu gokou no surikire...'
end

File.open('hoge.gz', 'w') do |f|
  gz = Zlib::GzipWriter.new(f)
  gz.write 'jugemu jugemu gokou no surikire...'
  gz.close
end


To make like gzip(1) does, run following:

orig = 'hoge.txt'
Zlib::GzipWriter.open('hoge.gz') do |gz|
  gz.mtime = File.mtime(orig)
  gz.orig_name = orig
  gz.write IO.binread(orig)
end


NOTE: Due to the limitation of Ruby's finalizer, you must explicitly close GzipWriter objects by Zlib::GzipWriter#close etc.  Otherwise, GzipWriter will be not able to write the gzip footer and will generate a broken gzip file.

  


    
Zlib:Inflate is the class for decompressing compressed data.  Unlike Zlib::Deflate, an instance of this class is not able to duplicate (clone, dup) itself.

  


    
Subclass of Zlib::Error

When zlib returns a Z_MEM_ERROR, usually if there was not enough memory.

  


    
Subclass of Zlib::Error

When zlib returns a Z_NEED_DICT if a preset dictionary is needed at this point.

Used by Zlib::Inflate.inflate and Zlib.inflate

  


    
Subclass of Zlib::Error

When zlib returns a Z_STREAM_END is return if the end of the compressed data has been reached and all uncompressed out put has been produced.

  


    
Subclass of Zlib::Error

When zlib returns a Z_STREAM_ERROR, usually if the stream state was inconsistent.

  


    
Subclass of Zlib::Error

When zlib returns a Z_VERSION_ERROR, usually if the zlib library version is incompatible with the version assumed by the caller.

  


    
Zlib::ZStream is the abstract class for the stream which handles the compressed data. The operations are defined in the subclasses: Zlib::Deflate for compression, and Zlib::Inflate for decompression.

An instance of Zlib::ZStream has one stream (struct zstream in the source) and two variable-length buffers which associated to the input (next_in) of the stream and the output (next_out) of the stream. In this document, “input buffer” means the buffer for input, and “output buffer” means the buffer for output.

Data input into an instance of Zlib::ZStream are temporally stored into the end of input buffer, and then data in input buffer are processed from the beginning of the buffer until no more output from the stream is produced (i.e. until avail_out > 0 after processing).  During processing, output buffer is allocated and expanded automatically to hold all output data.

Some particular instance methods consume the data in output buffer and return them as a String.

Here is an ascii art for describing above:

+================ an instance of Zlib::ZStream ================+
||                                                            ||
||     +--------+          +-------+          +--------+      ||
||  +--| output |<---------|zstream|<---------| input  |<--+  ||
||  |  | buffer |  next_out+-------+next_in   | buffer |   |  ||
||  |  +--------+                             +--------+   |  ||
||  |                                                      |  ||
+===|======================================================|===+
    |                                                      |
    v                                                      |
"output data"                                         "input data"

If an error occurs during processing input buffer, an exception which is a subclass of Zlib::Error is raised.  At that time, both input and output buffer keep their conditions at the time when the error occurs.

Method Catalogue¶ ↑

Many of the methods in this class are fairly low-level and unlikely to be of interest to users.  In fact, users are unlikely to use this class directly; rather they will be interested in Zlib::Inflate and Zlib::Deflate.

The higher level methods are listed below.

total_in

total_out

data_type

adler

reset

finish

finished?

close

closed?


  


    
fatal is an Exception that is raised when Ruby has encountered a fatal error and must exit.  You are not able to rescue fatal.

  

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment