glimmer-dsl-specification 0.0.1

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
+ SHA256:
3
+ metadata.gz: 5a7d09deaf02f95b8eb86bab872f38f977aeb76d958dbf201d80ad6b57008316
4
+ data.tar.gz: 928737b70dffe90683005f15b1f8eecd01e0e43fd0ff5ace33522acf895a15f8
5
+ SHA512:
6
+ metadata.gz: 8615c3c1b8ce1e83025d0e5be9aff6de42fcb613987764287236d81785dfff10ffdfcc994ebd77329a3bd9eb515b9a58d9edfd83cb935bf869f2c957d8fc966a
7
+ data.tar.gz: e0b5cfce47413fc9c9c88f1b1587b1133bd5b636d3d5a7167dec9dfe7ffba4f113fe495d12f4ea77719c5c292ddaa145c28be42fcc7c8562996a37979b42e864
data/CHANGELOG.md ADDED
@@ -0,0 +1,5 @@
1
+ # Change Log
2
+
3
+ ## 0.0.1
4
+
5
+ - Initial version with support for `specification`, `use_case`, `scenario`, and `fact` keywords.
data/LICENSE.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2021 Andy Maleh
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,260 @@
1
+ # [<img src="https://raw.githubusercontent.com/AndyObtiva/glimmer/master/images/glimmer-logo-hi-res.png" height=85 />](https://github.com/AndyObtiva/glimmer) Glimmer DSL for Specification 0.0.1
2
+ ## Pure Ruby Declarative Use Case Specification and Automated Verification
3
+ [![Gem Version](https://badge.fury.io/rb/glimmer-dsl-specification.svg)](http://badge.fury.io/rb/glimmer-dsl-specification)
4
+ [![Join the chat at https://gitter.im/AndyObtiva/glimmer](https://badges.gitter.im/AndyObtiva/glimmer.svg)](https://gitter.im/AndyObtiva/glimmer?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
5
+
6
+ Despite Ruby's highly expressive nature, all testing toolkits written in Ruby are either imperative (e.g. using `assert` or `expect`), thus losing expressiveness and focusing software engineers on the wrong thing, or mix non-Ruby code with Ruby (e.g. `cucumber` & `gherkin`), thus missing out on the simplicity of Ruby.
7
+
8
+ Glimmer DSL for Specification aims to provide a simple minimalistic and noun-based declarative syntax. No more verbs! It is time to think declaratively not imperatively!
9
+
10
+ As such, software engineers focus on [Requirements Specification](https://en.wikipedia.org/wiki/Software_requirements_specification) at the [Use Case](https://en.wikipedia.org/wiki/Use_case) level whereby each use case is composed of multiple scenarios. No need to specify scenario steps. The code is the steps!!!
11
+
12
+ Also, no need for extra DSL constructs for making comparisons in verification statements. Just use plain old Ruby and let the library figure out the rest!
13
+
14
+ For example:
15
+
16
+ ```ruby
17
+ scenario 'Same-content strings are equal' do
18
+ 'string' == 'string'
19
+ end
20
+ ```
21
+
22
+ That tells me the whole story without needing either `assert` or `expect`. It just contains plain Ruby code for performing the comparison.
23
+
24
+ Another example:
25
+
26
+ ```ruby
27
+ scenario 'person name consists of first name and last name' do
28
+ person = Person.new(first_name: 'Bob', last_name: 'Winfrey')
29
+
30
+ fact { person.first_name == 'Bob' }
31
+ fact { person.last_name == 'Winfrey' }
32
+ person.name == 'Bob Winfrey'
33
+ end
34
+ ```
35
+
36
+ That states a few extra facts in addition to the last statement in the scenario denoting the final verification.
37
+
38
+ ## Full Example
39
+
40
+ This library was written specification-first utilizing itself. In fact, here is the initial specification of [glimmer-dsl-specification](https://rubygems.org/gems/glimmer-dsl-specification) to prove it!
41
+
42
+ ```ruby
43
+ require 'glimmer-dsl-specification'
44
+
45
+ class Person
46
+ attr_reader :first_name, :last_name
47
+
48
+ def initialize(first_name: , last_name: )
49
+ @first_name = first_name
50
+ @last_name = last_name
51
+ end
52
+
53
+ def name
54
+ "#{first_name} #{last_name}"
55
+ end
56
+ end
57
+
58
+ module Glimmer::Specification
59
+ specification('Glimmer DSL for Specification') {
60
+ use_case('Compare Two Objects for Equality') {
61
+ scenario 'Same-content strings are equal' do
62
+ 'string' == 'string'
63
+ end
64
+
65
+ scenario 'Different-content strings are not equal' do
66
+ 'string1' != 'string2'
67
+ end
68
+
69
+ scenario 'Same-number integers are equal' do
70
+ 1 == 1
71
+ end
72
+
73
+ scenario 'Different-number integers are not equal' do
74
+ 1 != 2
75
+ end
76
+ }
77
+
78
+ use_case('Verify Multiple Facts') {
79
+ scenario 'person name consists of first name and last name' do
80
+ person = Person.new(first_name: 'Bob', last_name: 'Winfrey')
81
+
82
+ fact { person.first_name == 'Bob' }
83
+ fact { person.last_name == 'Winfrey' }
84
+ person.name == 'Bob Winfrey'
85
+ end
86
+ }
87
+ }
88
+ end
89
+ ```
90
+
91
+ Output (colored in actual usage):
92
+
93
+ ```
94
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Same-content strings are equal
95
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Different-content strings are not equal
96
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Same-number integers are equal
97
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Different-number integers are not equal
98
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality
99
+ VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts - person name consists of first name and last name - fact { person.first_name == 'Bob' }
100
+ VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts - person name consists of first name and last name - fact { person.last_name == 'Winfrey' }
101
+ VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts - person name consists of first name and last name
102
+ VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts
103
+ VERIFIED: Glimmer DSL for Specification
104
+ ```
105
+
106
+ Failure output when fudging some code (colored in actual usage):
107
+
108
+ ```
109
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Same-content strings are equal
110
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Different-content strings are not equal
111
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Same-number integers are equal
112
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality - Different-number integers are not equal
113
+ VERIFIED: Glimmer DSL for Specification - Compare Two Objects for Equality
114
+ VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts - person name consists of first name and last name - fact { person.first_name == 'Bob' }
115
+ VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts - person name consists of first name and last name - fact { person.last_name == 'Winfrey' }
116
+ NOT VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts - person name consists of first name and last name
117
+ NOT VERIFIED: Glimmer DSL for Specification - Verify Multiple Facts
118
+ NOT VERIFIED: Glimmer DSL for Specification
119
+ ```
120
+
121
+ ## Usage
122
+
123
+ 1 - Include in `Gemfile`
124
+
125
+ ```ruby
126
+ gem 'glimmer-dsl-specification', '~> 0.0.1'
127
+ ```
128
+
129
+ And, run:
130
+
131
+ ```
132
+ bundle
133
+ ```
134
+
135
+ 2 - Create specification files with `_specification.rb` extension under `specification` directory utilizing `specification`, `use_case`, `scenario`, and `fact` keywords explained in [DSL](#dsl) section by adding require statement on top and inserting specification/verification code in `Glimmer::Specification` module:
136
+
137
+ ```ruby
138
+ require 'glimmer-dsl-specification'
139
+
140
+ module Glimmer::Specification
141
+ specification('title of specification') {
142
+ use_case('title of use case') {
143
+ scenario('second scenario') {
144
+ fact { something2 == something_else2 } # optional
145
+ fact { something3 != something_else3 } # optional
146
+ fact { something1.include?(something_else1) } # optional
147
+ something == something_else # final verification can be a fact if preferred
148
+ }
149
+ }
150
+ }
151
+ end
152
+ ```
153
+
154
+ 3 - Run a specification directly with ruby:
155
+
156
+ ```
157
+ ruby specification/lib/glimmer-dsl-specification_specification.rb
158
+ ```
159
+
160
+ 4 - Alternatively run `rake verify` task assuming you have `rake` gem installed/configured in `Gemfile`:
161
+
162
+ ```
163
+ rake verify
164
+ ```
165
+
166
+ It is also recommended that you add the following lines to your `Rakefile`:
167
+
168
+ ```ruby
169
+ require 'glimmer-dsl-specification' # unless loaded by Bundler
170
+ require 'glimmer/specification/rake_tasks'
171
+
172
+ task :default => :verify
173
+ ```
174
+
175
+ That way, you can simply run:
176
+
177
+ ```
178
+ rake
179
+ ```
180
+
181
+ ## DSL
182
+
183
+ The Domain Specific Language consists of the following keywords simply nested under `Glimmer::Specification` module (to avoid namespace pollution).
184
+
185
+ This library highly emphasizes declarative specification, so it avoids "test" jargon including "pass" or "fail" and unit-test jargon including "class", "method", "attribute", or "assert" as that is not the ultimate aim of the library, yet specifying application requirements.
186
+
187
+ Specifications do not care about what specific "classes" or "methods" are executed. They only care about meeting the verification criteria.
188
+
189
+ ### specification
190
+
191
+ (nested directly under `Glimmer::Specification` module.)
192
+
193
+ `specification(title)` is the top-level keyword denoting a requirement specification.
194
+
195
+ ### use_case
196
+
197
+ (nested under `specification`)
198
+
199
+ `use_case(title)` represents one or more use cases that the requirement specification consists of
200
+
201
+ ### scenario
202
+
203
+ (nested under `use_case` or directly under `specification` for very simple cases)
204
+
205
+ `scenario(title)` represents one scenario in a use case that performs a verification by setting up preconditions, performing an action, and returning the final result as a postconditition boolean or alternatively relying on nested `fact` occurances.
206
+
207
+ ### fact
208
+
209
+ (nested under `scenario`)
210
+
211
+ `fact {}` states a fact embodied by a boolean result for the passed block of code.
212
+
213
+ ## Process
214
+
215
+ [Glimmer Process](https://github.com/AndyObtiva/glimmer/blob/master/PROCESS.md)
216
+
217
+ ## Resources
218
+
219
+ - [Code Master Blog](https://andymaleh.blogspot.com/search/label/glimmer)
220
+
221
+ ## Help
222
+
223
+ ### Issues
224
+
225
+ If you encounter [issues](https://github.com/AndyObtiva/glimmer-dsl-specification/issues) that are not reported, discover missing features that are not mentioned in [TODO.md](TODO.md), or think up better ways to write declarative automated tests, you may submit an [issue](https://github.com/AndyObtiva/glimmer-dsl-libui/issues/new) or [pull request](https://github.com/AndyObtiva/glimmer-dsl-specification/compare) on [GitHub](https://github.com). In the meantime, you may try an older version of the [Ruby gem](https://rubygems.org/gems/glimmer-dsl-specification) in case it works better for you until your issues are resolved.
226
+
227
+ ### Chat
228
+
229
+ If you need live help, try to [![Join the chat at https://gitter.im/AndyObtiva/glimmer](https://badges.gitter.im/AndyObtiva/glimmer.svg)](https://gitter.im/AndyObtiva/glimmer?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
230
+
231
+ ## TODO
232
+
233
+ [TODO.md](TODO.md)
234
+
235
+ ## Change Log
236
+
237
+ [CHANGELOG.md](CHANGELOG.md)
238
+
239
+ ## Contributing
240
+
241
+ - Check out the latest master to make sure the feature hasn't been
242
+ implemented or the bug hasn't been fixed yet.
243
+ - Check out the issue tracker to make sure someone already hasn't
244
+ requested it and/or contributed it.
245
+ - Fork the project.
246
+ - Start a feature/bugfix branch.
247
+ - Commit and push until you are happy with your contribution.
248
+ - Make sure to add tests for it. This is important so I don't break it
249
+ in a future version unintentionally.
250
+ - Please try not to mess with the Rakefile, version, or history. If
251
+ you want to have your own version, or is otherwise necessary, that
252
+ is fine, but please isolate to its own commit so I can cherry-pick
253
+ around it.
254
+
255
+ ## Copyright
256
+
257
+ [MIT](LICENSE.txt)
258
+
259
+ Copyright (c) 2021 Andy Maleh. See
260
+ [LICENSE.txt](LICENSE.txt) for further details.
data/TODO.md ADDED
@@ -0,0 +1,4 @@
1
+ # TODO
2
+
3
+ - Ensure that each element is only nestable under specific types of elements (e.g. `use_case` can go under `specification` only and `fact` can go under `scenario` only)
4
+ - Support setting up common `scenario`, `use case` or `specification` preconditions by adding code directly under their block or inside a `before`/`after` block
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.0.1
@@ -0,0 +1,67 @@
1
+ # Generated by juwelier
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Juwelier::Tasks in Rakefile, and run 'rake gemspec'
4
+ # -*- encoding: utf-8 -*-
5
+ # stub: glimmer-dsl-specification 0.0.1 ruby lib
6
+
7
+ Gem::Specification.new do |s|
8
+ s.name = "glimmer-dsl-specification".freeze
9
+ s.version = "0.0.1"
10
+
11
+ s.required_rubygems_version = Gem::Requirement.new(">= 0".freeze) if s.respond_to? :required_rubygems_version=
12
+ s.require_paths = ["lib".freeze]
13
+ s.authors = ["Andy Maleh".freeze]
14
+ s.date = "2021-11-23"
15
+ s.description = "Glimmer DSL for Specification - Pure Ruby Declarative Use Case Specification and Automated Verification".freeze
16
+ s.email = "andy.am@gmail.com".freeze
17
+ s.extra_rdoc_files = [
18
+ "CHANGELOG.md",
19
+ "LICENSE.txt",
20
+ "README.md"
21
+ ]
22
+ s.files = [
23
+ "CHANGELOG.md",
24
+ "LICENSE.txt",
25
+ "README.md",
26
+ "TODO.md",
27
+ "VERSION",
28
+ "glimmer-dsl-specification.gemspec",
29
+ "lib/glimmer-dsl-specification.rb",
30
+ "lib/glimmer/dsl/specification/attribute_expression.rb",
31
+ "lib/glimmer/dsl/specification/block_method_expression.rb",
32
+ "lib/glimmer/dsl/specification/dsl.rb",
33
+ "lib/glimmer/dsl/specification/element_expression.rb",
34
+ "lib/glimmer/specification.rb",
35
+ "lib/glimmer/specification/element.rb",
36
+ "lib/glimmer/specification/element/fact.rb",
37
+ "lib/glimmer/specification/element/scenario.rb",
38
+ "lib/glimmer/specification/element/specification.rb",
39
+ "lib/glimmer/specification/element/use_case.rb",
40
+ "lib/glimmer/specification/rake_tasks.rb"
41
+ ]
42
+ s.homepage = "http://github.com/AndyObtiva/glimmer-dsl-specification".freeze
43
+ s.licenses = ["MIT".freeze]
44
+ s.rubygems_version = "3.2.31".freeze
45
+ s.summary = "Glimmer DSL for Specification".freeze
46
+
47
+ if s.respond_to? :specification_version then
48
+ s.specification_version = 4
49
+ end
50
+
51
+ if s.respond_to? :add_runtime_dependency then
52
+ s.add_runtime_dependency(%q<glimmer>.freeze, ["~> 2.5.1"])
53
+ s.add_runtime_dependency(%q<puts_debuggerer>.freeze, ["~> 0.13.1"])
54
+ s.add_runtime_dependency(%q<colours>.freeze, ["~> 0.6.1"])
55
+ s.add_development_dependency(%q<juwelier>.freeze, ["~> 2.1.0"])
56
+ s.add_development_dependency(%q<rake-tui>.freeze, ["> 0"])
57
+ s.add_development_dependency(%q<glimmer-dsl-specification>.freeze, [">= 0"])
58
+ else
59
+ s.add_dependency(%q<glimmer>.freeze, ["~> 2.5.1"])
60
+ s.add_dependency(%q<puts_debuggerer>.freeze, ["~> 0.13.1"])
61
+ s.add_dependency(%q<colours>.freeze, ["~> 0.6.1"])
62
+ s.add_dependency(%q<juwelier>.freeze, ["~> 2.1.0"])
63
+ s.add_dependency(%q<rake-tui>.freeze, ["> 0"])
64
+ s.add_dependency(%q<glimmer-dsl-specification>.freeze, [">= 0"])
65
+ end
66
+ end
67
+
@@ -0,0 +1,17 @@
1
+ require 'glimmer/dsl/expression'
2
+
3
+ module Glimmer
4
+ module DSL
5
+ module Specification
6
+ class AttributeExpression < Expression
7
+ def can_interpret?(parent, keyword, *args, &block)
8
+ parent.respond_to?("#{keyword}=") && !args.empty? && block.nil?
9
+ end
10
+
11
+ def interpret(parent, keyword, *args, &block)
12
+ parent.send("#{keyword}=", *args)
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,18 @@
1
+ require 'glimmer/dsl/expression'
2
+
3
+ module Glimmer
4
+ module DSL
5
+ module Specification
6
+ class BlockMethodExpression < Expression
7
+ def can_interpret?(parent, keyword, *args, &block)
8
+ parent.respond_to?(keyword) and
9
+ block_given?
10
+ end
11
+
12
+ def interpret(parent, keyword, *args, &block)
13
+ parent.send("#{keyword}", &block)
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,17 @@
1
+ require 'glimmer/dsl/engine'
2
+ Dir[File.expand_path('*_expression.rb', __dir__)].each {|f| require f}
3
+
4
+ module Glimmer
5
+ module DSL
6
+ module Specification
7
+ Engine.add_dynamic_expressions(
8
+ Specification,
9
+ %w[
10
+ block_method
11
+ attribute
12
+ element
13
+ ]
14
+ )
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,29 @@
1
+ require 'glimmer/dsl/expression'
2
+ require 'glimmer/dsl/parent_expression'
3
+ require 'glimmer/dsl/top_level_expression'
4
+ require_relative '../../specification/element'
5
+
6
+ module Glimmer
7
+ module DSL
8
+ module Specification
9
+ class ElementExpression < Expression
10
+ include ParentExpression
11
+ include TopLevelExpression
12
+
13
+ def can_interpret?(parent, keyword, *args, &block)
14
+ Glimmer::Specification::Element.element_exist?(keyword)
15
+ end
16
+
17
+ def interpret(parent, keyword, *args, &block)
18
+ Glimmer::Specification::Element.element_class(keyword).new(parent, keyword, *args, &block) unless parent&.content_added?
19
+ end
20
+
21
+ def add_content(element, keyword, *args, &block)
22
+ result = super unless element.executable? && !element.content_added?
23
+ element.post_add_content
24
+ result
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
@@ -0,0 +1,23 @@
1
+ module Glimmer
2
+ module Specification
3
+ class Element
4
+ class Fact < Element
5
+ def initialize(parent, keyword, *args, &block)
6
+ @executable = true
7
+ super
8
+ source_code = PutsDebuggerer::SourceFile.new(@block.source_location.first).source(1, @block.source_location.last)
9
+ @title = source_code.strip
10
+ end
11
+
12
+ def run
13
+ @verified = @block.call
14
+ if @verified
15
+ puts Colours::GREEN + "VERIFIED: #{to_s}"
16
+ else
17
+ puts Colours::RED + "NOT VERIFIED: #{to_s}"
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,29 @@
1
+ module Glimmer
2
+ module Specification
3
+ class Element
4
+ class Scenario < Element
5
+ def initialize(parent, keyword, *args, &block)
6
+ @executable = true
7
+ super
8
+ end
9
+
10
+ def fact(&block)
11
+ new_fact = Fact.new(self, 'fact', [], &block)
12
+ new_fact.run
13
+ @verified &&= new_fact.verified?
14
+ end
15
+
16
+ def run
17
+ @verified = true
18
+ own_block_verified = Glimmer::DSL::Engine.add_content(self, Glimmer::DSL::Specification::ElementExpression.new, @keyword, &@block)
19
+ @verified &&= own_block_verified if own_block_verified.is_a?(TrueClass) || own_block_verified.is_a?(FalseClass)
20
+ if @verified
21
+ puts Colours::GREEN + "VERIFIED: #{to_s}"
22
+ else
23
+ puts Colours::RED + "NOT VERIFIED: #{to_s}"
24
+ end
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
@@ -0,0 +1,12 @@
1
+ module Glimmer
2
+ module Specification
3
+ class Element
4
+ class Specification < Element
5
+ def post_add_content
6
+ run
7
+ super
8
+ end
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,8 @@
1
+ module Glimmer
2
+ module Specification
3
+ class Element
4
+ class UseCase < Element
5
+ end
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,100 @@
1
+ module Glimmer
2
+ module Specification
3
+ class Element
4
+ class << self
5
+ def element_exist?(keyword)
6
+ constants.include?(element_class_name(keyword)) && element_class(keyword).respond_to?(:new)
7
+ end
8
+
9
+ def element_class(keyword)
10
+ const_get(element_class_name(keyword))
11
+ end
12
+
13
+ def element_class_name(keyword)
14
+ keyword.to_s.camelcase(:upper).to_sym
15
+ end
16
+ end
17
+
18
+ attr_reader :parent, :keyword, :args, :block
19
+ attr_accessor :title
20
+
21
+ def initialize(parent, keyword, *args, &block)
22
+ @parent = parent
23
+ @keyword = keyword
24
+ @args = args
25
+ @title = @args.first
26
+ @block = block
27
+ @children = children
28
+ @parent&.post_initialize_child(self)
29
+ post_add_content if @block.nil?
30
+ end
31
+
32
+ def children
33
+ @children ||= []
34
+ end
35
+
36
+ def verified?
37
+ @verified
38
+ end
39
+
40
+ def content_added?
41
+ @content_added
42
+ end
43
+
44
+ # subclasses may override (e.g. Scenario)
45
+ def executable?
46
+ !!@executable
47
+ end
48
+
49
+ def scenarios
50
+ children.map do |child|
51
+ child.is_a?(Scenario) ? child : child.scenarios
52
+ end.flatten
53
+ end
54
+
55
+ # ancestors including self ordered from closest to farthest
56
+ def ancestors
57
+ if @ancestors.nil?
58
+ @ancestors = [self]
59
+ current = self
60
+ while current.parent
61
+ current = current.parent
62
+ @ancestors << current
63
+ end
64
+ end
65
+ @ancestors
66
+ end
67
+
68
+ def post_initialize_child(child)
69
+ children << child
70
+ end
71
+
72
+ def post_add_content
73
+ # No Op (subclasses may override to do something at the closing of the element)
74
+ @content_added = true
75
+ end
76
+
77
+ # Enables re-opening content and adding new shapes
78
+ def content(&block)
79
+ Glimmer::DSL::Engine.add_content(self, Glimmer::DSL::Specification::ElementExpression.new, @keyword, &block)
80
+ end
81
+
82
+ # runs children by default. subclasses may override.
83
+ def run
84
+ children.each(&:run)
85
+ @verified = children.all?(&:verified?)
86
+ if @verified
87
+ puts Colours::GREEN + "VERIFIED: #{to_s}"
88
+ else
89
+ puts Colours::RED + "NOT VERIFIED: #{to_s}"
90
+ end
91
+ end
92
+
93
+ def to_s
94
+ ancestors.reverse.map(&:title).join(' - ')
95
+ end
96
+ end
97
+ end
98
+ end
99
+
100
+ Dir[File.expand_path('./element/*.rb', __dir__)].each {|f| require f}
@@ -0,0 +1,6 @@
1
+ desc "Verify Glimmer Specifications"
2
+ task :verify do
3
+ Dir['specification/**/*_specification.rb'].each do |specification_file|
4
+ load specification_file
5
+ end
6
+ end
@@ -0,0 +1,5 @@
1
+ module Glimmer
2
+ module Specification
3
+ extend Glimmer
4
+ end
5
+ end
@@ -0,0 +1,29 @@
1
+ # Copyright (c) 2021 Andy Maleh
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining
4
+ # a copy of this software and associated documentation files (the
5
+ # "Software"), to deal in the Software without restriction, including
6
+ # without limitation the rights to use, copy, modify, merge, publish,
7
+ # distribute, sublicense, and/or sell copies of the Software, and to
8
+ # permit persons to whom the Software is furnished to do so, subject to
9
+ # the following conditions:
10
+ #
11
+ # The above copyright notice and this permission notice shall be
12
+ # included in all copies or substantial portions of the Software.
13
+ #
14
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
+
22
+ $LOAD_PATH.unshift(File.expand_path('.', __dir__))
23
+
24
+ require 'facets/string/camelcase'
25
+ require 'puts_debuggerer'
26
+ require 'colours'
27
+ require 'glimmer'
28
+ require 'glimmer/dsl/specification/dsl'
29
+ require 'glimmer/specification'
metadata ADDED
@@ -0,0 +1,148 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: glimmer-dsl-specification
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Andy Maleh
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2021-11-23 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: glimmer
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: 2.5.1
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: 2.5.1
27
+ - !ruby/object:Gem::Dependency
28
+ name: puts_debuggerer
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: 0.13.1
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: 0.13.1
41
+ - !ruby/object:Gem::Dependency
42
+ name: colours
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: 0.6.1
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: 0.6.1
55
+ - !ruby/object:Gem::Dependency
56
+ name: juwelier
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: 2.1.0
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: 2.1.0
69
+ - !ruby/object:Gem::Dependency
70
+ name: rake-tui
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">"
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">"
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: glimmer-dsl-specification
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ description: Glimmer DSL for Specification - Pure Ruby Declarative Use Case Specification
98
+ and Automated Verification
99
+ email: andy.am@gmail.com
100
+ executables: []
101
+ extensions: []
102
+ extra_rdoc_files:
103
+ - CHANGELOG.md
104
+ - LICENSE.txt
105
+ - README.md
106
+ files:
107
+ - CHANGELOG.md
108
+ - LICENSE.txt
109
+ - README.md
110
+ - TODO.md
111
+ - VERSION
112
+ - glimmer-dsl-specification.gemspec
113
+ - lib/glimmer-dsl-specification.rb
114
+ - lib/glimmer/dsl/specification/attribute_expression.rb
115
+ - lib/glimmer/dsl/specification/block_method_expression.rb
116
+ - lib/glimmer/dsl/specification/dsl.rb
117
+ - lib/glimmer/dsl/specification/element_expression.rb
118
+ - lib/glimmer/specification.rb
119
+ - lib/glimmer/specification/element.rb
120
+ - lib/glimmer/specification/element/fact.rb
121
+ - lib/glimmer/specification/element/scenario.rb
122
+ - lib/glimmer/specification/element/specification.rb
123
+ - lib/glimmer/specification/element/use_case.rb
124
+ - lib/glimmer/specification/rake_tasks.rb
125
+ homepage: http://github.com/AndyObtiva/glimmer-dsl-specification
126
+ licenses:
127
+ - MIT
128
+ metadata: {}
129
+ post_install_message:
130
+ rdoc_options: []
131
+ require_paths:
132
+ - lib
133
+ required_ruby_version: !ruby/object:Gem::Requirement
134
+ requirements:
135
+ - - ">="
136
+ - !ruby/object:Gem::Version
137
+ version: '0'
138
+ required_rubygems_version: !ruby/object:Gem::Requirement
139
+ requirements:
140
+ - - ">="
141
+ - !ruby/object:Gem::Version
142
+ version: '0'
143
+ requirements: []
144
+ rubygems_version: 3.2.31
145
+ signing_key:
146
+ specification_version: 4
147
+ summary: Glimmer DSL for Specification
148
+ test_files: []