fitting 2.13.0 → 2.16.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (54) hide show
  1. checksums.yaml +5 -5
  2. data/.github/workflows/ruby.yml +33 -0
  3. data/.rubocop.yml +1 -1
  4. data/.ruby-version +1 -1
  5. data/.tool-versions +1 -1
  6. data/CHANGELOG.md +52 -0
  7. data/README.md +83 -259
  8. data/example.png +0 -0
  9. data/example2.png +0 -0
  10. data/fitting.gemspec +5 -5
  11. data/lib/fitting/cover/json_schema.rb +8 -6
  12. data/lib/fitting/cover/json_schema_enum.rb +8 -6
  13. data/lib/fitting/cover/json_schema_one_of.rb +7 -5
  14. data/lib/fitting/records/spherical/requests.rb +3 -1
  15. data/lib/fitting/report/action.rb +53 -0
  16. data/lib/fitting/report/actions.rb +51 -0
  17. data/lib/fitting/report/combination.rb +37 -0
  18. data/lib/fitting/report/combinations.rb +47 -0
  19. data/lib/fitting/report/console.rb +41 -0
  20. data/lib/fitting/report/prefix.rb +88 -0
  21. data/lib/fitting/report/prefixes.rb +54 -0
  22. data/lib/fitting/report/response.rb +71 -0
  23. data/lib/fitting/report/responses.rb +48 -0
  24. data/lib/fitting/report/test.rb +75 -0
  25. data/lib/fitting/report/tests.rb +69 -0
  26. data/lib/fitting/tests.rb +0 -1
  27. data/lib/fitting/version.rb +1 -1
  28. data/lib/tasks/fitting.rake +130 -0
  29. data/lib/templates/bomboniere/.gitignore +21 -0
  30. data/lib/templates/bomboniere/.tool-versions +1 -0
  31. data/lib/templates/bomboniere/README.md +19 -0
  32. data/lib/templates/bomboniere/dist/css/app.aa2bcd8a.css +1 -0
  33. data/lib/templates/bomboniere/dist/css/chunk-vendors.ec5f6c3f.css +1 -0
  34. data/lib/templates/bomboniere/dist/favicon.ico +0 -0
  35. data/lib/templates/bomboniere/dist/index.html +1 -0
  36. data/lib/templates/bomboniere/dist/js/app.e5f1a5ec.js +2 -0
  37. data/lib/templates/bomboniere/dist/js/app.e5f1a5ec.js.map +1 -0
  38. data/lib/templates/bomboniere/dist/js/chunk-vendors.0f99b670.js +13 -0
  39. data/lib/templates/bomboniere/dist/js/chunk-vendors.0f99b670.js.map +1 -0
  40. data/lib/templates/bomboniere/package-lock.json +9277 -0
  41. data/lib/templates/bomboniere/package.json +27 -0
  42. data/lib/templates/bomboniere/public/favicon.ico +0 -0
  43. data/lib/templates/bomboniere/public/index.html +17 -0
  44. data/lib/templates/bomboniere/src/App.vue +102 -0
  45. data/lib/templates/bomboniere/src/assets/logo.png +0 -0
  46. data/lib/templates/bomboniere/src/components/HelloWorld.vue +201 -0
  47. data/lib/templates/bomboniere/src/main.js +10 -0
  48. data/lib/templates/bomboniere/src/router/index.js +31 -0
  49. data/lib/templates/bomboniere/src/views/About.vue +5 -0
  50. data/lib/templates/bomboniere/src/views/Action.vue +173 -0
  51. data/lib/templates/bomboniere/src/views/Home.vue +17 -0
  52. data/lib/templates/bomboniere/vue.config.js +3 -0
  53. metadata +68 -31
  54. data/.travis.yml +0 -4
@@ -0,0 +1,54 @@
1
+ require 'fitting/report/prefix'
2
+
3
+ module Fitting
4
+ module Report
5
+ class Prefixes
6
+ def initialize(config_path)
7
+ @prefixes = []
8
+ YAML.safe_load(File.read(config_path))['prefixes'].map do |prefix|
9
+ @prefixes.push(
10
+ Fitting::Report::Prefix.new(
11
+ name: prefix['name'],
12
+ openapi2_json_path: prefix['openapi2_json_path'],
13
+ openapi3_yaml_path: prefix['openapi3_yaml_path'],
14
+ drafter_yaml_path: prefix['drafter_yaml_path'],
15
+ tomogram_json_path: prefix['tomogram_json_path'],
16
+ crafter_yaml_path: prefix['crafter_yaml_path'],
17
+ skip: prefix['skip']
18
+ )
19
+ )
20
+ end
21
+ end
22
+
23
+ def is_there_a_suitable_prefix?(test_path)
24
+ @prefixes.map do |prefix|
25
+ return true if test_path[0..prefix.name.size - 1] == prefix.name
26
+ end
27
+
28
+ false
29
+ end
30
+
31
+ def cram_into_the_appropriate_prefix(test)
32
+ @prefixes.map do |prefix|
33
+ if test.path[0..prefix.name.size - 1] == prefix.name
34
+ prefix.add_test(test)
35
+ return
36
+ end
37
+ end
38
+ end
39
+
40
+ def join(tests)
41
+ tests.to_a.map do |test|
42
+ if is_there_a_suitable_prefix?(test.path)
43
+ cram_into_the_appropriate_prefix(test)
44
+ test.mark_prefix
45
+ end
46
+ end
47
+ end
48
+
49
+ def to_a
50
+ @prefixes
51
+ end
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,71 @@
1
+ require 'fitting/statistics/template_cover_error'
2
+ require 'fitting/statistics/template_cover_error_enum'
3
+ require 'fitting/statistics/template_cover_error_one_of'
4
+ require 'fitting/report/combinations'
5
+ require 'fitting/report/combination'
6
+
7
+ module Fitting
8
+ module Report
9
+ class Response
10
+ def initialize(response)
11
+ @response = response
12
+ @tests = Fitting::Report::Tests.new([])
13
+ @id = SecureRandom.hex
14
+ end
15
+
16
+ def status
17
+ @response['status'] || @response[:status]
18
+ end
19
+
20
+ def body
21
+ @response['body'] || @response[:body]
22
+ end
23
+
24
+ def id
25
+ @id
26
+ end
27
+
28
+ def add_test(test)
29
+ @tests.push(test)
30
+ end
31
+
32
+ def tests
33
+ @tests
34
+ end
35
+
36
+ def combinations
37
+ return @combinations if @combinations
38
+
39
+ cmbntns = []
40
+ combinations = Fitting::Cover::JSONSchema.new(body).combi + Fitting::Cover::JSONSchemaEnum.new(body).combi + Fitting::Cover::JSONSchemaOneOf.new(body).combi
41
+ if combinations != []
42
+ combinations.map do |combination|
43
+ cmbntns.push(
44
+ Fitting::Report::Combination.new(
45
+ json_schema: combination[0],
46
+ type: combination[1][0],
47
+ combination: combination[1][1]
48
+ )
49
+ )
50
+ end
51
+ end
52
+
53
+ @combinations = Fitting::Report::Combinations.new(cmbntns)
54
+ end
55
+
56
+ def cover_percent
57
+ return '0%' if @tests.size == 0
58
+ return '100%' if @combinations.size == 0
59
+ "#{(@combinations.size_with_tests + 1) * 100 / (@combinations.size + 1)}%"
60
+ end
61
+
62
+ def details
63
+ {
64
+ cover_percent: cover_percent,
65
+ tests_without_combinations: @tests.without_combinations,
66
+ combinations_details: @combinations.to_a.map { |c| {json_schema: c.id, tests_size: c.tests.size, type: c.type, name: c.name} }
67
+ }
68
+ end
69
+ end
70
+ end
71
+ end
@@ -0,0 +1,48 @@
1
+ require 'fitting/report/response'
2
+
3
+ module Fitting
4
+ module Report
5
+ class Responses
6
+ def initialize(responses)
7
+ @responses = responses
8
+ @responses = []
9
+ responses.to_a.map do |response|
10
+ @responses.push(Fitting::Report::Response.new(response))
11
+ end
12
+ end
13
+
14
+ def to_a
15
+ @responses
16
+ end
17
+
18
+ def join(tests)
19
+ tests.to_a.map do |test|
20
+ if is_there_a_suitable_response?(test)
21
+ cram_into_the_appropriate_response(test)
22
+ test.mark_response
23
+ end
24
+ end
25
+ end
26
+
27
+ def is_there_a_suitable_response?(test)
28
+ return false if @responses.nil?
29
+ @responses.map do |response|
30
+ return true if response.status.to_s == test.status &&
31
+ JSON::Validator.fully_validate(response.body, test.body) == []
32
+ end
33
+
34
+ false
35
+ end
36
+
37
+ def cram_into_the_appropriate_response(test)
38
+ @responses.map do |response|
39
+ if response.status.to_s == test.status &&
40
+ JSON::Validator.fully_validate(response.body, test.body) == []
41
+ response.add_test(test)
42
+ return
43
+ end
44
+ end
45
+ end
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,75 @@
1
+ module Fitting
2
+ module Report
3
+ class Test
4
+ def initialize(test)
5
+ @test = test
6
+ @prefix = false
7
+ @action = false
8
+ @response = false
9
+ @combination = false
10
+ @id = SecureRandom.hex
11
+ end
12
+
13
+ def id
14
+ @id
15
+ end
16
+
17
+ def to_h
18
+ {
19
+ path: path,
20
+ method: method,
21
+ status: status,
22
+ body: body
23
+ }
24
+ end
25
+
26
+ def path
27
+ @test['path']
28
+ end
29
+
30
+ def method
31
+ @test['method']
32
+ end
33
+
34
+ def status
35
+ @test['response']['status'].to_s
36
+ end
37
+
38
+ def body
39
+ @test['response']['body']
40
+ end
41
+
42
+ def mark_prefix
43
+ @prefix = true
44
+ end
45
+
46
+ def mark_action
47
+ @action = true
48
+ end
49
+
50
+ def mark_response
51
+ @response = true
52
+ end
53
+
54
+ def mark_combination
55
+ @combination = true
56
+ end
57
+
58
+ def is_there_a_prefix?
59
+ @prefix
60
+ end
61
+
62
+ def is_there_an_actions?
63
+ @action
64
+ end
65
+
66
+ def is_there_an_responses?
67
+ @response
68
+ end
69
+
70
+ def is_there_an_combinations?
71
+ @combination
72
+ end
73
+ end
74
+ end
75
+ end
@@ -0,0 +1,69 @@
1
+ require 'fitting/report/test'
2
+
3
+ module Fitting
4
+ module Report
5
+ class Tests
6
+ def initialize(tests)
7
+ @tests = tests
8
+ end
9
+
10
+ def self.new_from_config(tests_path)
11
+ tests = []
12
+ Dir[tests_path].each do |file|
13
+ JSON.load(File.read(file)).map do |test|
14
+ tests.push(Fitting::Report::Test.new(test))
15
+ end
16
+ end
17
+ tests.sort { |a, b| b.path <=> a.path }
18
+ new(tests)
19
+ end
20
+
21
+ def without_prefixes
22
+ @tests.inject([]) do |result, test|
23
+ result.push(test.path) unless test.is_there_a_prefix?
24
+ result
25
+ end
26
+ end
27
+
28
+ def without_actions
29
+ @tests.inject([]) do |result, test|
30
+ result.push("#{test.method} #{test.path}") unless test.is_there_an_actions?
31
+ result
32
+ end
33
+ end
34
+
35
+ def without_responses
36
+ @tests.inject([]) do |result, test|
37
+ result.push(test.id) unless test.is_there_an_responses?
38
+ result
39
+ end
40
+ end
41
+
42
+ def without_combinations
43
+ @tests.inject([]) do |result, test|
44
+ result.push(test.path) unless test.is_there_an_combinations?
45
+ result
46
+ end
47
+ end
48
+
49
+ def push(test)
50
+ @tests.push(test)
51
+ end
52
+
53
+ def size
54
+ @tests.size
55
+ end
56
+
57
+ def to_a
58
+ @tests
59
+ end
60
+
61
+ def to_h
62
+ return @hash if @hash
63
+ @hash = @tests.inject({}) do |res, test|
64
+ res.merge!(test.id => test.to_h)
65
+ end
66
+ end
67
+ end
68
+ end
69
+ end
data/lib/fitting/tests.rb CHANGED
@@ -9,7 +9,6 @@ module Fitting
9
9
  def save
10
10
  make_dir('fitting_tests')
11
11
  array = @tested_requests.inject([]) do |res, request|
12
- next res unless request.path.to_s.start_with?(Fitting.configuration.prefix)
13
12
  res.push(request.to_spherical.to_hash)
14
13
  end
15
14
  json = JSON.dump(array)
@@ -1,3 +1,3 @@
1
1
  module Fitting
2
- VERSION = '2.13.0'.freeze
2
+ VERSION = '2.16.0'.freeze
3
3
  end
@@ -5,8 +5,138 @@ require 'fitting/templates/realized_template'
5
5
  require 'fitting/statistics/template_cover_error'
6
6
  require 'fitting/statistics/template_cover_error_enum'
7
7
  require 'fitting/statistics/template_cover_error_one_of'
8
+ require 'fitting/cover/json_schema'
9
+ require 'fitting/report/prefixes'
10
+ require 'fitting/report/tests'
11
+ require 'fitting/report/console'
8
12
 
9
13
  namespace :fitting do
14
+ task :report do
15
+ tests = Fitting::Report::Tests.new_from_config('fitting_tests/*.json')
16
+ prefixes = Fitting::Report::Prefixes.new('.fitting.yml')
17
+
18
+ prefixes.join(tests)
19
+
20
+ prefixes.to_a.map do |prefix|
21
+ prefix.actions.join(prefix.tests) unless prefix.skip?
22
+ end
23
+
24
+ prefixes.to_a.map do |prefix|
25
+ prefix.actions.to_a.map do |action|
26
+ action.responses.join(action.tests)
27
+ end unless prefix.skip?
28
+ end
29
+
30
+ prefixes.to_a.map do |prefix|
31
+ prefix.actions.to_a.map do |action|
32
+ action.responses.to_a.map do |response|
33
+ response.combinations.join(response.tests)
34
+ end
35
+ end unless prefix.skip?
36
+ end
37
+
38
+ report = JSON.pretty_generate(
39
+ {
40
+ tests_without_prefixes: tests.without_prefixes,
41
+ prefixes_details: prefixes.to_a.map { |p| p.details }
42
+ }
43
+ )
44
+
45
+ destination = 'fitting'
46
+ FileUtils.mkdir_p(destination)
47
+ FileUtils.rm_r Dir.glob("#{destination}/*"), :force => true
48
+ File.open('fitting/report.json', 'w') { |file| file.write(report) }
49
+
50
+ gem_path = $LOAD_PATH.find { |i| i.include?('fitting') }
51
+ source_path = "#{gem_path}/templates/bomboniere/dist"
52
+ FileUtils.copy_entry source_path, destination
53
+
54
+ json_schemas = {}
55
+ combinations = {}
56
+ prefixes.to_a.map do |prefix|
57
+ prefix.actions.to_a.map do |action|
58
+ action.responses.to_a.map do |response|
59
+ json_schemas.merge!(response.id => response.body)
60
+ response.combinations.to_a.map do |combination|
61
+ combinations.merge!(combination.id => combination.json_schema)
62
+ end
63
+ end
64
+ end unless prefix.skip?
65
+ end
66
+ File.open('fitting/json_schemas.json', 'w') { |file| file.write(JSON.pretty_generate(json_schemas)) }
67
+ File.open('fitting/combinations.json', 'w') { |file| file.write(JSON.pretty_generate(combinations)) }
68
+ File.open('fitting/tests.json', 'w') { |file| file.write(JSON.pretty_generate(tests.to_h)) }
69
+
70
+ js_path = Dir["#{destination}/js/*"].find { |f| f[0..14] == 'fitting/js/app.' and f[-3..-1] == '.js' }
71
+ js_file = File.read(js_path)
72
+ new_js_file = js_file.gsub("{stub:\"prefixes report\"}", report)
73
+ new_js_file = new_js_file.gsub("{stub:\"for action page\"}", report)
74
+ new_js_file = new_js_file.gsub("{stub:\"json-schemas\"}", JSON.pretty_generate(json_schemas))
75
+ new_js_file = new_js_file.gsub("{stub:\"combinations\"}", JSON.pretty_generate(combinations))
76
+ new_js_file = new_js_file.gsub("{stub:\"tests\"}", JSON.pretty_generate(tests.to_h))
77
+ File.open(js_path, 'w') { |file| file.write(new_js_file) }
78
+
79
+ console = Fitting::Report::Console.new(
80
+ tests.without_prefixes,
81
+ prefixes.to_a.map { |p| p.details }
82
+ )
83
+
84
+ puts console.output
85
+
86
+ exit 1 unless console.good?
87
+
88
+ exit 0
89
+
90
+ actions.map do |action|
91
+ action.to_hash["responses"].map do |response|
92
+ response['combination'] ||= []
93
+ combinations = Fitting::Cover::JSONSchema.new(response['body']).combi + Fitting::Cover::JSONSchemaEnum.new(response['body']).combi + Fitting::Cover::JSONSchemaOneOf.new(response['body']).combi
94
+ if combinations != []
95
+ combinations.map do |combination|
96
+ response['combination'].push(
97
+ {
98
+ 'json_schema' => combination[0],
99
+ 'type' => combination[1][0],
100
+ 'combination' => combination[1][1],
101
+ 'tests' => [],
102
+ 'error' => []
103
+ }
104
+ )
105
+ end
106
+ end
107
+ end
108
+ end
109
+
110
+ actions.map do |action|
111
+ action.to_hash["responses"].map do |response|
112
+ response['tests'] ||= []
113
+ response['tests'].map do |test|
114
+ if response['combination'][0]
115
+ response['combination'].map do |combination|
116
+ begin
117
+ res = JSON::Validator.fully_validate(combination['json_schema'], test['response']['body'])
118
+ if res == []
119
+ combination['tests'].push(test)
120
+ response['tests'] = response['tests'] - [test]
121
+ next
122
+ else
123
+ combination['error'].push({test: test, error: res})
124
+ end
125
+ rescue JSON::Schema::SchemaError => error
126
+ combination['error'].push({test: test, error: error})
127
+ end
128
+ end
129
+ end
130
+ end
131
+ end
132
+ end
133
+
134
+ actions_test = {actions: actions, tests: tests}
135
+
136
+ makedirs('fitting')
137
+ File.open('fitting/old_report.json', 'w') { |file| file.write(MultiJson.dump(actions_test)) }
138
+ end
139
+
10
140
  # deprecated
11
141
  desc 'Fitting documentation'
12
142
  task :documentation do