dradis-projects 4.6.0 → 4.8.0

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.
Files changed (26) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +7 -0
  3. data/app/controllers/dradis/plugins/projects/packages_controller.rb +6 -1
  4. data/app/controllers/dradis/plugins/projects/templates_controller.rb +6 -1
  5. data/app/views/dradis/plugins/projects/export/_index-content.html.erb +1 -1
  6. data/dradis-projects.gemspec +2 -2
  7. data/lib/dradis/plugins/projects/engine.rb +2 -2
  8. data/lib/dradis/plugins/projects/export/template.rb +1 -3
  9. data/lib/dradis/plugins/projects/export/v1/template.rb +8 -0
  10. data/lib/dradis/plugins/projects/export/v2/template.rb +8 -0
  11. data/lib/dradis/plugins/projects/export/v3/template.rb +8 -0
  12. data/lib/dradis/plugins/projects/export/v4/template.rb +207 -0
  13. data/lib/dradis/plugins/projects/gem_version.rb +1 -1
  14. data/lib/dradis/plugins/projects/upload/template.rb +2 -4
  15. data/lib/dradis/plugins/projects/upload/v1/template.rb +8 -0
  16. data/lib/dradis/plugins/projects/upload/v2/template.rb +8 -0
  17. data/lib/dradis/plugins/projects/upload/v3/template.rb +8 -0
  18. data/lib/dradis/plugins/projects/upload/v4/template.rb +651 -0
  19. data/spec/fixtures/files/with_invalid_states.xml +111 -0
  20. data/spec/fixtures/files/with_states.xml +111 -0
  21. data/spec/lib/dradis/plugins/projects/export/v2/template_spec.rb +9 -1
  22. data/spec/lib/dradis/plugins/projects/export/v4/template_spec.rb +84 -0
  23. data/spec/lib/dradis/plugins/projects/upload/v1/template_spec.rb +8 -0
  24. data/spec/lib/dradis/plugins/projects/upload/v2/template_spec.rb +9 -1
  25. data/spec/lib/dradis/plugins/projects/upload/v4/template_spec.rb +168 -0
  26. metadata +20 -10
@@ -0,0 +1,111 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <dradis-template version="4">
3
+ <nodes>
4
+ <node>
5
+ <id>3</id>
6
+ <label>Node 1</label>
7
+ <parent-id/>
8
+ <position>0</position>
9
+ <properties><![CDATA[{
10
+ }]]></properties>
11
+ <type-id>1</type-id>
12
+ <notes>
13
+ <note>
14
+ <id>2</id>
15
+ <author>xavi</author>
16
+ <category-id>2</category-id>
17
+ <text><![CDATA[#[Title]#
18
+ Note 1
19
+
20
+ #[Description]#
21
+
22
+ ]]></text>
23
+ <activities>
24
+ <activity>
25
+ <action>create</action>
26
+ <user_email>xavi</user_email>
27
+ <created_at>1538467955</created_at>
28
+ </activity>
29
+ </activities>
30
+ <comments>
31
+ <comment>
32
+ <content><![CDATA[A comment on a note]]></content>
33
+ <author>xavi</author>
34
+ <created_at>1538467968</created_at>
35
+ </comment>
36
+ </comments>
37
+ </note>
38
+ </notes>
39
+ <evidence>
40
+ <evidence>
41
+ <id>386</id>
42
+ <author>xavi</author>
43
+ <issue-id>586</issue-id>
44
+ <content><![CDATA[#[Location]#
45
+ A
46
+ ]]></content>
47
+ <activities>
48
+ <activity>
49
+ <action>create</action>
50
+ <user_email>xavi</user_email>
51
+ <created_at>1538549260</created_at>
52
+ </activity>
53
+ </activities>
54
+ <comments>
55
+ <comment>
56
+ <content><![CDATA[A comment on an evidence]]></content>
57
+ <author>xavi</author>
58
+ <created_at>1538549286</created_at>
59
+ </comment>
60
+ </comments>
61
+ </evidence>
62
+ </evidence>
63
+ <activities>
64
+ <activity>
65
+ <action>create</action>
66
+ <user_email>xavi</user_email>
67
+ <created_at>1538467945</created_at>
68
+ </activity>
69
+ </activities>
70
+ </node>
71
+ </nodes>
72
+ <issues>
73
+ <issue>
74
+ <id>586</id>
75
+ <author>xavi</author>
76
+ <state>fakestate</state>
77
+ <text><![CDATA[#[Title]#
78
+ Issue 1
79
+
80
+ #[Description]#
81
+
82
+ ]]></text>
83
+ <activities>
84
+ <activity>
85
+ <action>create</action>
86
+ <user_email>xavi</user_email>
87
+ <created_at>1538467938</created_at>
88
+ </activity>
89
+ </activities>
90
+ <comments>
91
+ <comment>
92
+ <content><![CDATA[A comment on an issue]]></content>
93
+ <author>xavi</author>
94
+ <created_at>1538467997</created_at>
95
+ </comment>
96
+ </comments>
97
+ </issue>
98
+ </issues>
99
+ <methodologies/>
100
+ <categories>
101
+ <category>
102
+ <id>1</id>
103
+ <name>Issue description</name>
104
+ </category>
105
+ <category>
106
+ <id>2</id>
107
+ <name>Default category</name>
108
+ </category>
109
+ </categories>
110
+ <tags/>
111
+ </dradis-template>
@@ -0,0 +1,111 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <dradis-template version="4">
3
+ <nodes>
4
+ <node>
5
+ <id>3</id>
6
+ <label>Node 1</label>
7
+ <parent-id/>
8
+ <position>0</position>
9
+ <properties><![CDATA[{
10
+ }]]></properties>
11
+ <type-id>1</type-id>
12
+ <notes>
13
+ <note>
14
+ <id>2</id>
15
+ <author>xavi</author>
16
+ <category-id>2</category-id>
17
+ <text><![CDATA[#[Title]#
18
+ Note 1
19
+
20
+ #[Description]#
21
+
22
+ ]]></text>
23
+ <activities>
24
+ <activity>
25
+ <action>create</action>
26
+ <user_email>xavi</user_email>
27
+ <created_at>1538467955</created_at>
28
+ </activity>
29
+ </activities>
30
+ <comments>
31
+ <comment>
32
+ <content><![CDATA[A comment on a note]]></content>
33
+ <author>xavi</author>
34
+ <created_at>1538467968</created_at>
35
+ </comment>
36
+ </comments>
37
+ </note>
38
+ </notes>
39
+ <evidence>
40
+ <evidence>
41
+ <id>386</id>
42
+ <author>xavi</author>
43
+ <issue-id>586</issue-id>
44
+ <content><![CDATA[#[Location]#
45
+ A
46
+ ]]></content>
47
+ <activities>
48
+ <activity>
49
+ <action>create</action>
50
+ <user_email>xavi</user_email>
51
+ <created_at>1538549260</created_at>
52
+ </activity>
53
+ </activities>
54
+ <comments>
55
+ <comment>
56
+ <content><![CDATA[A comment on an evidence]]></content>
57
+ <author>xavi</author>
58
+ <created_at>1538549286</created_at>
59
+ </comment>
60
+ </comments>
61
+ </evidence>
62
+ </evidence>
63
+ <activities>
64
+ <activity>
65
+ <action>create</action>
66
+ <user_email>xavi</user_email>
67
+ <created_at>1538467945</created_at>
68
+ </activity>
69
+ </activities>
70
+ </node>
71
+ </nodes>
72
+ <issues>
73
+ <issue>
74
+ <id>586</id>
75
+ <author>xavi</author>
76
+ <state>ready_for_review</state>
77
+ <text><![CDATA[#[Title]#
78
+ Issue 1
79
+
80
+ #[Description]#
81
+
82
+ ]]></text>
83
+ <activities>
84
+ <activity>
85
+ <action>create</action>
86
+ <user_email>xavi</user_email>
87
+ <created_at>1538467938</created_at>
88
+ </activity>
89
+ </activities>
90
+ <comments>
91
+ <comment>
92
+ <content><![CDATA[A comment on an issue]]></content>
93
+ <author>xavi</author>
94
+ <created_at>1538467997</created_at>
95
+ </comment>
96
+ </comments>
97
+ </issue>
98
+ </issues>
99
+ <methodologies/>
100
+ <categories>
101
+ <category>
102
+ <id>1</id>
103
+ <name>Issue description</name>
104
+ </category>
105
+ <category>
106
+ <id>2</id>
107
+ <name>Default category</name>
108
+ </category>
109
+ </categories>
110
+ <tags/>
111
+ </dradis-template>
@@ -1,6 +1,14 @@
1
+ # DEPRECATED - this class is v2 of the Template Importer and shouldn't be updated.
2
+ # V4 released on Apr 2022
3
+ # V2 can be removed on Apr 2024
4
+ #
5
+ # We're duplicating this file for v4, and even though the code lives in two
6
+ # places now, this file isn't expected to evolve and is now frozen to V2
7
+ # behavior.
8
+
1
9
  require 'rails_helper'
2
10
 
3
- describe Dradis::Plugins::Projects::Export::V2::Template do
11
+ describe 'Dradis::Plugins::Projects::Export::V2::Template' do
4
12
  let(:project) { create(:project) }
5
13
  let(:user) { create(:user) }
6
14
  let(:export) do
@@ -0,0 +1,84 @@
1
+ # Run the spec in CE/Pro context with:
2
+ # rspec <relative path to dradis-projects>/spec/lib/dradis/plugins/projects/export/v4/template_spec.rb
3
+
4
+ require 'rails_helper'
5
+
6
+ describe 'Dradis::Plugins::Projects::Export::V4::Template' do
7
+ let(:project) { create(:project) }
8
+ let(:user) { create(:user) }
9
+ let(:exporter) { 'Dradis::Plugins::Projects::Export::V4::Template' }
10
+ let(:export) do
11
+ exporter.constantize.new(
12
+ default_user_id: user.id,
13
+ plugin: Dradis::Plugins::Projects,
14
+ project_id: project.id
15
+ ).export
16
+ end
17
+
18
+ context 'exporting a project' do
19
+ before do
20
+ @node = create(:node, project: project)
21
+ @issue = create(:issue, text: 'Issue 1', node: project.issue_library)
22
+ end
23
+
24
+ describe 'comments' do
25
+ context 'with comments in an issue' do
26
+ before do
27
+ create(:comment, content: 'A comment on an issue', commentable: @issue)
28
+ end
29
+
30
+ it 'exports comments in the issue' do
31
+ expect(export).to include('A comment on an issue')
32
+ end
33
+ end
34
+
35
+ context 'with comments in a note' do
36
+ before do
37
+ note = create(:note, text: 'Note 1', node: @node)
38
+ create(:comment, content: 'A comment on a note', commentable: note)
39
+ end
40
+
41
+ it 'exports comments in the note' do
42
+ expect(export).to include('A comment on a note')
43
+ end
44
+ end
45
+
46
+ context 'with comments in an evidence' do
47
+ before do
48
+ evidence = create(:evidence, content: 'Test evidence', node: @node, issue: @issue)
49
+ create(:comment, content: 'A comment on an evidence', commentable: evidence)
50
+ end
51
+
52
+ it 'exports comments in the evidence' do
53
+ expect(export).to include('A comment on an evidence')
54
+ end
55
+ end
56
+
57
+ context 'with comments with a deleted author' do
58
+ before do
59
+ note = create(:note, text: 'Note 1', node: @node)
60
+ comment = create(:comment, content: 'Deleted user', commentable: note)
61
+ comment.update_attribute :user, nil
62
+ end
63
+
64
+ it 'exports the comment without errors' do
65
+ expect(export).to include('Deleted user')
66
+ end
67
+ end
68
+ end
69
+
70
+ describe 'states' do
71
+ before do
72
+ Issue.states.each do |state|
73
+ create(:issue, text: 'Issue 1', node: project.issue_library, state: state[0])
74
+ end
75
+ end
76
+
77
+ it 'export issues with states' do
78
+ Issue.states.each do |state|
79
+ expect(export).to include("<state>#{state[0]}</state>")
80
+ end
81
+ end
82
+ end
83
+ end
84
+ end
@@ -1,3 +1,11 @@
1
+ # DEPRECATED - this class is v1 of the Template Importer and shouldn't be updated.
2
+ # V4 released on Apr 2022
3
+ # V1 can be removed on Apr 2024
4
+ #
5
+ # We're duplicating this file for v4, and even though the code lives in two
6
+ # places now, this file isn't expected to evolve and is now frozen to V1
7
+ # behavior.
8
+
1
9
  # frozen_string_literal: true
2
10
 
3
11
  require 'rails_helper'
@@ -1,6 +1,14 @@
1
+ # DEPRECATED - this class is v2 of the Template Importer and shouldn't be updated.
2
+ # V4 released on Apr 2022
3
+ # V2 can be removed on Apr 2024
4
+ #
5
+ # We're duplicating this file for v4, and even though the code lives in two
6
+ # places now, this file isn't expected to evolve and is now frozen to V2
7
+ # behavior.
8
+
1
9
  require 'rails_helper'
2
10
 
3
- describe Dradis::Plugins::Projects::Upload::V2::Template::Importer do
11
+ describe 'Dradis::Plugins::Projects::Upload::V2::Template::Importer' do
4
12
  let(:project) { create(:project) }
5
13
  let(:user) { create(:user) }
6
14
  let(:importer_class) { Dradis::Plugins::Projects::Upload::Template }
@@ -0,0 +1,168 @@
1
+ # Run the spec in CE/Pro context with:
2
+ # rspec <relative path to dradis-projects>/spec/lib/dradis/plugins/projects/upload/v4/template_spec.rb
3
+
4
+ require 'rails_helper'
5
+
6
+ describe 'Dradis::Plugins::Projects::Upload::V4::Template::Importer' do
7
+ let(:project) { create(:project) }
8
+ let(:user) { create(:user) }
9
+ let(:importer_class) { Dradis::Plugins::Projects::Upload::Template }
10
+
11
+ context 'uploading a template with attachments url' do
12
+ let(:file_path) do
13
+ File.join(File.dirname(__FILE__), '../../../../../../', 'fixtures', 'files', 'attachments_url.xml')
14
+ end
15
+
16
+ it 'converts the urls' do
17
+ importer = importer_class::Importer.new(
18
+ default_user_id: user.id,
19
+ plugin: importer_class,
20
+ project_id: project.id
21
+ )
22
+
23
+ importer.import(file: file_path)
24
+
25
+ p_id = project.id
26
+ n_id = project.plugin_uploads_node.id
27
+
28
+ expect(project.issues.first.text).to include(
29
+ "!/pro/projects/#{p_id}/nodes/#{n_id}/attachments/hello.jpg!\n\n" +
30
+ "!/projects/#{p_id}/nodes/#{n_id}/attachments/hello.jpg!\n\n" +
31
+ "!/pro/projects/#{p_id}/nodes/#{n_id}/attachments/hello.jpg!\n\n" +
32
+ "!/projects/#{p_id}/nodes/#{n_id}/attachments/hello.jpg!"
33
+ )
34
+ end
35
+ end
36
+
37
+ context 'uploading a template malformed paths as ids' do
38
+ let(:file_path) do
39
+ File.join(File.dirname(__FILE__), '../../../../../../', 'fixtures', 'files', 'malformed_ids.xml')
40
+ end
41
+
42
+ it 'returns false' do
43
+ importer = importer_class::Importer.new(
44
+ default_user_id: user.id,
45
+ plugin: importer_class,
46
+ project_id: project.id
47
+ )
48
+
49
+ expect(importer.import(file: file_path)).to be false
50
+ end
51
+ end
52
+
53
+ context 'uploading a template with attachment but missing node' do
54
+ let(:file_path) do
55
+ File.join(File.dirname(__FILE__), '../../../../../../', 'fixtures', 'files', 'missing_node.xml')
56
+ end
57
+
58
+ it 'does not modify the attachment' do
59
+ logger = double('logger')
60
+ allow(logger).to receive_messages(debug: nil, error: nil, fatal: nil, info: nil)
61
+ expect(logger).to receive(:error).once
62
+
63
+ importer = importer_class::Importer.new(
64
+ default_user_id: user.id,
65
+ logger: logger,
66
+ plugin: importer_class,
67
+ project_id: project.id
68
+ )
69
+
70
+ importer.import(file: file_path)
71
+
72
+ expect(project.issues.first.text).to include(
73
+ "!/pro/projects/222/nodes/12345/attachments/hello.jpg!"
74
+ )
75
+ end
76
+ end
77
+
78
+ context 'uploading a template with comments' do
79
+ let(:file_path) do
80
+ File.join(
81
+ File.dirname(__FILE__),
82
+ '../../../../../../',
83
+ 'fixtures',
84
+ 'files',
85
+ 'with_comments.xml'
86
+ )
87
+ end
88
+
89
+ before do
90
+ importer = importer_class::Importer.new(
91
+ default_user_id: user.id,
92
+ plugin: importer_class,
93
+ project_id: project.id
94
+ )
95
+
96
+ importer.import(file: file_path)
97
+ end
98
+
99
+ let(:node) { project.nodes.find_by(label: 'Node 1') }
100
+
101
+ it 'imports comments in issues' do
102
+ issue = project.issues.first
103
+ expect(issue.comments.first.content).to include('A comment on an issue')
104
+ end
105
+
106
+ it 'imports comments in notes' do
107
+ note = node.notes.first
108
+ expect(note.comments.first.content).to include('A comment on a note')
109
+ end
110
+
111
+ it 'imports comments in evidence' do
112
+ evidence = node.evidence.first
113
+ expect(evidence.comments.first.content).to include('A comment on an evidence')
114
+ end
115
+
116
+ it 'imports comments without user' do
117
+ issue = project.issues.first
118
+ note = node.notes.first
119
+ evidence = node.evidence.first
120
+
121
+ aggregate_failures do
122
+ expect(issue.comments.first.user).to be_nil
123
+ expect(note.comments.first.user).to be_nil
124
+ expect(evidence.comments.first.user).to be_nil
125
+ end
126
+ end
127
+ end
128
+
129
+
130
+ describe 'states' do
131
+ let(:dir) do
132
+ File.join(File.dirname(__FILE__), '../../../../../../', 'fixtures', 'files')
133
+ end
134
+
135
+ before do
136
+ @importer = importer_class::Importer.new(
137
+ default_user_id: user.id,
138
+ plugin: importer_class,
139
+ project_id: project.id
140
+ )
141
+ end
142
+
143
+ context 'uploading a template without states' do
144
+ it 'imports issues with the published state' do
145
+ @importer.import(file: File.join(dir, 'with_comments.xml'))
146
+ issue = project.issues.first
147
+ expect(issue.state).to eq('published')
148
+ end
149
+ end
150
+
151
+ context 'uploading a template with states' do
152
+ context 'valid states' do
153
+ it 'imports issues with states from the template' do
154
+ @importer.import(file: File.join(dir, 'with_states.xml'))
155
+ issue = project.issues.first
156
+ expect(issue.state).to eq('ready_for_review')
157
+ end
158
+ end
159
+
160
+ context 'invalid states' do
161
+ it 'does not import the issue' do
162
+ @importer.import(file: File.join(dir, 'with_invalid_states.xml'))
163
+ expect(project.issues.count).to eq(0)
164
+ end
165
+ end
166
+ end
167
+ end
168
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dradis-projects
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.6.0
4
+ version: 4.8.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Daniel Martin
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-11-20 00:00:00.000000000 Z
11
+ date: 2023-04-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -42,16 +42,16 @@ dependencies:
42
42
  name: rake
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
- - - "~>"
45
+ - - ">="
46
46
  - !ruby/object:Gem::Version
47
- version: '10.0'
47
+ version: 12.3.3
48
48
  type: :development
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
- - - "~>"
52
+ - - ">="
53
53
  - !ruby/object:Gem::Version
54
- version: '10.0'
54
+ version: 12.3.3
55
55
  - !ruby/object:Gem::Dependency
56
56
  name: rspec
57
57
  requirement: !ruby/object:Gem::Requirement
@@ -70,16 +70,16 @@ dependencies:
70
70
  name: dradis-plugins
71
71
  requirement: !ruby/object:Gem::Requirement
72
72
  requirements:
73
- - - "~>"
73
+ - - ">="
74
74
  - !ruby/object:Gem::Version
75
- version: '4.0'
75
+ version: 4.8.0
76
76
  type: :runtime
77
77
  prerelease: false
78
78
  version_requirements: !ruby/object:Gem::Requirement
79
79
  requirements:
80
- - - "~>"
80
+ - - ">="
81
81
  - !ruby/object:Gem::Version
82
- version: '4.0'
82
+ version: 4.8.0
83
83
  - !ruby/object:Gem::Dependency
84
84
  name: rubyzip
85
85
  requirement: !ruby/object:Gem::Requirement
@@ -125,21 +125,27 @@ files:
125
125
  - lib/dradis/plugins/projects/export/v1/template.rb
126
126
  - lib/dradis/plugins/projects/export/v2/template.rb
127
127
  - lib/dradis/plugins/projects/export/v3/template.rb
128
+ - lib/dradis/plugins/projects/export/v4/template.rb
128
129
  - lib/dradis/plugins/projects/gem_version.rb
129
130
  - lib/dradis/plugins/projects/upload/package.rb
130
131
  - lib/dradis/plugins/projects/upload/template.rb
131
132
  - lib/dradis/plugins/projects/upload/v1/template.rb
132
133
  - lib/dradis/plugins/projects/upload/v2/template.rb
133
134
  - lib/dradis/plugins/projects/upload/v3/template.rb
135
+ - lib/dradis/plugins/projects/upload/v4/template.rb
134
136
  - lib/dradis/plugins/projects/version.rb
135
137
  - lib/tasks/thorfile.rb
136
138
  - spec/fixtures/files/attachments_url.xml
137
139
  - spec/fixtures/files/malformed_ids.xml
138
140
  - spec/fixtures/files/missing_node.xml
139
141
  - spec/fixtures/files/with_comments.xml
142
+ - spec/fixtures/files/with_invalid_states.xml
143
+ - spec/fixtures/files/with_states.xml
140
144
  - spec/lib/dradis/plugins/projects/export/v2/template_spec.rb
145
+ - spec/lib/dradis/plugins/projects/export/v4/template_spec.rb
141
146
  - spec/lib/dradis/plugins/projects/upload/v1/template_spec.rb
142
147
  - spec/lib/dradis/plugins/projects/upload/v2/template_spec.rb
148
+ - spec/lib/dradis/plugins/projects/upload/v4/template_spec.rb
143
149
  homepage: http://dradisframework.org
144
150
  licenses:
145
151
  - GPL-2
@@ -168,6 +174,10 @@ test_files:
168
174
  - spec/fixtures/files/malformed_ids.xml
169
175
  - spec/fixtures/files/missing_node.xml
170
176
  - spec/fixtures/files/with_comments.xml
177
+ - spec/fixtures/files/with_invalid_states.xml
178
+ - spec/fixtures/files/with_states.xml
171
179
  - spec/lib/dradis/plugins/projects/export/v2/template_spec.rb
180
+ - spec/lib/dradis/plugins/projects/export/v4/template_spec.rb
172
181
  - spec/lib/dradis/plugins/projects/upload/v1/template_spec.rb
173
182
  - spec/lib/dradis/plugins/projects/upload/v2/template_spec.rb
183
+ - spec/lib/dradis/plugins/projects/upload/v4/template_spec.rb