basic_service 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: e933ceced4c2ef5c0cef61cd59ab0883fbbcf0b0
4
+ data.tar.gz: 16e82a8d106a9bf259a1d2257f8fb6c0b2b54e55
5
+ SHA512:
6
+ metadata.gz: 1c27b98b3ca60fc38efc5446f093543071ebfb532f9a8a71f20bbf4670e7ea7483b937e7b0e27821b601fdf46ba79721fb03a0f5c59c37523dc1eaadda84a7b2
7
+ data.tar.gz: 111cf3a08adf541d1acf618cc322cc060cf4a08ce450dda0bf40cb60ce5f6fdde66e827fefb23d70519010ae22f59e5d05c84294627bbcf9e2bd72779d28019b
@@ -0,0 +1,14 @@
1
+ *.gem
2
+ *.rbc
3
+ /.config
4
+ /pkg/
5
+ /tests/tmp/
6
+ /tests/version_tmp/
7
+ /tmp/
8
+
9
+ ## Documentation cache and generated files:
10
+ /.yardoc/
11
+ /_yardoc/
12
+ /doc/
13
+ /rdoc/
14
+ .idea/
File without changes
data/Gemfile ADDED
File without changes
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2015 Julián Porta
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
22
+
@@ -0,0 +1,64 @@
1
+ # basic_service
2
+
3
+ Simple class for a simple service object implementation.
4
+
5
+ While there are a few different implementations for this pattern out there, this particular has a few unique (I think) features.
6
+
7
+ - It forces you to call `success()` or `error()` inside the `call()` method in order to access the `result?` method (or it will raise a `RuntimeError` if you haven't)
8
+
9
+ - It raises a `RuntimeError` if both `success()` and `error()` are called.
10
+
11
+ - It allows a return value independently of the `message` method.
12
+
13
+
14
+ ## Usage
15
+
16
+ ```ruby
17
+ # Gemfile
18
+ gem 'basic_service'
19
+
20
+
21
+ # my_service.rb
22
+ class MyService < Basic::Service
23
+
24
+ def call
25
+ first_param = args.pop #args contains the parameters passed to the call function
26
+ if first_param == "foo"
27
+ success('foo found') # call #success() to make #success? return true.
28
+ else
29
+ error('foo not found') # calling #error() will make #success? return false
30
+ end
31
+ "I'm done" #this return value is passed as result from the #call() method itself,
32
+ #independently from the #success? and #message methods
33
+ end
34
+
35
+ end
36
+
37
+ # somewhere_else.rb
38
+ require_relative 'my_service'
39
+
40
+ service = MyService.call('foo')
41
+
42
+ service.success?
43
+ # => true
44
+ service.message
45
+ # => "foo found"
46
+ service.error?
47
+ # => false
48
+ service.result
49
+ # => "I'm done"
50
+
51
+ service = MyService.call('bar')
52
+
53
+ service.success?
54
+ # => false
55
+ service.message
56
+ # => "foo not found"
57
+ service.error?
58
+ # => true
59
+ service.result
60
+ # => "I'm done"
61
+
62
+ ```
63
+
64
+ ## More to come
@@ -0,0 +1,11 @@
1
+ Gem::Specification.new do |s|
2
+ s.name = 'basic_service'
3
+ s.version = '0.0.1'
4
+ s.summary = 'Simple class for a simple service object implementation.'
5
+ s.authors = ['Julián Porta']
6
+ s.email = ['julian@porta.sh']
7
+ s.homepage = "http://github.com/Porta/basic_service/"
8
+ s.license = "MIT"
9
+ s.files = `git ls-files`.split("\n")
10
+ s.add_development_dependency "minitest", '~>5.5'
11
+ end
@@ -0,0 +1,48 @@
1
+ # encoding: UTF-8
2
+ module Basic
3
+ class Service
4
+
5
+ def self.call(args)
6
+ new(args).tap do |basic_service|
7
+ basic_service.instance_eval do
8
+ self.result = call
9
+ end
10
+ end
11
+ end
12
+
13
+ def success(str = '')
14
+ @success = true
15
+ @message = str
16
+ @pristine = true
17
+ end
18
+
19
+ def error(str = '')
20
+ @error = true
21
+ @message = str
22
+ @pristine = true
23
+ end
24
+
25
+ def initialize(*args)
26
+ @args = args
27
+ @success = false
28
+ @error = false
29
+ @pristine = false
30
+ end
31
+
32
+ attr_accessor :result
33
+ attr_reader :args, :message
34
+ private :result=, :args
35
+
36
+ # Defaults to the boolean'ed result of "call"
37
+ def success?
38
+ raise RuntimeError, "#success or #error should be called inside #call" unless @pristine
39
+ raise RuntimeError, "both #success and #error where called" if (@success && @error)
40
+ @success && !@error
41
+ end
42
+
43
+ # method error if call not defined
44
+ def call
45
+ raise NoMethodError, "Called undefined #call. You need to implement the method in the class: #{self.class.name}"
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,4 @@
1
+ all: test
2
+
3
+ test:
4
+ ruby ./tests/test_class.rb
@@ -0,0 +1,6 @@
1
+ class BadTest < Basic::Service
2
+ def call
3
+ something = args.pop
4
+ "this is the result"
5
+ end
6
+ end
@@ -0,0 +1,11 @@
1
+ class GoodTest < Basic::Service
2
+ def call
3
+ something = args.pop
4
+ if something == 'mimimi'
5
+ success("success is great")
6
+ else
7
+ error("error is for loosers")
8
+ end
9
+ "this is the result"
10
+ end
11
+ end
@@ -0,0 +1,49 @@
1
+ #! /usr/bin/env ruby
2
+ require 'minitest/autorun'
3
+ require_relative '../lib/basic_service'
4
+
5
+ require_relative './good_test.rb'
6
+ require_relative './bad_test.rb'
7
+ require_relative './ugly_test.rb'
8
+
9
+ class TestClass < Minitest::Test
10
+
11
+ def test_success_should_work
12
+ test = GoodTest.call('mimimi')
13
+ assert_equal test.success?, true
14
+ assert_equal test.message, "success is great"
15
+ end
16
+
17
+ def test_error_should_work
18
+ test = GoodTest.call('mandanga')
19
+ assert_equal test.success?, false
20
+ assert_equal test.message, "error is for loosers"
21
+ end
22
+
23
+ def test_result
24
+ test = GoodTest.call('mimimi')
25
+ assert_equal test.result, "this is the result"
26
+ end
27
+
28
+
29
+ def test_raise_if_not_pristine
30
+ test = BadTest.call('mimimi')
31
+ exception = assert_raises(RuntimeError) { test.success? }
32
+ assert_equal("#success or #error should be called inside #call", exception.message)
33
+ end
34
+
35
+ def test_raise_if_success_and_error
36
+ test = UglyTest.call('Pistola')
37
+ exception = assert_raises(RuntimeError) { test.success? }
38
+ assert_equal("both #success and #error where called", exception.message)
39
+ end
40
+
41
+
42
+ def test_instance_cases
43
+ mimimi = GoodTest.call('mimimi')
44
+ foo = GoodTest.call('foo')
45
+ refute_equal mimimi.object_id, foo.object_id
46
+ refute_equal mimimi.message, foo.message
47
+ end
48
+
49
+ end
@@ -0,0 +1,8 @@
1
+ class UglyTest < Basic::Service
2
+ def call
3
+ something = args.pop
4
+ success("success is great")
5
+ error("error is for loosers")
6
+ "this is the result"
7
+ end
8
+ end
metadata ADDED
@@ -0,0 +1,70 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: basic_service
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Julián Porta
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2015-03-24 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: minitest
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '5.5'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '5.5'
27
+ description:
28
+ email:
29
+ - julian@porta.sh
30
+ executables: []
31
+ extensions: []
32
+ extra_rdoc_files: []
33
+ files:
34
+ - ".gitignore"
35
+ - CHANGELOG.md
36
+ - Gemfile
37
+ - LICENSE
38
+ - README.md
39
+ - basic_service.gemspec
40
+ - lib/basic_service.rb
41
+ - makefile
42
+ - tests/bad_test.rb
43
+ - tests/good_test.rb
44
+ - tests/test_class.rb
45
+ - tests/ugly_test.rb
46
+ homepage: http://github.com/Porta/basic_service/
47
+ licenses:
48
+ - MIT
49
+ metadata: {}
50
+ post_install_message:
51
+ rdoc_options: []
52
+ require_paths:
53
+ - lib
54
+ required_ruby_version: !ruby/object:Gem::Requirement
55
+ requirements:
56
+ - - ">="
57
+ - !ruby/object:Gem::Version
58
+ version: '0'
59
+ required_rubygems_version: !ruby/object:Gem::Requirement
60
+ requirements:
61
+ - - ">="
62
+ - !ruby/object:Gem::Version
63
+ version: '0'
64
+ requirements: []
65
+ rubyforge_project:
66
+ rubygems_version: 2.2.2
67
+ signing_key:
68
+ specification_version: 4
69
+ summary: Simple class for a simple service object implementation.
70
+ test_files: []