safety 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 82ccd013a24f2ad81da78340b9ceceae95240f52
4
+ data.tar.gz: 9d5429001690a7a33dabcce0002103560bfcff2a
5
+ SHA512:
6
+ metadata.gz: e1c567f91aa9079323da52b092dfa5dfff36e3c656f758c95fc6844cbce4dc6b66d78d1e3c3c8c86885bacc47d2c3518c26def7a23bcc78802f726d393b928d6
7
+ data.tar.gz: 0fa062d38e2f969ea32b374723c4ace3a96dd803b1905b5e0f072b3a7a8683a282caeb1880aa33e5c3c5a78f0e602d8e363ff1e9367344d1a52cba3fd852d3c7
@@ -0,0 +1,13 @@
1
+ module SafetyAttributeHelper
2
+ def self.parse_attribute_type method
3
+ if method.to_s =~ /attr_accessor_[a-zA-Z_]*/
4
+ :accessor
5
+ elsif method.to_s =~ /attr_reader_[a-zA-Z_]*/
6
+ :reader
7
+ elsif method.to_s =~ /attr_writer_[a-zA-Z_]*/
8
+ :writer
9
+ else
10
+ nil
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,91 @@
1
+ require 'safety/safety_attribute_helper'
2
+ module SafetyModule
3
+ def respond_to?(method)
4
+ if SafetyAttributeHelper.parse_attribute_type method
5
+ true
6
+ else
7
+ super
8
+ end
9
+ end
10
+
11
+ def method_missing(method, *args, &block)
12
+ type = SafetyAttributeHelper.parse_attribute_type method
13
+ if type
14
+ # Extract the type name from the attribute declaration
15
+ type_name = method.to_s.slice("attr_#{type.to_s}_".length...method.to_s.length)
16
+
17
+ # If the type name is var, type safety will be disabled for this attribute
18
+ should_enforce_type_safety = type_name != 'var'
19
+
20
+ # The class to enforce type safety on
21
+ type_safe_class = nil
22
+
23
+ # Get the type, which could be deep in modules
24
+ if should_enforce_type_safety == true
25
+ type_safe_class = type_name.split('::').inject(Object.class) do |current_module, class_name|
26
+ current_module.const_get(class_name)
27
+ end
28
+ end
29
+
30
+ # Define enforce safety for this property
31
+ define_method "__enforce_safety_#{args[0]}".to_sym do |value|
32
+ # If enforcing type and value is not of type safe class, raise TypeError
33
+ if should_enforce_type_safety == true and value.is_a?(type_safe_class) == false
34
+ raise TypeError, "Type Safe Attribute \"#{args[0]}\", of type \"#{type_safe_class}\", set to value \"#{value}\" of class \"#{value.class}\"."
35
+ end
36
+ return value
37
+ end
38
+
39
+ # A way to get the default value
40
+ define_method "__default_value_#{args[0]}".to_sym do
41
+ if args[1] != nil
42
+ return args[1]
43
+ else
44
+ return nil
45
+ end
46
+ end
47
+
48
+ # Set default, if one was provided
49
+ #set_value.call(args[1]) if args[1] != nil
50
+ define_method "__lazy_instantiator_#{args[0]}".to_sym do
51
+ return block
52
+ end
53
+
54
+ lazy_instantiation = <<EVAL
55
+ def __lazy_instantiation_#{args[0]}
56
+ return nil if __lazy_instantiator_#{args[0]}().nil?
57
+ instance_exec &__lazy_instantiator_#{args[0]}
58
+ end
59
+ EVAL
60
+
61
+ getter = <<EVAL
62
+ def #{args[0]}
63
+ @#{args[0]} = __lazy_instantiation_#{args[0]} if @#{args[0]}.nil? && __lazy_instantiator_#{args[0]} != nil
64
+ @#{args[0]} = __enforce_safety_#{args[0]}(__default_value_#{args[0]}) if @#{args[0]}.nil? && __default_value_#{args[0]} != nil
65
+ __enforce_safety_#{args[0]}(@#{args[0]})
66
+ end
67
+ EVAL
68
+
69
+ setter = <<EVAL
70
+ def #{args[0]}= value
71
+ @#{args[0]} = __enforce_safety_#{args[0]}(value)
72
+ end
73
+ EVAL
74
+
75
+ to_evaluate = lazy_instantiation
76
+ case type
77
+ when :accessor
78
+ to_evaluate << getter
79
+ to_evaluate << setter
80
+ when :reader
81
+ to_evaluate << getter
82
+ when :writer
83
+ to_evaluate << setter
84
+ end
85
+
86
+ self.class_eval to_evaluate
87
+ else
88
+ super
89
+ end
90
+ end
91
+ end
data/lib/safety.rb ADDED
@@ -0,0 +1,6 @@
1
+ require 'safety/safety_module'
2
+ module Safety
3
+ def self.included(base)
4
+ base.extend SafetyModule
5
+ end
6
+ end
metadata ADDED
@@ -0,0 +1,47 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: safety
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - James Lawrence Turner
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-03-06 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: Allows you to create type safe attributes in Ruby. Attributes may also
14
+ have default values or lazy instantiators
15
+ email: james@jameslawrenceturner.com
16
+ executables: []
17
+ extensions: []
18
+ extra_rdoc_files: []
19
+ files:
20
+ - lib/safety.rb
21
+ - lib/safety/safety_module.rb
22
+ - lib/safety/safety_attribute_helper.rb
23
+ homepage: http://github.com/jlturner/safety
24
+ licenses:
25
+ - MIT
26
+ metadata: {}
27
+ post_install_message:
28
+ rdoc_options: []
29
+ require_paths:
30
+ - lib
31
+ required_ruby_version: !ruby/object:Gem::Requirement
32
+ requirements:
33
+ - - '>='
34
+ - !ruby/object:Gem::Version
35
+ version: '0'
36
+ required_rubygems_version: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - '>='
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ requirements: []
42
+ rubyforge_project:
43
+ rubygems_version: 2.1.11
44
+ signing_key:
45
+ specification_version: 4
46
+ summary: Type Safety in Ruby
47
+ test_files: []