erlang-terms 1.1.0 → 2.0.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.coveralls.yml +1 -0
- data/.editorconfig +20 -0
- data/.gitignore +10 -18
- data/.ruby-gemset +1 -0
- data/.ruby-version +1 -0
- data/.travis.yml +15 -3
- data/.yardopts +6 -0
- data/CHANGELOG.md +9 -0
- data/Gemfile +21 -1
- data/LICENSE.txt +1 -1
- data/README.md +95 -17
- data/Rakefile +8 -3
- data/erlang-terms.gemspec +14 -11
- data/lib/erlang-terms.rb +1 -0
- data/lib/erlang/associable.rb +98 -0
- data/lib/erlang/atom.rb +257 -0
- data/lib/erlang/binary.rb +425 -0
- data/lib/erlang/bitstring.rb +464 -0
- data/lib/erlang/cons.rb +122 -0
- data/lib/erlang/enumerable.rb +160 -0
- data/lib/erlang/error.rb +4 -0
- data/lib/erlang/export.rb +110 -12
- data/lib/erlang/float.rb +201 -0
- data/lib/erlang/function.rb +259 -0
- data/lib/erlang/immutable.rb +101 -0
- data/lib/erlang/list.rb +1685 -24
- data/lib/erlang/map.rb +935 -21
- data/lib/erlang/nil.rb +73 -10
- data/lib/erlang/pid.rb +120 -18
- data/lib/erlang/port.rb +123 -0
- data/lib/erlang/reference.rb +161 -0
- data/lib/erlang/string.rb +175 -3
- data/lib/erlang/term.rb +24 -0
- data/lib/erlang/terms.rb +324 -8
- data/lib/erlang/terms/version.rb +1 -1
- data/lib/erlang/trie.rb +364 -0
- data/lib/erlang/tuple.rb +1582 -14
- data/lib/erlang/undefined.rb +32 -0
- metadata +49 -71
- data/spec/erlang/export_spec.rb +0 -17
- data/spec/erlang/list_spec.rb +0 -39
- data/spec/erlang/map_spec.rb +0 -24
- data/spec/erlang/nil_spec.rb +0 -18
- data/spec/erlang/pid_spec.rb +0 -21
- data/spec/erlang/string_spec.rb +0 -11
- data/spec/erlang/terms_spec.rb +0 -7
- data/spec/erlang/tuple_spec.rb +0 -20
- data/spec/spec_helper.rb +0 -7
data/lib/erlang/nil.rb
CHANGED
@@ -1,15 +1,78 @@
|
|
1
|
+
require 'singleton'
|
2
|
+
|
1
3
|
module Erlang
|
2
|
-
|
3
|
-
|
4
|
-
|
4
|
+
# A list without any elements. This is a singleton, since all empty lists are equivalent.
|
5
|
+
#
|
6
|
+
# Licensing
|
7
|
+
# =========
|
8
|
+
#
|
9
|
+
# Portions taken and modified from https://github.com/hamstergem/hamster
|
10
|
+
#
|
11
|
+
# Copyright (c) 2009-2014 Simon Harris
|
12
|
+
#
|
13
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
14
|
+
# a copy of this software and associated documentation files (the
|
15
|
+
# "Software"), to deal in the Software without restriction, including
|
16
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
17
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
18
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
19
|
+
# the following conditions:
|
20
|
+
#
|
21
|
+
# The above copyright notice and this permission notice shall be
|
22
|
+
# included in all copies or substantial portions of the Software.
|
23
|
+
#
|
24
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
25
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
26
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
27
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
28
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
29
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
30
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
31
|
+
#
|
32
|
+
# @private
|
33
|
+
class EmptyList
|
34
|
+
include Singleton
|
35
|
+
include Erlang::Term
|
36
|
+
include Erlang::List
|
37
|
+
include Erlang::Immutable
|
38
|
+
|
39
|
+
# @private
|
40
|
+
def hash
|
41
|
+
return Erlang::EmptyList.hash
|
42
|
+
end
|
43
|
+
|
44
|
+
# There is no first item in an empty list, so return `Undefined`.
|
45
|
+
# @return [Undefined]
|
46
|
+
def head
|
47
|
+
return Erlang::Undefined
|
48
|
+
end
|
49
|
+
alias :first :head
|
50
|
+
|
51
|
+
# There are no subsequent elements, so return an empty list.
|
52
|
+
# @return [self]
|
53
|
+
def tail
|
54
|
+
return self
|
5
55
|
end
|
6
56
|
|
7
|
-
def
|
8
|
-
|
9
|
-
true
|
10
|
-
else
|
11
|
-
other === self.class
|
12
|
-
end
|
57
|
+
def empty?
|
58
|
+
return true
|
13
59
|
end
|
60
|
+
|
61
|
+
def improper?
|
62
|
+
return false
|
63
|
+
end
|
64
|
+
|
65
|
+
# Return the number of items in this `List`.
|
66
|
+
# @return [Integer]
|
67
|
+
def size
|
68
|
+
return 0
|
69
|
+
end
|
70
|
+
alias :length :size
|
14
71
|
end
|
15
|
-
|
72
|
+
|
73
|
+
# A list without any elements. This is a singleton, since all empty lists are equivalent.
|
74
|
+
Nil = EmptyList.instance
|
75
|
+
|
76
|
+
# @private
|
77
|
+
EmptyList.freeze
|
78
|
+
end
|
data/lib/erlang/pid.rb
CHANGED
@@ -1,31 +1,133 @@
|
|
1
1
|
module Erlang
|
2
|
+
# A `Pid` is a process identifier object obtained from [`erlang:spawn/3`](http://erlang.org/doc/man/erlang.html#spawn-3).
|
3
|
+
#
|
4
|
+
# ### Creating Pids
|
5
|
+
#
|
6
|
+
# Erlang::Pid["nonode@nohost", 38, 0, 0]
|
7
|
+
# # => Erlang::Pid[:"nonode@nohost", 38, 0, 0]
|
8
|
+
#
|
2
9
|
class Pid
|
3
|
-
|
10
|
+
include Erlang::Term
|
11
|
+
include Erlang::Immutable
|
4
12
|
|
13
|
+
# Return the node for this `Pid`
|
14
|
+
# @return [Atom]
|
15
|
+
attr_reader :node
|
16
|
+
|
17
|
+
# Return the id for this `Pid`
|
18
|
+
# @return [Integer]
|
19
|
+
attr_reader :id
|
20
|
+
|
21
|
+
# Return the serial for this `Pid`
|
22
|
+
# @return [Integer]
|
23
|
+
attr_reader :serial
|
24
|
+
|
25
|
+
# Return the creation for this `Pid`
|
26
|
+
# @return [Integer]
|
27
|
+
attr_reader :creation
|
28
|
+
|
29
|
+
class << self
|
30
|
+
# Create a new `Pid` populated with the given `node`, `id`, `serial`, and `creation`.
|
31
|
+
# @param node [Atom, Symbol] The node atom
|
32
|
+
# @param id [Integer] The id as a non-negative integer
|
33
|
+
# @param serial [Integer] The serial time as a non-negative integer
|
34
|
+
# @param creation [Integer] The creation time as a non-negative integer
|
35
|
+
# @return [Pid]
|
36
|
+
# @raise [ArgumentError] if `node` is not an `Atom` or one of `id`, `serial`, or `creation` are not non-negative `Integer`s
|
37
|
+
def [](node, id, serial = 0, creation = 0)
|
38
|
+
return new(node, id, serial, creation)
|
39
|
+
end
|
40
|
+
|
41
|
+
# Compares `a` and `b` and returns whether they are less than,
|
42
|
+
# equal to, or greater than each other.
|
43
|
+
#
|
44
|
+
# @param a [Pid] The left argument
|
45
|
+
# @param b [Pid] The right argument
|
46
|
+
# @return [-1, 0, 1]
|
47
|
+
# @raise [ArgumentError] if `a` or `b` is not a `Pid`
|
48
|
+
def compare(a, b)
|
49
|
+
raise ArgumentError, "'a' must be of Erlang::Pid type" unless a.kind_of?(Erlang::Pid)
|
50
|
+
raise ArgumentError, "'b' must be of Erlang::Pid type" unless b.kind_of?(Erlang::Pid)
|
51
|
+
c = Erlang.compare(a.node, b.node)
|
52
|
+
return c if c != 0
|
53
|
+
c = Erlang.compare(a.id, b.id)
|
54
|
+
return c if c != 0
|
55
|
+
c = Erlang.compare(a.serial, b.serial)
|
56
|
+
return c if c != 0
|
57
|
+
c = Erlang.compare(a.creation, b.creation)
|
58
|
+
return c
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
# @private
|
5
63
|
def initialize(node, id, serial = 0, creation = 0)
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
64
|
+
raise ArgumentError, 'id must be a non-negative Integer' if not id.is_a?(::Integer) or id < 0
|
65
|
+
raise ArgumentError, 'serial must be a non-negative Integer' if not serial.is_a?(::Integer) or serial < 0
|
66
|
+
raise ArgumentError, 'creation must be a non-negative Integer' if not creation.is_a?(::Integer) or creation < 0
|
67
|
+
@node = Erlang::Atom[node]
|
68
|
+
@id = id.freeze
|
69
|
+
@serial = serial.freeze
|
70
|
+
@creation = creation.freeze
|
71
|
+
end
|
72
|
+
|
73
|
+
# @private
|
74
|
+
def hash
|
75
|
+
state = [@node, @id, @serial, @creation]
|
76
|
+
return state.reduce(Erlang::Pid.hash) { |acc, item| (acc << 5) - acc + item.hash }
|
77
|
+
end
|
78
|
+
|
79
|
+
# Return true if `other` has the same type and contents as this `Pid`.
|
80
|
+
#
|
81
|
+
# @param other [Object] The object to compare with
|
82
|
+
# @return [Boolean]
|
83
|
+
def eql?(other)
|
84
|
+
return true if other.equal?(self)
|
85
|
+
if instance_of?(other.class)
|
86
|
+
return !!(node == other.node &&
|
87
|
+
id == other.id &&
|
88
|
+
serial == other.serial &&
|
89
|
+
creation == other.creation)
|
90
|
+
else
|
91
|
+
return !!(Erlang.compare(other, self) == 0)
|
92
|
+
end
|
93
|
+
end
|
94
|
+
alias :== :eql?
|
95
|
+
|
96
|
+
# Return the contents of this `Pid` as a Erlang-readable `::String`.
|
97
|
+
#
|
98
|
+
# @example
|
99
|
+
# Erlang::Pid["nonode@nohost", 38, 0, 0].erlang_inspect
|
100
|
+
# # => "{'pid','nonode@nohost',38,0,0}"
|
101
|
+
#
|
102
|
+
# @return [::String]
|
103
|
+
def erlang_inspect(raw = false)
|
104
|
+
if raw == true and Erlang.respond_to?(:term_to_binary)
|
105
|
+
result = 'erlang:binary_to_term('
|
106
|
+
result << Erlang.inspect(Erlang.term_to_binary(self), raw: raw)
|
107
|
+
result << ')'
|
108
|
+
return result
|
109
|
+
else
|
110
|
+
return Erlang.inspect(Erlang::Tuple[:pid, node, id, serial, creation], raw: raw)
|
111
|
+
end
|
10
112
|
end
|
11
113
|
|
12
|
-
# @return [String] the nicely formatted version of the
|
114
|
+
# @return [::String] the nicely formatted version of the `Pid`.
|
13
115
|
def inspect
|
14
|
-
"
|
116
|
+
return "Erlang::Pid[#{node.inspect}, #{id.inspect}, #{serial.inspect}, #{creation.inspect}]"
|
15
117
|
end
|
16
118
|
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
119
|
+
# @return [::Array]
|
120
|
+
# @private
|
121
|
+
def marshal_dump
|
122
|
+
return [@node, @id, @serial, @creation]
|
21
123
|
end
|
22
124
|
|
23
|
-
|
24
|
-
|
25
|
-
node
|
26
|
-
|
27
|
-
|
28
|
-
|
125
|
+
# @private
|
126
|
+
def marshal_load(args)
|
127
|
+
node, id, serial, creation = args
|
128
|
+
initialize(node, id, serial, creation)
|
129
|
+
__send__(:immutable!)
|
130
|
+
return self
|
29
131
|
end
|
30
132
|
end
|
31
|
-
end
|
133
|
+
end
|
data/lib/erlang/port.rb
ADDED
@@ -0,0 +1,123 @@
|
|
1
|
+
module Erlang
|
2
|
+
# A `Port` is a port object obtained from [`erlang:open_port/2`](http://erlang.org/doc/man/erlang.html#open_port-2).
|
3
|
+
#
|
4
|
+
# ### Creating Ports
|
5
|
+
#
|
6
|
+
# Erlang::Port["nonode@nohost", 100, 1]
|
7
|
+
# # => Erlang::Port[:"nonode@nohost", 100, 1]
|
8
|
+
#
|
9
|
+
class Port
|
10
|
+
include Erlang::Term
|
11
|
+
include Erlang::Immutable
|
12
|
+
|
13
|
+
# Return the node for this `Port`
|
14
|
+
# @return [Atom]
|
15
|
+
attr_reader :node
|
16
|
+
|
17
|
+
# Return the id for this `Port`
|
18
|
+
# @return [Integer]
|
19
|
+
attr_reader :id
|
20
|
+
|
21
|
+
# Return the creation for this `Port`
|
22
|
+
# @return [Integer]
|
23
|
+
attr_reader :creation
|
24
|
+
|
25
|
+
class << self
|
26
|
+
# Create a new `Port` populated with the given `node`, `id`, and `creation`.
|
27
|
+
# @param node [Atom, Symbol] The node atom
|
28
|
+
# @param id [Integer] The id as a non-negative integer
|
29
|
+
# @param creation [Integer] The creation time as a non-negative integer
|
30
|
+
# @return [Port]
|
31
|
+
# @raise [ArgumentError] if `node` is not an `Atom` or `id` or `creation` are not non-negative `Integer`s
|
32
|
+
def [](node, id, creation = 0)
|
33
|
+
return new(node, id, creation)
|
34
|
+
end
|
35
|
+
|
36
|
+
# Compares `a` and `b` and returns whether they are less than,
|
37
|
+
# equal to, or greater than each other.
|
38
|
+
#
|
39
|
+
# @param a [Port] The left argument
|
40
|
+
# @param b [Port] The right argument
|
41
|
+
# @return [-1, 0, 1]
|
42
|
+
# @raise [ArgumentError] if `a` or `b` is not a `Port`
|
43
|
+
def compare(a, b)
|
44
|
+
raise ArgumentError, "'a' must be of Erlang::Port type" unless a.kind_of?(Erlang::Port)
|
45
|
+
raise ArgumentError, "'b' must be of Erlang::Port type" unless b.kind_of?(Erlang::Port)
|
46
|
+
c = Erlang.compare(a.node, b.node)
|
47
|
+
return c if c != 0
|
48
|
+
c = Erlang.compare(a.id, b.id)
|
49
|
+
return c if c != 0
|
50
|
+
c = Erlang.compare(a.creation, b.creation)
|
51
|
+
return c
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
# @private
|
56
|
+
def initialize(node, id, creation = 0)
|
57
|
+
raise ArgumentError, 'id must be a non-negative Integer' if not id.is_a?(::Integer) or id < 0
|
58
|
+
raise ArgumentError, 'creation must be a non-negative Integer' if not creation.is_a?(::Integer) or creation < 0
|
59
|
+
@node = Erlang::Atom[node]
|
60
|
+
@id = id.freeze
|
61
|
+
@creation = creation.freeze
|
62
|
+
end
|
63
|
+
|
64
|
+
# @private
|
65
|
+
def hash
|
66
|
+
state = [@node, @id, @creation]
|
67
|
+
return state.reduce(Erlang::Port.hash) { |acc, item| (acc << 5) - acc + item.hash }
|
68
|
+
end
|
69
|
+
|
70
|
+
# Return true if `other` has the same type and contents as this `Port`.
|
71
|
+
#
|
72
|
+
# @param other [Object] The object to compare with
|
73
|
+
# @return [Boolean]
|
74
|
+
def eql?(other)
|
75
|
+
return true if other.equal?(self)
|
76
|
+
if instance_of?(other.class)
|
77
|
+
return !!(node == other.node &&
|
78
|
+
id == other.id &&
|
79
|
+
creation == other.creation)
|
80
|
+
else
|
81
|
+
return !!(Erlang.compare(other, self) == 0)
|
82
|
+
end
|
83
|
+
end
|
84
|
+
alias :== :eql?
|
85
|
+
|
86
|
+
# Return the contents of this `Port` as a Erlang-readable `::String`.
|
87
|
+
#
|
88
|
+
# @example
|
89
|
+
# Erlang::Port["nonode@nohost", 100, 1].erlang_inspect
|
90
|
+
# # => "{'port','nonode@nohost',100,1}"
|
91
|
+
#
|
92
|
+
# @return [::String]
|
93
|
+
def erlang_inspect(raw = false)
|
94
|
+
if raw == true and Erlang.respond_to?(:term_to_binary)
|
95
|
+
result = 'erlang:binary_to_term('
|
96
|
+
result << Erlang.inspect(Erlang.term_to_binary(self), raw: raw)
|
97
|
+
result << ')'
|
98
|
+
return result
|
99
|
+
else
|
100
|
+
return Erlang.inspect(Erlang::Tuple[:port, node, id, creation], raw: raw)
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
# @return [::String] the nicely formatted version of the `Port`.
|
105
|
+
def inspect
|
106
|
+
return "Erlang::Port[#{node.inspect}, #{id.inspect}, #{creation.inspect}]"
|
107
|
+
end
|
108
|
+
|
109
|
+
# @return [::Array]
|
110
|
+
# @private
|
111
|
+
def marshal_dump
|
112
|
+
return [@node, @id, @creation]
|
113
|
+
end
|
114
|
+
|
115
|
+
# @private
|
116
|
+
def marshal_load(args)
|
117
|
+
node, id, creation = args
|
118
|
+
initialize(node, id, creation)
|
119
|
+
__send__(:immutable!)
|
120
|
+
return self
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
@@ -0,0 +1,161 @@
|
|
1
|
+
module Erlang
|
2
|
+
# @private
|
3
|
+
class NewReferenceError < Erlang::Error; end
|
4
|
+
|
5
|
+
# A `Reference` is an [unique reference](http://erlang.org/doc/efficiency_guide/advanced.html#unique_references).
|
6
|
+
#
|
7
|
+
# ### Creating New References
|
8
|
+
#
|
9
|
+
# # New reference
|
10
|
+
# Erlang::Reference["nonode@nohost", 0, [0, 0, 0]]
|
11
|
+
# # => Erlang::Reference[:"nonode@nohost", 0, [0, 0, 0]]
|
12
|
+
# # Old reference
|
13
|
+
# Erlang::Reference["nonode@nohost", 0, 0]
|
14
|
+
# # => Erlang::Reference[:"nonode@nohost", 0, 0]
|
15
|
+
#
|
16
|
+
class Reference
|
17
|
+
include Erlang::Term
|
18
|
+
include Erlang::Immutable
|
19
|
+
|
20
|
+
# Return the node for this `Reference`
|
21
|
+
# @return [Atom]
|
22
|
+
attr_reader :node
|
23
|
+
|
24
|
+
# Return the creation for this `Reference`
|
25
|
+
# @return [Integer]
|
26
|
+
attr_reader :creation
|
27
|
+
|
28
|
+
# Return the ids for this `Reference`
|
29
|
+
# @return [[Integer]]
|
30
|
+
attr_reader :ids
|
31
|
+
|
32
|
+
class << self
|
33
|
+
# Create a new `Reference` populated with the given node, creation, and id(s).
|
34
|
+
# @param node [Atom, Symbol] The node atom
|
35
|
+
# @param creation [Integer] The creation time as a non-negative integer
|
36
|
+
# @param ids [Integer] The ids as a `List` of non-negative integers
|
37
|
+
# @return [Reference]
|
38
|
+
# @raise [ArgumentError] if `node` is not an `Atom` or `creation` or `ids` are not non-negative `Integer`s
|
39
|
+
def [](node, creation, ids)
|
40
|
+
return new(node, creation, ids)
|
41
|
+
end
|
42
|
+
|
43
|
+
# Compares `a` and `b` and returns whether they are less than,
|
44
|
+
# equal to, or greater than each other.
|
45
|
+
#
|
46
|
+
# @param a [Reference] The left argument
|
47
|
+
# @param b [Reference] The right argument
|
48
|
+
# @return [-1, 0, 1]
|
49
|
+
# @raise [ArgumentError] if `a` or `b` is not a `Reference`
|
50
|
+
def compare(a, b)
|
51
|
+
raise ArgumentError, "'a' must be of Erlang::Reference type" unless a.kind_of?(Erlang::Reference)
|
52
|
+
raise ArgumentError, "'b' must be of Erlang::Reference type" unless b.kind_of?(Erlang::Reference)
|
53
|
+
c = Erlang.compare(a.node, b.node)
|
54
|
+
return c if c != 0
|
55
|
+
c = Erlang.compare(a.creation, b.creation)
|
56
|
+
return c if c != 0
|
57
|
+
c = Erlang.compare(a.ids, b.ids)
|
58
|
+
return c
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
# @private
|
63
|
+
def initialize(node, creation, ids)
|
64
|
+
raise ArgumentError, 'creation must be a non-negative Integer' if not creation.is_a?(::Integer) or creation < 0
|
65
|
+
ids = Erlang.from(ids)
|
66
|
+
if Erlang.is_list(ids)
|
67
|
+
raise ArgumentError, 'ids list cannot be empty' if ids.empty?
|
68
|
+
raise ArgumentError, 'ids must be a List of non-negative Integer' if ids.any? { |id| !id.is_a?(::Integer) or id < 0 }
|
69
|
+
@node = Erlang::Atom[node]
|
70
|
+
@creation = creation.freeze
|
71
|
+
@ids = ids
|
72
|
+
else
|
73
|
+
id = ids
|
74
|
+
raise ArgumentError, 'id must be a non-negative Integer' if not id.is_a?(::Integer) or id < 0
|
75
|
+
@node = Erlang::Atom[node]
|
76
|
+
@creation = creation.freeze
|
77
|
+
@ids = id.freeze
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
# @private
|
82
|
+
def hash
|
83
|
+
state = [@node, @creation, @ids]
|
84
|
+
return state.reduce(Erlang::Reference.hash) { |acc, item| (acc << 5) - acc + item.hash }
|
85
|
+
end
|
86
|
+
|
87
|
+
# Return true if `other` has the same type and contents as this `Reference`.
|
88
|
+
#
|
89
|
+
# @param other [Object] The object to compare with
|
90
|
+
# @return [Boolean]
|
91
|
+
def eql?(other)
|
92
|
+
return true if other.equal?(self)
|
93
|
+
if instance_of?(other.class)
|
94
|
+
return !!(@node == other.node &&
|
95
|
+
@creation == other.creation &&
|
96
|
+
@ids == other.ids)
|
97
|
+
else
|
98
|
+
return !!(Erlang.compare(other, self) == 0)
|
99
|
+
end
|
100
|
+
end
|
101
|
+
alias :== :eql?
|
102
|
+
|
103
|
+
# Return the singular id if this `Reference` is an old
|
104
|
+
# reference. Otherwise, raise a `NewReferenceError`.
|
105
|
+
#
|
106
|
+
# @return [Integer]
|
107
|
+
# @raise [NewReferenceError] if new reference
|
108
|
+
def id
|
109
|
+
raise Erlang::NewReferenceError if new_reference?
|
110
|
+
return @ids
|
111
|
+
end
|
112
|
+
|
113
|
+
# Return true if this is a new reference.
|
114
|
+
#
|
115
|
+
# @return [Boolean]
|
116
|
+
def new_reference?
|
117
|
+
return Erlang.is_list(@ids)
|
118
|
+
end
|
119
|
+
|
120
|
+
# Return the contents of this `reference` as a Erlang-readable `::String`.
|
121
|
+
#
|
122
|
+
# @example
|
123
|
+
# # New reference
|
124
|
+
# Erlang::Reference["nonode@nohost", 0, [0, 0, 0]].erlang_inspect
|
125
|
+
# # => "{'reference','nonode@nohost',0,[0,0,0]}"
|
126
|
+
# # Old reference
|
127
|
+
# Erlang::Reference["nonode@nohost", 0, 0].erlang_inspect
|
128
|
+
# # => "{'reference','nonode@nohost',0,0}"
|
129
|
+
#
|
130
|
+
# @return [::String]
|
131
|
+
def erlang_inspect(raw = false)
|
132
|
+
if raw == true and Erlang.respond_to?(:term_to_binary)
|
133
|
+
result = 'erlang:binary_to_term('
|
134
|
+
result << Erlang.inspect(Erlang.term_to_binary(self), raw: raw)
|
135
|
+
result << ')'
|
136
|
+
return result
|
137
|
+
else
|
138
|
+
return Erlang.inspect(Erlang::Tuple[:reference, @node, @creation, @ids], raw: raw)
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
# @return [::String] the nicely formatted version of the `Reference`
|
143
|
+
def inspect
|
144
|
+
return "Erlang::Reference[#{@node.inspect}, #{@creation.inspect}, #{@ids.inspect}]"
|
145
|
+
end
|
146
|
+
|
147
|
+
# @return [::Array]
|
148
|
+
# @private
|
149
|
+
def marshal_dump
|
150
|
+
return [@node, @creation, @ids]
|
151
|
+
end
|
152
|
+
|
153
|
+
# @private
|
154
|
+
def marshal_load(args)
|
155
|
+
node, creation, ids = args
|
156
|
+
initialize(node, creation, ids)
|
157
|
+
__send__(:immutable!)
|
158
|
+
return self
|
159
|
+
end
|
160
|
+
end
|
161
|
+
end
|