mudguard 0.1.8 → 0.2.4

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6db3d7377ad8b0b1d13e59c306bd937bcb39a2b68bee5d0539a4dff17d460243
4
- data.tar.gz: b46919284fea9ad09e6db895025c50eeff3577fc0fe32bbc3b5ad7aec0e4833f
3
+ metadata.gz: 456ae028fad5fdfd5e2e96158d53956c7a709823d2477c351050fb220e8ab1ec
4
+ data.tar.gz: 0c9375de37dd75a71f89203c2248aad4cf4b555ef5f63d8ecb4442d63fe1a56f
5
5
  SHA512:
6
- metadata.gz: 68ed243c036a7bdbe9a5e3e5e5996c76006cbc7057f4f5aad78d43c011038a6de16496c61ce5bd9c88a63c678f6d501f53af17e18e931abb20d0bce351ce0585
7
- data.tar.gz: 050fdc731cc7297f986f10ed1b39e95aa6e82bf2f36959d7fe6e322c9681b5322a8a0390b177ced26ecc5c09bea737e86b26645966e4d1b2612eee25d370a735
6
+ metadata.gz: 15a30108d5b47a12905075ed35c62ace335fd4b9303b4da46301af6db2f6b5d509d4cba95e245a4144368accf710f85e4be334c9d09a50840bad4600962078d3
7
+ data.tar.gz: 6102ca6a925655ccae7d345ed4522ac8cf546f3d3fd212bedd519c1a69be3321c80a09e46b8aa1893ff67f62d9ce9703672d255dfc5ff0a22c14278dd4b7853d
data/.gitignore CHANGED
@@ -20,3 +20,4 @@
20
20
 
21
21
  # Following file is dynamically created while running tests
22
22
  /spec/lib/infrastructure/persistence/policy_file_project/.mudguard.yml
23
+ /spec/test_projects/project_without_mudguard_file/.mudguard.yml
@@ -0,0 +1,6 @@
1
+ './**/*.rb':
2
+ # uncomment following lines to allow all dependencies
3
+ # - .*
4
+
5
+ # all code can depend on modules or constants defined in same module
6
+ - ^(::.+)(::[^:]+)* -> \1(::[^:]+)*$
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- mudguard (0.1.8)
4
+ mudguard (0.2.4)
5
5
  parser (~> 2.7)
6
6
  rake (~> 13.0)
7
7
 
data/Guardfile CHANGED
@@ -1,7 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  rspec_options = {
4
- cmd: "rspec",
4
+ cmd: "bundle exec rspec",
5
5
  notification: false,
6
6
  failed_mode: :focus
7
7
  }
data/README.md CHANGED
@@ -1,10 +1,16 @@
1
1
  # Mudguard
2
2
 
3
- Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/mudguard`. To experiment with that code, run `bin/console` for an interactive prompt.
3
+ **Mudguard** is a Ruby static code analyzer that investigates the coupling of modules in your source code. Mudguard
4
+ prevents your code from becoming a [Big ball of mud](http://www.laputan.org/mud/) and helps implementing and
5
+ maintaining an intended design.
4
6
 
5
- TODO: Delete this and the text above, and describe your gem
7
+ Mudguard is inspired by
8
+ * [Rubocop](https://github.com/rubocop-hq/rubocop)
9
+ * Clean Architecture by Robert C. Martin (ISBN-13: 978-0-13-449416-6)
10
+ * having seen many larger code bases in a sorrow state
11
+ * my inability to efficiently break up application code into gems or rails engines
6
12
 
7
- ## Installation
13
+ # Installation
8
14
 
9
15
  Add this line to your application's Gemfile:
10
16
 
@@ -20,19 +26,66 @@ Or install it yourself as:
20
26
 
21
27
  $ gem install mudguard
22
28
 
23
- ## Usage
29
+ ## Quickstart
30
+ ```
31
+ $ cd my/cool/ruby/project
32
+ $ mudguard
33
+ ```
34
+
35
+ Mudguard creates on it's first run a file called **.mudguard.yml** which is used to configure **design policies**
36
+ governing your code. A .mudguard.yml could look like:
37
+ ```
38
+ './**/*.rb': # all code
39
+ # all code can depend on siblings in same module or class
40
+ - ^(::.+)(::[^:]+)* -> \1(::[^:]+)*$
41
+ # all code can depend on certain types
42
+ - .* -> ::(String|SecureRandom|Container|Time|Date|JSON|Object|Hash)$
43
+
44
+ # in all code module Application can depend on module Domain
45
+ - ^::Application(::[^:]+)* -> ::(Domain)(::[^:]+)*$
46
+ # in all code module Infrastructure can depend on module Application
47
+ - ^::Infrastructure(::[^:]+)* -> ::(Application)(::[^:]+)*$
48
+
49
+ 'spec/**/*.rb': # spec code
50
+ # Only in test code can we use RSpec, Timecop and Exception
51
+ - .* -> ::(RSpec|Timecop|Exception)$
52
+ ```
53
+
54
+ ## The .mudguard.yml
55
+ The .mudguard.yml defines scopes and policies. A policy defines which dependencies are inside that scope permissible:
56
+ ```
57
+ scope1:
58
+ - policy 1
59
+ - policy 2
60
+ scope2:
61
+ - policy 3
62
+ ```
63
+ The **scope** is a [glob-pattern](https://en.wikipedia.org/wiki/Glob_(programming)) and defines to which files a set
64
+ of policies apply. For example a value `lib/docker/**/*.rb` defines a scope containing all Ruby files inside
65
+ folder lib/docker.
24
66
 
25
- TODO: Write usage instructions here
67
+ A **policy** is a [regular expression](https://ruby-doc.org/core-2.5.1/Regexp.html) matching one or a set of
68
+ dependencies that are permissible inside that scope. Mudguard represents a **dependency** as a symbol in form
69
+ of `X -> Y` meaning "X depends on Y". See following examples:
26
70
 
27
- ## Development
71
+ | Policy | matched Dependency| Explanation |
72
+ | --- | --- | --- |
73
+ | `^::A -> ::B$` | `::A -> ::B` |Module A can depend on module or constant B |
74
+ | `^::Infrastructure -> ::Rails$` | `::Infrastructure -> ::Rails` |Module Infrastructure can depend on Rails |
75
+ | `^::Infrastructure(::[^:]+)* -> ::ActiveRecord$` | `::Infrastructure::Logger -> ::ActiveRecord` or `::Infrastructure::Persistence -> ::ActiveRecord`|Module Infrastructure and its submodules can depend on ActiveRecord |
76
+ | `.* -> ::Exception$` | `::Api::Gateway -> ::Exception` or `::Logger -> ::Gateway` |Any module can depend on class Exception |
28
77
 
29
- After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
78
+ Any dependency for which Mudguard doesn't find a matching policy is reported as an impermissible dependency.
30
79
 
31
- To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
80
+ ## Outlook
81
+ Using regular expressions as policies is very flexible but difficult to use. Furthermore certain patterns used in
82
+ the regular expressions do repeat. It might be useful to replace regular expressions in future with a specific language
83
+ to describe permissible dependencies. Any thoughts on that?
32
84
 
33
85
  ## Contributing
34
86
 
35
- Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/mudguard. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the [Contributor Covenant](http://contributor-covenant.org) code of conduct.
87
+ Bug reports and pull requests are welcome on GitHub at https://github.com/Enceradeira/mudguard.
88
+ This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the [Contributor Covenant](http://contributor-covenant.org) code of conduct.
36
89
 
37
90
  ## License
38
91
 
@@ -7,13 +7,12 @@ module Mudguard
7
7
  # Knows all constants of the project
8
8
  class Consts
9
9
  def initialize(sources:)
10
- @consts = sources
11
- .flat_map(&:find_consts)
12
- .each_with_object(Hash.new { |h, k| h[k] = {} }) do |c, a|
10
+ @consts = sources.flat_map(&:find_consts)
11
+ .each_with_object({}) do |c, a|
13
12
  path = split_hierarchy(c)
14
13
  const_name = path.last
15
14
  module_names = path.take(path.count - 1)
16
- sub_module = module_names.reduce(a) { |h, m| h[m] }
15
+ sub_module = module_names.reduce(a) { |h, m| h.key?(m) ? h[m] : h[m] = {} }
17
16
  sub_module[const_name] = {} unless sub_module.key?(const_name)
18
17
  end
19
18
  end
@@ -1,6 +1,13 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require "parser/current"
3
+ orig = $VERBOSE
4
+ begin
5
+ $VERBOSE = nil # silence warning when ruby versions are not exactly matching
6
+ require "parser/current"
7
+ ensure
8
+ $VERBOSE = orig
9
+ end
10
+
4
11
  require_relative "dependency"
5
12
  require_relative "dependency_visitor"
6
13
  require_relative "const_visitor"
@@ -0,0 +1,6 @@
1
+ './**/*.rb':
2
+ # uncomment following lines to allow all dependencies
3
+ # - .*
4
+
5
+ # all code can depend on modules or constants defined in same module
6
+ - ^(::.+)(::[^:]+)* -> \1(::[^:]+)*$
@@ -15,7 +15,8 @@ module Mudguard
15
15
  policy_exists = File.exist?(policy_file)
16
16
 
17
17
  unless policy_exists
18
- raise Mudguard::Domain::Error, "expected policy file #{policy_file} doesn't exists"
18
+ template_file = File.join(__dir__, ".mudguard.template.yml")
19
+ FileUtils.cp(template_file, policy_file)
19
20
  end
20
21
 
21
22
  read_yml(policy_file)
@@ -25,7 +25,7 @@ module Mudguard
25
25
  def enumerate_files(project_path, patterns)
26
26
  project_path_name = Pathname.new(project_path)
27
27
  ruby_files = patterns.map { |p| File.join(project_path, p) }
28
- Dir.glob(ruby_files).map do |f|
28
+ Dir.glob(ruby_files).select { |f| File.file?(f) }.map do |f|
29
29
  file_path_name = Pathname.new(f)
30
30
  diff_path = file_path_name.relative_path_from(project_path_name).to_s
31
31
  Mudguard::Domain::Source.new(location: File.join("./", diff_path),
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Mudguard
4
- VERSION = "0.1.8"
4
+ VERSION = "0.2.4"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mudguard
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.8
4
+ version: 0.2.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jorg Jenni
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-06-07 00:00:00.000000000 Z
11
+ date: 2021-01-09 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -174,6 +174,7 @@ extra_rdoc_files: []
174
174
  files:
175
175
  - ".envrc"
176
176
  - ".gitignore"
177
+ - ".mudguard.yml"
177
178
  - ".rubocop.yml"
178
179
  - ".ruby-version"
179
180
  - CODE_OF_CONDUCT.md
@@ -200,6 +201,7 @@ files:
200
201
  - lib/mudguard/infrastructure/cli/controller.rb
201
202
  - lib/mudguard/infrastructure/cli/notification_adapter.rb
202
203
  - lib/mudguard/infrastructure/cli/view.rb
204
+ - lib/mudguard/infrastructure/persistence/.mudguard.template.yml
203
205
  - lib/mudguard/infrastructure/persistence/policy_file.rb
204
206
  - lib/mudguard/infrastructure/persistence/project_repository.rb
205
207
  - lib/mudguard/infrastructure/persistence/ruby_files.rb