owasp-pipeline 0.8.5 → 0.8.6

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
  SHA1:
3
- metadata.gz: bf5efee842fff5ee62a05d074fe47d057bc0dd1d
4
- data.tar.gz: 417d5379d1b73b82a0a20561d5d78d50e907c020
3
+ metadata.gz: e0a8269dc146b2c043c1f82f86a181b69e1bf35e
4
+ data.tar.gz: e1f15cfe853e2d53b8e894033a9b665f4813ff26
5
5
  SHA512:
6
- metadata.gz: 5c44a4dc6c22acacac6b6d3a4b6197da7427ed3373341b28f2c4b1d01064b9d7d3357ae59c9a4020bf7fc2bb462d913db3f353038bbed328d556f427c7d68c12
7
- data.tar.gz: 4a8f15ac36f2533638c0d8fc2d695168bc6bfa3bac7e3d41429b712d6e2b2618cd8b7c068f5b9d5140eaaaab9b9694e3e7100aad1a522e5fb75eefb3780a1206
6
+ metadata.gz: c6ff7447583d96ca3b88da5d54f0c85663879017c3e6d4cc4119e5d1969bfd36e356ab5db1e5aaea5bda4df181a95f39f826acac174d72bd53226058b609c741
7
+ data.tar.gz: 7d811611176d44b8f9d7c3a7955c049430142907f1fb453771724c102617a6a2b49bb9589e6d40e5ba2b880abe08dca874f0039aaadb7ed169fd5e0032ea21a8
@@ -0,0 +1,76 @@
1
+ require 'pipeline/filters/base_filter'
2
+
3
+ class Pipeline::ZAPCondensingFilter < Pipeline::BaseFilter
4
+
5
+ Pipeline::Filters.add self
6
+
7
+ def initialize
8
+ @name = "ZAP Condensing Filter"
9
+ @description = "Consolidate N ZAP warnings to one per issue type."
10
+ end
11
+
12
+ def filter tracker
13
+ Pipeline.debug "Have #{tracker.findings.count} items pre ZAP filter."
14
+ tracker.findings.each do |finding|
15
+ if zap? finding
16
+ if xframe? finding
17
+ record tracker,finding
18
+ elsif xcontenttypeoptions? finding
19
+ record tracker, finding
20
+ elsif dirbrowsing? finding
21
+ record tracker, finding
22
+ elsif xxssprotection? finding
23
+ record tracker, finding
24
+ end
25
+ end
26
+ end
27
+ Pipeline.debug "Have #{tracker.findings.count} items post ZAP filter."
28
+ end
29
+
30
+ def zap? finding
31
+ if finding.source =~ /\AZAP/
32
+ return true
33
+ end
34
+ return false
35
+ end
36
+
37
+ def xframe? finding
38
+ if finding.description == "X-Frame-Options header is not included in the HTTP response to protect against 'ClickJacking' attacks."
39
+ return true
40
+ end
41
+ return false
42
+ end
43
+
44
+ def xcontenttypeoptions? finding
45
+ if finding.description == "The Anti-MIME-Sniffing header X-Content-Type-Options was not set to 'nosniff'. This allows older versions of Internet Explorer and Chrome to perform MIME-sniffing on the response body, potentially causing the response body to be interpreted and displayed as a content type other than the declared content type. Current (early 2014) and legacy versions of Firefox will use the declared content type (if one is set), rather than performing MIME-sniffing."
46
+ return true
47
+ end
48
+ return false
49
+ end
50
+
51
+ def dirbrowsing? finding
52
+ if finding.description == "It is possible to view the directory listing. Directory listing may reveal hidden scripts, include files , backup source files etc which be accessed to read sensitive information."
53
+ return true
54
+ end
55
+ return false
56
+ end
57
+
58
+ def xxssprotection? finding
59
+ if finding.description == "Web Browser XSS Protection is not enabled, or is disabled by the configuration of the 'X-XSS-Protection' HTTP response header on the web server"
60
+ return true
61
+ end
62
+ return false
63
+ end
64
+
65
+ # Is it always true that the findings will be on the same site?
66
+ # For now, we can assume that.
67
+ # Note that this may not be an efficient way to to do this, but it seems to work as a first pass.
68
+ def record tracker, finding
69
+ tracker.findings.delete_if do |to_delete|
70
+ to_delete.description == finding.description
71
+ end
72
+ finding.detail << "\n\t** Consolidated ** - Potentially identified in > 1 spot." # Make sure to note that there were
73
+ tracker.findings.push finding
74
+ end
75
+
76
+ end
@@ -99,6 +99,13 @@ module Pipeline::Options
99
99
  options[:npm_registry] = url
100
100
  end
101
101
 
102
+ opts.on "--exclude path1,path2,path3,etc", Array, "A list of paths to ignore when running recursive tasks (npm, retirejs, snyk, etc)" do |paths|
103
+ paths.each do |path|
104
+ options[:exclude_dirs] ||= Set.new
105
+ options[:exclude_dirs] << path
106
+ end
107
+ end
108
+
102
109
  opts.separator ""
103
110
  opts.separator "Output options:"
104
111
 
@@ -43,6 +43,22 @@ class Pipeline::BaseTask
43
43
  @stage
44
44
  end
45
45
 
46
+ def directories_with? file, exclude_dirs = []
47
+ exclude_dirs = @tracker.options[:exclude_dirs] if exclude_dirs == [] and @tracker.options[:exclude_dirs]
48
+ results = []
49
+
50
+ Find.find(@trigger.path) do |path|
51
+ if FileTest.directory? path
52
+ Find.prune if exclude_dirs.include? File.basename(path) or exclude_dirs.include? File.basename(path) + '/'
53
+ next
54
+ end
55
+
56
+ Find.prune unless File.basename(path) == file
57
+
58
+ results << File.dirname(path)
59
+ end
60
+ return results
61
+ end
46
62
 
47
63
  def run
48
64
  end
@@ -17,7 +17,6 @@ class Pipeline::Brakeman < Pipeline::BaseTask
17
17
  end
18
18
 
19
19
  def run
20
- # Pipeline.notify "#{@name}"
21
20
  rootpath = @trigger.path
22
21
  @result=runsystem(true, "brakeman", "-A", "-q", "-f", "json", "#{rootpath}")
23
22
  end
@@ -57,4 +56,3 @@ class Pipeline::Brakeman < Pipeline::BaseTask
57
56
  end
58
57
 
59
58
  end
60
-
@@ -13,14 +13,15 @@ class Pipeline::BundleAudit < Pipeline::BaseTask
13
13
  @description = "Dependency Checker analysis for Ruby"
14
14
  @stage = :code
15
15
  @labels << "code" << "ruby"
16
+ @results = {}
16
17
  end
17
18
 
18
19
  def run
19
- # Pipeline.notify "#{@name}"
20
- rootpath = @trigger.path
21
- Pipeline.debug "Rootpath: #{rootpath}"
22
- Dir.chdir("#{rootpath}") do
23
- @result= runsystem(true, "bundle-audit", "check")
20
+ directories_with?('Gemfile.lock').each do |dir|
21
+ Pipeline.notify "#{@name} scanning: #{dir}"
22
+ Dir.chdir(dir) do
23
+ @results[dir] = runsystem(true, "bundle-audit", "check")
24
+ end
24
25
  end
25
26
  end
26
27
 
@@ -46,43 +47,45 @@ class Pipeline::BundleAudit < Pipeline::BaseTask
46
47
 
47
48
  private
48
49
  def get_warnings
49
- detail, jem, source, sev, hash = '','',{},'',''
50
- @result.each_line do | line |
50
+ @results.each do |dir, result|
51
+ detail, jem, source, sev, hash = '','',{},'',''
52
+ result.each_line do | line |
51
53
 
52
- if /\S/ !~ line
53
- # Signal section is over. Reset variables and report.
54
- if detail != ''
55
- report "Gem #{jem} has known security issues.", detail, source, sev, fingerprint(hash)
56
- end
54
+ if /\S/ !~ line
55
+ # Signal section is over. Reset variables and report.
56
+ if detail != ''
57
+ report "Gem #{jem} has known security issues.", detail, source, sev, fingerprint(hash)
58
+ end
57
59
 
58
- detail, jem, source, sev, hash = '','', {},'',''
59
- end
60
+ detail, jem, source, sev, hash = '','', {},'',''
61
+ end
60
62
 
61
- name, value = line.chomp.split(':')
62
- case name
63
- when 'Name'
64
- jem << value
65
- hash << value
66
- when 'Version'
67
- jem << value
68
- hash << value
69
- when 'Advisory'
70
- source = { :scanner => @name, :file => 'Gemfile.lock', :line => nil, :code => nil }
71
- hash << value
72
- when 'Criticality'
73
- sev = severity(value)
74
- hash << sev
75
- when 'URL'
76
- detail += line.chomp.split('URL:').last
77
- when 'Title'
78
- detail += ",#{value}"
79
- when 'Solution'
80
- detail += ": #{value}"
81
- when 'Insecure Source URI found'
82
- report "Insecure GEM Source", "#{line.chomp} - use git or https", {:scanner => @name, :file => 'Gemfile.lock', :line => nil, :code => nil}, severity('high'), fingerprint("bundlerauditgemsource#{line.chomp}")
83
- else
84
- if line =~ /\S/ and line !~ /Unpatched versions found/
85
- Pipeline.debug "Not sure how to handle line: #{line}"
63
+ name, value = line.chomp.split(':')
64
+ case name
65
+ when 'Name'
66
+ jem << value
67
+ hash << value
68
+ when 'Version'
69
+ jem << value
70
+ hash << value
71
+ when 'Advisory'
72
+ source = { :scanner => @name, :file => "#{relative_path(dir, @trigger.path)}/Gemfile.lock", :line => nil, :code => nil }
73
+ hash << value
74
+ when 'Criticality'
75
+ sev = severity(value)
76
+ hash << sev
77
+ when 'URL'
78
+ detail += line.chomp.split('URL:').last
79
+ when 'Title'
80
+ detail += ",#{value}"
81
+ when 'Solution'
82
+ detail += ": #{value}"
83
+ when 'Insecure Source URI found'
84
+ report "Insecure GEM Source", "#{line.chomp} - use git or https", {:scanner => @name, :file => 'Gemfile.lock', :line => nil, :code => nil}, severity('high'), fingerprint("bundlerauditgemsource#{line.chomp}")
85
+ else
86
+ if line =~ /\S/ and line !~ /Unpatched versions found/
87
+ Pipeline.debug "Not sure how to handle line: #{line}"
88
+ end
86
89
  end
87
90
  end
88
91
  end
@@ -90,4 +93,3 @@ class Pipeline::BundleAudit < Pipeline::BaseTask
90
93
 
91
94
 
92
95
  end
93
-
@@ -16,7 +16,6 @@ class Pipeline::Checkmarx < Pipeline::BaseTask
16
16
  end
17
17
 
18
18
  def run
19
- Pipeline.notify "#{@name}"
20
19
  rootpath = @trigger.path
21
20
  runsystem(true, "runCxConsole.sh", "scan", "-v",
22
21
  "-CxUser", "#{@tracker.options[:checkmarx_user]}",
@@ -16,7 +16,6 @@ class Pipeline::DawnScanner < Pipeline::BaseTask
16
16
  end
17
17
 
18
18
  def run
19
- Pipeline.notify "#{@name}"
20
19
  Dir.chdir("#{@trigger.path}") do
21
20
  @results_file = Tempfile.new(['dawnresults', 'xml'])
22
21
  runsystem(true, "dawn", "-F", "#{@results_file.path}", "-j", ".")
@@ -16,7 +16,6 @@ class Pipeline::ESLint < Pipeline::BaseTask
16
16
  end
17
17
 
18
18
  def run
19
- Pipeline.notify "#{@name}"
20
19
  rootpath = @trigger.path
21
20
  currentpath = File.expand_path File.dirname(__FILE__)
22
21
  Pipeline.debug "ESLint Config Path: #{currentpath}"
@@ -68,4 +67,3 @@ class Pipeline::ESLint < Pipeline::BaseTask
68
67
  end
69
68
 
70
69
  end
71
-
@@ -17,7 +17,6 @@ class Pipeline::FIM < Pipeline::BaseTask
17
17
  end
18
18
 
19
19
  def run
20
- Pipeline.notify "#{@name}"
21
20
  rootpath = @trigger.path
22
21
  if File.exists?("/area81/tmp/#{rootpath}/filehash")
23
22
  Pipeline.notify "File Hashes found, comparing to file system"
@@ -20,14 +20,23 @@ class Pipeline::FindSecurityBugs < Pipeline::BaseTask
20
20
  end
21
21
 
22
22
  def run
23
- Pipeline.notify "#{@name}"
24
23
  @results_file = Tempfile.new(['findsecbugs','xml'])
25
24
 
26
- Dir.chdir("#{@trigger.path}") do
27
- runsystem(true, "mvn", "compile", "-fn")
25
+ unless File.exist?("#{@trigger.path}/.git/config")
26
+ Dir.chdir(@trigger.path) do
27
+ system("git", "init")
28
+ system("git", "add", "*")
29
+ system("git", "commit", "-am", "fake commit for mvn compile")
30
+ end
31
+ end
32
+
33
+ directories_with?('pom.xml').each do |dir|
34
+ Dir.chdir(dir) do
35
+ runsystem(true, "mvn", "compile", "-fn")
36
+ end
28
37
  end
29
38
 
30
- Dir.chdir("#{@tracker.options[:findsecbugs_path]}") do
39
+ Dir.chdir(@tracker.options[:findsecbugs_path]) do
31
40
  runsystem(true, "/bin/sh", "#{@tracker.options[:findsecbugs_path]}/findsecbugs.sh", "-effort:max", "-quiet", "-xml:withMessages", "-output", "#{@results_file.path}", "#{@trigger.path}")
32
41
  @results = Nokogiri::XML(File.read(@results_file)).xpath '//BugInstance'
33
42
  end
@@ -0,0 +1,58 @@
1
+ require 'pipeline/tasks/base_task'
2
+ require 'pipeline/util'
3
+ require 'find'
4
+ require 'pry'
5
+
6
+ class Pipeline::Npm < Pipeline::BaseTask
7
+
8
+ Pipeline::Tasks.add self
9
+ include Pipeline::Util
10
+
11
+ def initialize(trigger, tracker)
12
+ super(trigger, tracker)
13
+ @name = "NPM"
14
+ @description = "Node Package Manager"
15
+ @stage = :file
16
+ @labels << "file" << "javascript"
17
+ @results = []
18
+ end
19
+
20
+ def run
21
+ exclude_dirs = ['node_modules','bower_components']
22
+ exclude_dirs = exclude_dirs.concat(@tracker.options[:exclude_dirs]).uniq if @tracker.options[:exclude_dirs]
23
+ directories_with?('package.json', exclude_dirs).each do |dir|
24
+ Pipeline.notify "#{@name} scanning: #{dir}"
25
+ Dir.chdir(dir) do
26
+ if @tracker.options.has_key?(:npm_registry)
27
+ registry = "--registry #{@tracker.options[:npm_registry]}"
28
+ else
29
+ registry = nil
30
+ end
31
+ @command = "npm install --ignore-scripts #{registry}"
32
+ @results << system(@command)
33
+ end
34
+ end
35
+ end
36
+
37
+ def analyze
38
+ begin
39
+ if @results.include? false
40
+ Pipeline.warn 'Error installing javascript dependencies with #{@command}'
41
+ end
42
+ rescue Exception => e
43
+ Pipeline.warn e.message
44
+ Pipeline.warn e.backtrace
45
+ end
46
+ end
47
+
48
+ def supported?
49
+ supported = find_executable0('npm')
50
+ unless supported
51
+ Pipeline.notify "Install npm: https://nodejs.org/en/download/"
52
+ return false
53
+ else
54
+ return true
55
+ end
56
+ end
57
+
58
+ end
@@ -12,31 +12,37 @@ class Pipeline::NodeSecurityProject < Pipeline::BaseTask
12
12
  @description = "Node Security Project"
13
13
  @stage = :code
14
14
  @labels << "code"
15
+ @results = []
15
16
  end
16
17
 
17
18
  def run
18
- Pipeline.notify "#{@name}"
19
- rootpath = @trigger.path
20
- Dir.chdir("#{rootpath}") do
21
- @results = JSON.parse `nsp check --output json 2>&1`
19
+ exclude_dirs = ['node_modules','bower_components']
20
+ exclude_dirs = exclude_dirs.concat(@tracker.options[:exclude_dirs]).uniq if @tracker.options[:exclude_dirs]
21
+ directories_with?('package.json', exclude_dirs).each do |dir|
22
+ Pipeline.notify "#{@name} scanning: #{dir}"
23
+ Dir.chdir(dir) do
24
+ @results << JSON.parse(`nsp check --output json 2>&1`)
25
+ end
22
26
  end
23
27
  end
24
28
 
25
29
  def analyze
26
30
  begin
27
- # This block iterates through each package name found and selects the unique nsp advisories
28
- # regardless of version, and builds a pipeline finding hash for each unique package/advisory combo.
29
- @results.uniq {|finding| finding['module']}.each do |package|
30
- @results.select {|f| f['module'] == package['module']}.uniq {|m| m['advisory']}.each do |unique_finding|
31
- description = "#{unique_finding['module']} - #{unique_finding['title']}"
32
- detail = "Upgrade to versions: #{unique_finding['patched_versions']}\n#{unique_finding['advisory']}"
33
- source = {
34
- :scanner => 'NodeSecurityProject',
35
- :file => "#{unique_finding['module']} - #{unique_finding['vulnerable_versions']}",
36
- :line => nil,
37
- :code => nil
38
- }
39
- report description, detail, source, 'medium', fingerprint("#{description}#{detail}#{source}")
31
+ @results.each do |dir_result|
32
+ # This block iterates through each package name found and selects the unique nsp advisories
33
+ # regardless of version, and builds a pipeline finding hash for each unique package/advisory combo.
34
+ dir_result.uniq {|finding| finding['module']}.each do |package|
35
+ dir_result.select {|f| f['module'] == package['module']}.uniq {|m| m['advisory']}.each do |unique_finding|
36
+ description = "#{unique_finding['module']} - #{unique_finding['title']}"
37
+ detail = "Upgrade to versions: #{unique_finding['patched_versions']}\n#{unique_finding['advisory']}"
38
+ source = {
39
+ :scanner => 'NodeSecurityProject',
40
+ :file => "#{unique_finding['module']} - #{unique_finding['vulnerable_versions']}",
41
+ :line => nil,
42
+ :code => nil
43
+ }
44
+ report description, detail, source, 'medium', fingerprint("#{description}#{detail}#{source}")
45
+ end
40
46
  end
41
47
  end
42
48
  rescue Exception => e
@@ -56,4 +62,3 @@ class Pipeline::NodeSecurityProject < Pipeline::BaseTask
56
62
  end
57
63
 
58
64
  end
59
-
@@ -17,7 +17,6 @@ class Pipeline::PMD < Pipeline::BaseTask
17
17
  end
18
18
 
19
19
  def run
20
- Pipeline.notify "#{@name}"
21
20
  @tracker.options[:pmd_checks] ||= "java-basic,java-sunsecure"
22
21
  Dir.chdir @tracker.options[:pmd_path] do
23
22
  @results = Nokogiri::XML(`bin/run.sh pmd -d #{@trigger.path} -f xml -R #{@tracker.options[:pmd_checks]}`).xpath('//file')
@@ -3,6 +3,7 @@ require 'json'
3
3
  require 'pipeline/util'
4
4
  require 'jsonpath'
5
5
  require 'pathname'
6
+ require 'pry'
6
7
 
7
8
  class Pipeline::RetireJS < Pipeline::BaseTask
8
9
 
@@ -15,28 +16,26 @@ class Pipeline::RetireJS < Pipeline::BaseTask
15
16
  @description = "Dependency analysis for JavaScript"
16
17
  @stage = :code
17
18
  @labels << "code" << "javascript"
19
+ @results = []
18
20
  end
19
21
 
20
22
  def run
21
- rootpath = @trigger.path
22
- Pipeline.debug "Retire rootpath: #{rootpath}"
23
- Dir.chdir("#{rootpath}") do
24
- if @tracker.options.has_key?(:npm_registry)
25
- registry = "--registry #{@tracker.options[:npm_registry]}"
26
- else
27
- registry = nil
28
- end
29
- @result = `npm install --ignore-scripts #{registry}` # Need this even though it is slow to get full dependency analysis.
23
+ exclude_dirs = ['node_modules','bower_components']
24
+ exclude_dirs = exclude_dirs.concat(@tracker.options[:exclude_dirs]).uniq if @tracker.options[:exclude_dirs]
25
+ directories_with?('package.json', exclude_dirs).each do |dir|
26
+ Pipeline.notify "#{@name} scanning: #{dir}"
27
+ @results << `retire -c --outputformat json --path #{dir} 2>&1`
30
28
  end
31
- @result = `retire -c --outputformat json --path #{rootpath} 2>&1`
32
29
  end
33
30
 
34
31
  def analyze
35
32
  begin
36
- vulnerabilities = parse_retire_json(JSON.parse(@result))
33
+ @results.each do |result|
34
+ vulnerabilities = parse_retire_json(JSON.parse(result))
37
35
 
38
- vulnerabilities.each do |vuln|
39
- report "Package #{vuln[:package]} has known security issues", vuln[:detail], vuln[:source], vuln[:severity], fingerprint("#{vuln[:package]}#{vuln[:source]}#{vuln[:severity]}")
36
+ vulnerabilities.each do |vuln|
37
+ report "Package #{vuln[:package]} has known security issues", vuln[:detail], vuln[:source], vuln[:severity], fingerprint("#{vuln[:package]}#{vuln[:source]}#{vuln[:severity]}")
38
+ end
40
39
  end
41
40
  rescue Exception => e
42
41
  Pipeline.warn e.message
@@ -84,7 +83,7 @@ class Pipeline::RetireJS < Pipeline::BaseTask
84
83
  result.select { |r| !r['file'].nil? }.each do |file_result|
85
84
  JsonPath.on(file_result, '$..component').uniq.each do |comp|
86
85
  JsonPath.on(file_result, "$..results[?(@.component == \'#{comp}\')].version").uniq.each do |version|
87
- source_path = Pathname.new(file_result['file']).relative_path_from Pathname.new(@trigger.path)
86
+ source_path = relative_path(file_result['file'], @trigger.path)
88
87
  vulnerabilities.select { |v| v[:package] == "#{comp}-#{version}" }.first[:source] = { :scanner => @name, :file => source_path.to_s, :line => nil, :code => nil }
89
88
  end
90
89
  end
@@ -103,4 +102,3 @@ class Pipeline::RetireJS < Pipeline::BaseTask
103
102
  end
104
103
 
105
104
  end
106
-
@@ -0,0 +1,81 @@
1
+ require 'pipeline/tasks/base_task'
2
+ require 'pipeline/util'
3
+ require 'redcarpet'
4
+
5
+ class Pipeline::Snyk < Pipeline::BaseTask
6
+
7
+ Pipeline::Tasks.add self
8
+ include Pipeline::Util
9
+
10
+ def initialize(trigger, tracker)
11
+ super(trigger, tracker)
12
+ @name = "Snyk"
13
+ @description = "Snyk.io JS dependency checker"
14
+ @stage = :code
15
+ @labels << "code" << "javascript"
16
+ @results = []
17
+ end
18
+
19
+ def run
20
+ exclude_dirs = ['node_modules','bower_components']
21
+ exclude_dirs = exclude_dirs.concat(@tracker.options[:exclude_dirs]).uniq if @tracker.options[:exclude_dirs]
22
+ directories_with?('package.json', exclude_dirs).each do |dir|
23
+ Pipeline.notify "#{@name} scanning: #{dir}"
24
+ Dir.chdir(dir) do
25
+ @results << JSON.parse(runsystem(true, "snyk", "test", "--json"))["vulnerabilities"]
26
+ end
27
+ end
28
+ end
29
+
30
+ def analyze
31
+ begin
32
+ markdown = Redcarpet::Markdown.new Redcarpet::Render::HTML.new(link_attributes: {target: "_blank"}), autolink: true, tables: true
33
+
34
+ @results.each do |dir_result|
35
+ # We build a single finding for each uniq result ID, adding the unique info (upgrade path and files) as a list
36
+ dir_result.uniq {|r| r['id']}.each do |result|
37
+ description = "#{result['name']}@#{result['version']} - #{result['title']}"
38
+
39
+ # Use Redcarpet to render the Markdown details to something pretty for web display
40
+ detail = markdown.render(result['description']).gsub('h2>','strong>').gsub('h3>', 'strong>')
41
+ upgrade_paths = [ "Upgrade Path:\n" ]
42
+ files = []
43
+
44
+ # Pull the list of files and upgrade paths from all results matching this ID
45
+ # This uses the same form as the retirejs task so it all looks nice together
46
+ dir_result.select{|r| r['id'] == result['id']}.each do |res|
47
+ res['upgradePath'].each_with_index do |upgrade, i|
48
+ upgrade_paths << "#{res['from'][i]} -> #{upgrade}"
49
+ end
50
+ files << res['from'].join('->')
51
+ end
52
+
53
+ source = {
54
+ :scanner => @name,
55
+ :file => files.join('<br>'),
56
+ :line => nil,
57
+ :code => upgrade_paths.uniq.join("\n"),
58
+ }
59
+ sev = severity(result['severity'])
60
+ fprint = fingerprint("#{description}#{detail}#{source}#{sev}")
61
+
62
+ report description, detail, source, sev, fprint
63
+ end
64
+ end
65
+ rescue Exception => e
66
+ Pipeline.warn e.message
67
+ Pipeline.warn e.backtrace
68
+ end
69
+ end
70
+
71
+ def supported?
72
+ supported = find_executable0('snyk')
73
+ unless supported
74
+ Pipeline.notify "Install Snyk: 'npm install -g snyk'"
75
+ return false
76
+ else
77
+ return true
78
+ end
79
+ end
80
+
81
+ end
@@ -24,7 +24,10 @@ class Pipeline::Zap < Pipeline::BaseTask
24
24
  context = SecureRandom.uuid
25
25
 
26
26
  Pipeline.debug "Running ZAP on: #{rootpath} from #{base} with #{context}"
27
-
27
+
28
+ # Create a new session so that the findings will be new.
29
+ Curl.get("#{base}/JSON/core/action/newSession/?zapapiformat=JSON&apikey=#{apikey}&name=&overwrite=")
30
+
28
31
  # Set up Context
29
32
  Curl.get("#{base}/JSON/context/action/newContext/?&apikey=#{apikey}&contextName=#{context}")
30
33
  Curl.get("#{base}/JSON/context/action/includeInContext/?apikey=#{apikey}&contextName=#{context}&regex=#{rootpath}.*")
@@ -85,10 +88,10 @@ class Pipeline::Zap < Pipeline::BaseTask
85
88
  def supported?
86
89
  base = "#{@tracker.options[:zap_host]}:#{@tracker.options[:zap_port]}"
87
90
  supported=JSON.parse(Curl.get("#{base}/JSON/core/view/version/").body_str)
88
- if supported["version"] == "2.4.3"
91
+ if supported["version"] =~ /2.(4|5).\d+/
89
92
  return true
90
93
  else
91
- Pipeline.notify "Install ZAP from owasp.org and ensure that the configuration to connect is correct."
94
+ Pipeline.notify "Install ZAP from owasp.org and ensure that the configuration to connect is correct. Supported versions = 2.4.0 and up - got #{supported['version']}"
92
95
  return false
93
96
  end
94
97
  end
@@ -60,8 +60,8 @@ class Pipeline::Tasks
60
60
 
61
61
  #Run or don't run task based on options
62
62
  #Now case-insensitive specifiers: nodesecurityproject = Pipeline::NodeSecurityProject
63
-
64
- if tracker.options[:skip_tasks]
63
+
64
+ if tracker.options[:skip_tasks]
65
65
  skip_tasks = tracker.options[:skip_tasks].map {|task| task.downcase}
66
66
  end
67
67
  if (tracker.options[:run_tasks])
@@ -73,9 +73,9 @@ class Pipeline::Tasks
73
73
 
74
74
  task = c.new(trigger, tracker)
75
75
  begin
76
- if task.supported? and task.stage == stage
77
- if task.labels.intersect? tracker.options[:labels] or # Only run tasks with labels
78
- ( run_tasks and run_tasks.include? task_name.downcase ) # or that are explicitly requested.
76
+ if task.supported? and task.stage == stage
77
+ if task.labels.intersect? tracker.options[:labels] or # Only run tasks with labels
78
+ ( run_tasks and run_tasks.include? task_name.downcase ) # or that are explicitly requested.
79
79
  Pipeline.notify "#{stage} - #{task_name} - #{task.labels}"
80
80
  task.run
81
81
  task.analyze
@@ -1,3 +1,3 @@
1
1
  module Pipeline
2
- Version = "0.8.5"
2
+ Version = "0.8.6"
3
3
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: owasp-pipeline
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.8.5
4
+ version: 0.8.6
5
5
  platform: ruby
6
6
  authors:
7
7
  - Matt Konda
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2016-03-07 00:00:00.000000000 Z
13
+ date: 2016-04-20 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: terminal-table
@@ -166,6 +166,20 @@ dependencies:
166
166
  - - ">="
167
167
  - !ruby/object:Gem::Version
168
168
  version: 1.6.0
169
+ - !ruby/object:Gem::Dependency
170
+ name: redcarpet
171
+ requirement: !ruby/object:Gem::Requirement
172
+ requirements:
173
+ - - ">="
174
+ - !ruby/object:Gem::Version
175
+ version: '0'
176
+ type: :runtime
177
+ prerelease: false
178
+ version_requirements: !ruby/object:Gem::Requirement
179
+ requirements:
180
+ - - ">="
181
+ - !ruby/object:Gem::Version
182
+ version: '0'
169
183
  - !ruby/object:Gem::Dependency
170
184
  name: pry
171
185
  requirement: !ruby/object:Gem::Requirement
@@ -211,6 +225,7 @@ files:
211
225
  - lib/pipeline/filters/base_filter.rb
212
226
  - lib/pipeline/filters/jira_one_time_filter.rb
213
227
  - lib/pipeline/filters/remove_all_filter.rb
228
+ - lib/pipeline/filters/zap_consdensing_filter.rb
214
229
  - lib/pipeline/finding.rb
215
230
  - lib/pipeline/mounters.rb
216
231
  - lib/pipeline/mounters/base_mounter.rb
@@ -237,6 +252,7 @@ files:
237
252
  - lib/pipeline/tasks/eslint.rb
238
253
  - lib/pipeline/tasks/fim.rb
239
254
  - lib/pipeline/tasks/findsecbugs.rb
255
+ - lib/pipeline/tasks/npm.rb
240
256
  - lib/pipeline/tasks/nsp.rb
241
257
  - lib/pipeline/tasks/owasp-dep-check.rb
242
258
  - lib/pipeline/tasks/patterns.json
@@ -245,6 +261,7 @@ files:
245
261
  - lib/pipeline/tasks/scanjs-eslintrc
246
262
  - lib/pipeline/tasks/scanjs.rb
247
263
  - lib/pipeline/tasks/sfl.rb
264
+ - lib/pipeline/tasks/snyk.rb
248
265
  - lib/pipeline/tasks/test.rb
249
266
  - lib/pipeline/tasks/zap.rb
250
267
  - lib/pipeline/tracker.rb