kamaze-project 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (106) hide show
  1. checksums.yaml +7 -0
  2. data/.yardopts +18 -0
  3. data/bin/plop +5 -0
  4. data/lib/kamaze-project.rb +39 -0
  5. data/lib/kamaze/project.rb +155 -0
  6. data/lib/kamaze/project/boot/core_ext.rb +16 -0
  7. data/lib/kamaze/project/boot/listen.rb +38 -0
  8. data/lib/kamaze/project/concern.rb +13 -0
  9. data/lib/kamaze/project/concern/cli.rb +53 -0
  10. data/lib/kamaze/project/concern/cli/with_exit_on_failure.rb +36 -0
  11. data/lib/kamaze/project/concern/env.rb +63 -0
  12. data/lib/kamaze/project/concern/helper.rb +20 -0
  13. data/lib/kamaze/project/concern/mode.rb +19 -0
  14. data/lib/kamaze/project/concern/observable.rb +132 -0
  15. data/lib/kamaze/project/concern/sh.rb +91 -0
  16. data/lib/kamaze/project/concern/tasks.rb +55 -0
  17. data/lib/kamaze/project/concern/tools.rb +27 -0
  18. data/lib/kamaze/project/config.rb +58 -0
  19. data/lib/kamaze/project/core_ext/object.rb +27 -0
  20. data/lib/kamaze/project/core_ext/pp.rb +28 -0
  21. data/lib/kamaze/project/debug.rb +136 -0
  22. data/lib/kamaze/project/dsl.rb +16 -0
  23. data/lib/kamaze/project/dsl/definition.rb +43 -0
  24. data/lib/kamaze/project/dsl/setup.rb +11 -0
  25. data/lib/kamaze/project/helper.rb +63 -0
  26. data/lib/kamaze/project/helper/inflector.rb +44 -0
  27. data/lib/kamaze/project/helper/project.rb +34 -0
  28. data/lib/kamaze/project/helper/project/config.rb +25 -0
  29. data/lib/kamaze/project/observable.rb +20 -0
  30. data/lib/kamaze/project/observer.rb +37 -0
  31. data/lib/kamaze/project/resources/Vagrantfile +128 -0
  32. data/lib/kamaze/project/resources/config/tools.yml +15 -0
  33. data/lib/kamaze/project/struct.rb +34 -0
  34. data/lib/kamaze/project/tasks/cs.rb +23 -0
  35. data/lib/kamaze/project/tasks/cs/control.rb +17 -0
  36. data/lib/kamaze/project/tasks/cs/correct.rb +17 -0
  37. data/lib/kamaze/project/tasks/cs/pre_commit.rb +66 -0
  38. data/lib/kamaze/project/tasks/doc.rb +21 -0
  39. data/lib/kamaze/project/tasks/doc/watch.rb +41 -0
  40. data/lib/kamaze/project/tasks/gem.rb +14 -0
  41. data/lib/kamaze/project/tasks/gem/build.rb +34 -0
  42. data/lib/kamaze/project/tasks/gem/compile.rb +30 -0
  43. data/lib/kamaze/project/tasks/gem/gemspec.rb +20 -0
  44. data/lib/kamaze/project/tasks/gem/install.rb +32 -0
  45. data/lib/kamaze/project/tasks/gem/push.rb +27 -0
  46. data/lib/kamaze/project/tasks/misc/gitignore.rb +29 -0
  47. data/lib/kamaze/project/tasks/shell.rb +17 -0
  48. data/lib/kamaze/project/tasks/sources.rb +6 -0
  49. data/lib/kamaze/project/tasks/sources/license.rb +35 -0
  50. data/lib/kamaze/project/tasks/test.rb +16 -0
  51. data/lib/kamaze/project/tasks/vagrant.rb +71 -0
  52. data/lib/kamaze/project/tasks/version/edit.rb +16 -0
  53. data/lib/kamaze/project/tools.rb +18 -0
  54. data/lib/kamaze/project/tools/base_tool.rb +55 -0
  55. data/lib/kamaze/project/tools/console.rb +48 -0
  56. data/lib/kamaze/project/tools/console/output.rb +120 -0
  57. data/lib/kamaze/project/tools/console/output/buffer.rb +48 -0
  58. data/lib/kamaze/project/tools/gemspec.rb +33 -0
  59. data/lib/kamaze/project/tools/gemspec/builder.rb +99 -0
  60. data/lib/kamaze/project/tools/gemspec/concern.rb +13 -0
  61. data/lib/kamaze/project/tools/gemspec/concern/reading.rb +49 -0
  62. data/lib/kamaze/project/tools/gemspec/packager.rb +67 -0
  63. data/lib/kamaze/project/tools/gemspec/packer.rb +89 -0
  64. data/lib/kamaze/project/tools/gemspec/packer/command.rb +143 -0
  65. data/lib/kamaze/project/tools/gemspec/reader.rb +70 -0
  66. data/lib/kamaze/project/tools/gemspec/reader/decorator.rb +78 -0
  67. data/lib/kamaze/project/tools/gemspec/writer.rb +127 -0
  68. data/lib/kamaze/project/tools/gemspec/writer/dep_gen.rb +61 -0
  69. data/lib/kamaze/project/tools/gemspec/writer/dependency.rb +104 -0
  70. data/lib/kamaze/project/tools/git.rb +95 -0
  71. data/lib/kamaze/project/tools/git/hooks.rb +66 -0
  72. data/lib/kamaze/project/tools/git/hooks/base_hook.rb +33 -0
  73. data/lib/kamaze/project/tools/git/hooks/pre_commit.rb +81 -0
  74. data/lib/kamaze/project/tools/git/status.rb +101 -0
  75. data/lib/kamaze/project/tools/git/status/decorator.rb +39 -0
  76. data/lib/kamaze/project/tools/git/status/file.rb +180 -0
  77. data/lib/kamaze/project/tools/git/status/files_array.rb +39 -0
  78. data/lib/kamaze/project/tools/git/status/index.rb +77 -0
  79. data/lib/kamaze/project/tools/git/status/worktree.rb +19 -0
  80. data/lib/kamaze/project/tools/git/util.rb +35 -0
  81. data/lib/kamaze/project/tools/licenser.rb +197 -0
  82. data/lib/kamaze/project/tools/packager.rb +86 -0
  83. data/lib/kamaze/project/tools/packager/filesystem.rb +178 -0
  84. data/lib/kamaze/project/tools/packager/filesystem/operator.rb +83 -0
  85. data/lib/kamaze/project/tools/packager/filesystem/operator/utils.rb +77 -0
  86. data/lib/kamaze/project/tools/process_locker.rb +106 -0
  87. data/lib/kamaze/project/tools/rspec.rb +115 -0
  88. data/lib/kamaze/project/tools/rubocop.rb +128 -0
  89. data/lib/kamaze/project/tools/rubocop/arguments.rb +19 -0
  90. data/lib/kamaze/project/tools/rubocop/config.rb +43 -0
  91. data/lib/kamaze/project/tools/shell.rb +85 -0
  92. data/lib/kamaze/project/tools/vagrant.rb +182 -0
  93. data/lib/kamaze/project/tools/vagrant/composer.rb +88 -0
  94. data/lib/kamaze/project/tools/vagrant/composer/file.rb +79 -0
  95. data/lib/kamaze/project/tools/vagrant/remote.rb +79 -0
  96. data/lib/kamaze/project/tools/vagrant/shell.rb +102 -0
  97. data/lib/kamaze/project/tools/vagrant/writer.rb +81 -0
  98. data/lib/kamaze/project/tools/yardoc.rb +75 -0
  99. data/lib/kamaze/project/tools/yardoc/file.rb +55 -0
  100. data/lib/kamaze/project/tools/yardoc/watchable.rb +70 -0
  101. data/lib/kamaze/project/tools/yardoc/watcher.rb +106 -0
  102. data/lib/kamaze/project/tools_provider.rb +161 -0
  103. data/lib/kamaze/project/tools_provider/resolver.rb +42 -0
  104. data/lib/kamaze/project/version.rb +104 -0
  105. data/lib/kamaze/project/version.yml +17 -0
  106. metadata +321 -0
@@ -0,0 +1,66 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (C) 2017-2018 Dimitri Arrigoni <dimitri@arrigoni.me>
4
+ # License GPLv3+: GNU GPL version 3 or later
5
+ # <http://www.gnu.org/licenses/gpl.html>.
6
+ # This is free software: you are free to change and redistribute it.
7
+ # There is NO WARRANTY, to the extent permitted by law.
8
+
9
+ require_relative '../git'
10
+ require_relative 'hooks/base_hook'
11
+ require 'kamaze/project/concern/helper'
12
+
13
+ # Provide hooks
14
+ #
15
+ # Kind of factory registering and building hooks
16
+ class Kamaze::Project::Tools::Git::Hooks
17
+ class << self
18
+ include Kamaze::Project::Concern::Helper
19
+
20
+ attr_reader :registered_hooks
21
+
22
+ def register(name, klass = nil)
23
+ klass ||= proc do
24
+ cname = helper.get(:inflector).classify(name.to_s)
25
+
26
+ require_relative "hooks/#{name}"
27
+
28
+ helper.get(:inflector).constantize("#{self.name}::#{cname}")
29
+ end.call
30
+
31
+ @registered_hooks ||= {}
32
+ @registered_hooks[name] = klass
33
+ self
34
+ end
35
+ end
36
+
37
+ @registered_hooks = {}
38
+
39
+ # @param [Kamaze::Project::Tools::Git] repository
40
+ def initialize(repository)
41
+ @hooks = {}
42
+ @repository = repository
43
+
44
+ [:pre_commit].each { |n| self.class.register(n) }
45
+
46
+ self.class
47
+ .registered_hooks
48
+ .each { |name, klass| @hooks[name] = klass.new(repository) }
49
+ end
50
+
51
+ # @return [Hash]
52
+ def to_h
53
+ @hooks.freeze
54
+ end
55
+
56
+ # @param [Symbol] key
57
+ # @return [nil|Array<Hook>]
58
+ def [](key)
59
+ to_h[key]
60
+ end
61
+
62
+ protected
63
+
64
+ # @return [Kamaze::Project::Tools::Git]
65
+ attr_reader :repository
66
+ end
@@ -0,0 +1,33 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (C) 2017-2018 Dimitri Arrigoni <dimitri@arrigoni.me>
4
+ # License GPLv3+: GNU GPL version 3 or later
5
+ # <http://www.gnu.org/licenses/gpl.html>.
6
+ # This is free software: you are free to change and redistribute it.
7
+ # There is NO WARRANTY, to the extent permitted by law.
8
+
9
+ require_relative '../hooks'
10
+ require_relative '../../../concern/cli/with_exit_on_failure'
11
+
12
+ # rubocop:disable Style/Documentation
13
+
14
+ class Kamaze::Project::Tools::Git::Hooks
15
+ class BaseHook
16
+ include Kamaze::Project::Concern::Cli::WithExitOnFailure
17
+ end
18
+ end
19
+
20
+ # rubocop:enable Style/Documentation
21
+
22
+ # Base Hook
23
+ class Kamaze::Project::Tools::Git::Hooks::BaseHook
24
+ # @param [Kamaze::Project::Tools::Git] repository
25
+ def initialize(repository)
26
+ @repository = repository
27
+ end
28
+
29
+ protected
30
+
31
+ # @return [Kamaze::Project::Tools::Git]
32
+ attr_reader :repository
33
+ end
@@ -0,0 +1,81 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (C) 2017-2018 Dimitri Arrigoni <dimitri@arrigoni.me>
4
+ # License GPLv3+: GNU GPL version 3 or later
5
+ # <http://www.gnu.org/licenses/gpl.html>.
6
+ # This is free software: you are free to change and redistribute it.
7
+ # There is NO WARRANTY, to the extent permitted by law.
8
+
9
+ require_relative '../hooks'
10
+ require_relative 'base_hook'
11
+
12
+ class Kamaze::Project::Tools::Git::Hooks
13
+ class PreCommit < BaseHook
14
+ end
15
+ end
16
+
17
+ # PreCommit hook
18
+ #
19
+ # Provide helper methods intended to write hooks relating to pre-commit
20
+ #
21
+ # Sample of use:
22
+ #
23
+ # ```ruby
24
+ # retcode = tools.fetch(:git).hooks[:pre_commit].process_index do |files|
25
+ # tools.fetch(:rubocop).prepare do |c|
26
+ # c.patterns = files.reject(&:deleted?).map(&:to_s)
27
+ # end.run
28
+ #
29
+ # exit(retcode) unless retcode.zero?
30
+ # end
31
+ # ```
32
+ class Kamaze::Project::Tools::Git::Hooks::PreCommit
33
+ # Process index (files)
34
+ #
35
+ # Exits with a status code, raising ``SystemExit``.
36
+ #
37
+ # | code | constant | reason |
38
+ # |---------|-----------------------|-----------------|
39
+ # | ``125`` | ``Errno::ECANCELED`` | Index is empty |
40
+ # | ``95`` | ``Errno::EOPNOTSUPP`` | Index is unsafe |
41
+ # | ``0`` | ``Errno::NOERROR`` | Success |
42
+ #
43
+ # @param [Hash] options
44
+ # @option options [Boolean] :allow_unsafe
45
+ # Unsafe index is processed (``false``)
46
+ # @option options [Boolean] :allow_empty
47
+ # Empty index is processed (``false``)
48
+ # @yield [Array<Kamaze::Project::Tools::Git::Status::File>]
49
+ # @yieldreturn [Fixnum]
50
+ # @raise [SystemExit]
51
+ #
52
+ # ``:allow_empty`` and ``:allow_unsafe`` options are available,
53
+ # to continue processing even if ``empty`` or ``unsafe``.
54
+ def process_index(options = {})
55
+ index = _process_index(repository.status.index, options)
56
+ self.retcode = Errno::NOERROR::Errno
57
+
58
+ yield(index.to_a.freeze) if block_given?
59
+ end
60
+
61
+ protected
62
+
63
+ # @param [Kamaze::Project::Tools::Git::Status::Index] index
64
+ # @param [Hash] options
65
+ # @raise [SystemExit]
66
+ #
67
+ # @return [Kamaze::Project::Tools::Git::Status::Index]
68
+ def _process_index(index, options = {})
69
+ { empty: Errno::ECANCELED, unsafe: Errno::EOPNOTSUPP }.each do |type, v|
70
+ with_exit_on_failure do
71
+ key = "allow_#{type}".to_sym
72
+ options[key] = options.keys.include?(key) ? !!options[key] : false
73
+
74
+ next if options[key]
75
+ self.retcode = v.const_get(:Errno) if index.public_send("#{type}?")
76
+ end
77
+ end
78
+
79
+ index
80
+ end
81
+ end
@@ -0,0 +1,101 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (C) 2017-2018 Dimitri Arrigoni <dimitri@arrigoni.me>
4
+ # License GPLv3+: GNU GPL version 3 or later
5
+ # <http://www.gnu.org/licenses/gpl.html>.
6
+ # This is free software: you are free to change and redistribute it.
7
+ # There is NO WARRANTY, to the extent permitted by law.
8
+
9
+ require_relative '../git'
10
+ require_relative 'status/file'
11
+ require_relative 'status/index'
12
+ require_relative 'status/worktree'
13
+ require_relative 'status/decorator'
14
+ require 'pathname'
15
+
16
+ # Provide status
17
+ #
18
+ # Status can provide different kind of file lists, as seen by ``libgit``.
19
+ #
20
+ # ``index`` and ``worktree`` are directly provided throuh ``status``,
21
+ # but files can also been easily discriminated by status.
22
+ #
23
+ # @see Kamaze::Project::Tools::Git::Status::File
24
+ class Kamaze::Project::Tools::Git::Status
25
+ # @return [Pathname]
26
+ attr_reader :base_dir
27
+
28
+ # @param [Hash{String => Array<Symbol>}] status
29
+ # @param [String] base_dir
30
+ def initialize(status, base_dir = Dir.pwd)
31
+ @base_dir = ::Pathname.new(base_dir)
32
+ @status = status.clone
33
+ @cached = nil
34
+ end
35
+
36
+ # @return [Decorator]
37
+ def decorate
38
+ Decorator.new(self)
39
+ end
40
+
41
+ # @return [String]
42
+ def to_s
43
+ decorate.to_s
44
+ end
45
+
46
+ # Empty cache
47
+ #
48
+ # @return [self]
49
+ def refresh!
50
+ @cached = nil
51
+
52
+ self
53
+ end
54
+
55
+ # Get index
56
+ #
57
+ # @return [Index]
58
+ def index
59
+ Index.new(self.to_a)
60
+ end
61
+
62
+ # Get worktree
63
+ #
64
+ # @return [Worktree]
65
+ def worktree
66
+ Worktree.new(self.to_a)
67
+ end
68
+
69
+ # @return [Array<File>]
70
+ def to_a
71
+ cached.to_a.map { |v| File.new(v.fetch(0), v.fetch(1), base_dir) }
72
+ end
73
+
74
+ protected
75
+
76
+ # Get cached filepaths
77
+ #
78
+ # @return [Hash]
79
+ def cached
80
+ @cached ||= prepared
81
+
82
+ @cached
83
+ end
84
+
85
+ # Get prepared filepaths with symbols (states)
86
+ #
87
+ # @return [Hash{String => Hash{Symbol => Symbol}}]
88
+ def prepared
89
+ output = {}
90
+ @status.each do |file, status_data|
91
+ status_data.each do |status|
92
+ status = status.to_s.split('_').map(&:to_sym)
93
+ flags = { status[0] => status[1] || status[0] }
94
+
95
+ output[file] = (output[file] || {}).merge(flags)
96
+ end
97
+ end
98
+
99
+ output
100
+ end
101
+ end
@@ -0,0 +1,39 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (C) 2017-2018 Dimitri Arrigoni <dimitri@arrigoni.me>
4
+ # License GPLv3+: GNU GPL version 3 or later
5
+ # <http://www.gnu.org/licenses/gpl.html>.
6
+ # This is free software: you are free to change and redistribute it.
7
+ # There is NO WARRANTY, to the extent permitted by law.
8
+
9
+ require_relative '../status'
10
+
11
+ # Provide decoration for status
12
+ #
13
+ # Result of ``to_s``, SHOULD be similar to result obtained with:
14
+ #
15
+ # ```sh
16
+ # git status -z | sed "s/\x0/\n/g"
17
+ # ```
18
+ class Kamaze::Project::Tools::Git::Status::Decorator
19
+ # @param [Kamaze::Project::Tools::Git::Status] status
20
+ def initialize(status)
21
+ @status = status
22
+ end
23
+
24
+ def files
25
+ files = [status.index.to_a, status.worktree.to_a].flatten.sort_by(&:to_s)
26
+
27
+ files.reject(&:untracked?)
28
+ .concat(files.keep_if(&:untracked?))
29
+ end
30
+
31
+ def to_s
32
+ files.map { |file| "#{file.status} #{file}" }.uniq.join("\n")
33
+ end
34
+
35
+ protected
36
+
37
+ # @return [Kamaze::Project::Tools::Git::Status]
38
+ attr_reader :status
39
+ end
@@ -0,0 +1,180 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Copyright (C) 2017-2018 Dimitri Arrigoni <dimitri@arrigoni.me>
4
+ # License GPLv3+: GNU GPL version 3 or later
5
+ # <http://www.gnu.org/licenses/gpl.html>.
6
+ # This is free software: you are free to change and redistribute it.
7
+ # There is NO WARRANTY, to the extent permitted by law.
8
+
9
+ require_relative '../status'
10
+ require 'pathname'
11
+
12
+ # Status file
13
+ #
14
+ # Describe a file as seen in status,
15
+ # file is described by path and flags, and is immutable by design.
16
+ #
17
+ # @see http://www.rubydoc.info/github/libgit2/rugged/Rugged%2FRepository%3Astatus
18
+ class Kamaze::Project::Tools::Git::Status::File
19
+ # @return [Pathname]
20
+ attr_reader :base_dir
21
+
22
+ # @return [Pathname]
23
+ attr_reader :path
24
+
25
+ # @return [String]
26
+ attr_reader :flags
27
+
28
+ # @param [Pathname|String] path
29
+ # @param [Hash] flags
30
+ # @param [Pathname|String] base_dir
31
+ def initialize(path, flags, base_dir = Dir.pwd)
32
+ @base_dir = ::Pathname.new(base_dir).freeze
33
+ @path = ::Pathname.new(path).freeze
34
+ @flags = flags.freeze
35
+ end
36
+
37
+ # @return [String]
38
+ def to_s
39
+ path.to_s
40
+ end
41
+
42
+ # Get a status string, composed of two chars
43
+ #
44
+ # @see https://git-scm.com/docs/git-status
45
+ # @return [String]
46
+ def status
47
+ return '??' if untracked?
48
+ states = [' ', ' ']
49
+ mapping = { new: 'A', modified: 'M', deleted: 'D' }
50
+ { index: 0, worktree: 1 }.each do |from, index|
51
+ next unless self.public_send("#{from}?")
52
+
53
+ mapping.each do |flag, s|
54
+ states[index] = s if self.public_send("#{from}_#{flag}?")
55
+ end
56
+ end
57
+
58
+ states.join
59
+ end
60
+
61
+ # @return [Boolean]
62
+ def ==(other)
63
+ return false unless comparable_with?(other)
64
+
65
+ [[self.path.to_s, other.path.to_s],
66
+ [self.base_dir.to_s, other.base_dir.to_s],
67
+ [self.flags.sort, other.flags.sort]].each do |c|
68
+ return false unless c[0] == c[1]
69
+ end
70
+
71
+ true
72
+ end
73
+
74
+ # Denote instance is comparable with another object
75
+ #
76
+ # @param [Object] other
77
+ # @return [Boolean]
78
+ def comparable_to?(other)
79
+ [:flags, :path, :base_dir]
80
+ .map { |m| other.respond_to?(m) }.uniq == [true]
81
+ end
82
+
83
+ # Get absolute path
84
+ #
85
+ # @return [Pathname]
86
+ def absolute_path
87
+ base_dir.join(path)
88
+ end
89
+
90
+ # Denote ignored
91
+ #
92
+ # @return [Boolean]
93
+ def ignored?
94
+ flags.keys.include?(:ignored)
95
+ end
96
+
97
+ # Denote worktree
98
+ #
99
+ # @return [Boolean]
100
+ def worktree?
101
+ flags.keys.include?(:worktree)
102
+ end
103
+
104
+ # Denote index
105
+ #
106
+ # @return [Boolean]
107
+ def index?
108
+ flags.keys.include?(:index)
109
+ end
110
+
111
+ # Denote new
112
+ #
113
+ # @return [Boolean]
114
+ def new?
115
+ flags.values.include?(:new)
116
+ end
117
+
118
+ # Denote modified
119
+ #
120
+ # @return [Boolean]
121
+ def modified?
122
+ flags.values.include?(:modified)
123
+ end
124
+
125
+ # Denote deleted
126
+ #
127
+ # @return [Boolean]
128
+ def deleted?
129
+ flags.values.include?(:deleted)
130
+ end
131
+
132
+ # Denote untracked
133
+ #
134
+ # @return [Boolean]
135
+ def untracked?
136
+ worktree? and new? and !index?
137
+ end
138
+
139
+ # Denote new in index
140
+ #
141
+ # @return [Boolean]
142
+ def index_new?
143
+ index? and new?
144
+ end
145
+
146
+ # Denote modified in index
147
+ #
148
+ # @return [Boolean]
149
+ def index_modified?
150
+ index? and modified?
151
+ end
152
+
153
+ # Denote deleted in index
154
+ #
155
+ # @return [Boolean]
156
+ def index_deleted?
157
+ index? and deleted?
158
+ end
159
+
160
+ # Denote new in worktree
161
+ #
162
+ # @return [Boolean]
163
+ def worktree_new?
164
+ worktree? and new?
165
+ end
166
+
167
+ # Denote modified in worktree
168
+ #
169
+ # @return [Boolean]
170
+ def worktree_modified?
171
+ worktree? and modified?
172
+ end
173
+
174
+ # Denote deleted in worktree
175
+ #
176
+ # @return [Boolean]
177
+ def worktree_deleted?
178
+ worktree? and deleted?
179
+ end
180
+ end