Skip to content

Commit

Permalink
Improved documentation and added bootstrap 2.x stuff to produce HTML
Browse files Browse the repository at this point in the history
reports
  • Loading branch information
thesp0nge committed Feb 5, 2014
1 parent f1e6460 commit 9634185
Show file tree
Hide file tree
Showing 9 changed files with 2,252 additions and 30 deletions.
57 changes: 36 additions & 21 deletions README.md
Expand Up @@ -115,28 +115,32 @@ $ dawn [options] target
In case of need, there is a quick command line option reference running ```dawn -h``` at your OS prompt.

```
$ bundle exec dawn -h
08:05:21 [*] dawn v1.0.0 is starting up
Usage: dawn [options] target_directory
$ dawn -h
Usage: dawn [options] target_directory
Examples:$ dawn a_sinatra_webapp_directory
$ dawn -C the_rails_blog_engine
$ dawn -C --output json a_sinatra_webapp_directory
-r, --rails force dawn to consider the target a rails application
-s, --sinatra force dawn to consider the target a sinatra application
-p, --padrino force dawn to consider the target a padrino application
-G, --gem-lock force dawn to scan only for vulnerabilities affecting dependencies in Gemfile.lock
-D, --debug enters dawn debug mode
-f, --list-known-framework list ruby MVC frameworks supported by dawn
-k, --list-knowledgebase [check_name] list dawn known security checks. If check_name is specified dawn says if check is present or not
-o, --output [console, json. csv, html] the output will be in the specified format
-V, --verbose the output will be more verbose
-C, --count-only dawn will only count vulnerabilities (useful for scripts)
-z, --exit-on-warn dawn will return number of found vulnerabilities as exit code
-v, --version show version information
-h, --help show this help
Examples:
$ dawn a_sinatra_webapp_directory
$ dawn -C the_rails_blog_engine
$ dawn -C --json a_sinatra_webapp_directory
$ dawn --ascii-tabular-report my_rails_blog_ecommerce
$ dawn --html -F my_report.html my_rails_blog_ecommerce
-r, --rails force dawn to consider the target a rails application
-s, --sinatra force dawn to consider the target a sinatra application
-p, --padrino force dawn to consider the target a padrino application
-G, --gem-lock force dawn to scan only for vulnerabilities affecting dependencies in Gemfile.lock
-D, --debug enters dawn debug mode
-f, --list-known-framework list ruby MVC frameworks supported by dawn
-k, --list-knowledgebase [check_name] list dawn known security checks. If check_name is specified dawn says if check is present or not
-a, --ascii-tabular-report cause dawn to format findings using table in ascii art
-j, --json cause dawn to format findings using json
-V, --verbose the output will be more verbose
-C, --count-only dawn will only count vulnerabilities (useful for scripts)
-z, --exit-on-warn dawn will return number of found vulnerabilities as exit code
-F, --file tells dawn to write output to filename
-v, --version show version information
-h, --help show this help
```

### Codesake::Dawn security scan in action
Expand Down Expand Up @@ -227,6 +231,17 @@ This check will analyze the source code looking for the following patterns: XXX,
08:28:18 [*] dawn is leaving
```

If you need a fancy HTML report about your scan, just ask to Codesake::Dawn

```
$ dawn /Users/thesp0nge/src/hacking/rt_first_app --html --file report.html (ruby-2.0.0-p353@codesake)
09:00:54 [*] dawn v1.1.0 is starting up
09:00:54 [!] dawn: this is a development Codesake::Dawn version
09:00:54 [*] dawn: report.html created (2952 bytes)
09:00:54 [*] dawn is leaving
```

---

## Useful links
Expand Down Expand Up @@ -263,7 +278,7 @@ Thank you.

[saten](https://github.com/saten): first issue posted about a typo in the README

[presidentbeef](https://github.com/presidentbeef): for his outstanding work that inspired me creating dawn and for double check comparison matrix. Issue #2 is your :)
[presidentbeef](https://github.com/presidentbeef): for his outstanding work that inspired me creating dawn and for double check comparison matrix. Issue #2 is yours :)

[marinerJB](https://github.com/marinerJB): for misc bug reports and further ideas

Expand Down
1 change: 1 addition & 0 deletions Roadmap.md
Expand Up @@ -54,6 +54,7 @@ _latest update: Thu Jan 30 08:39:13 CET 2014_
* Create a digital signature as described [here](http://rubygems.rubyforge.org/rubygems-update/Gem/Security.html)
* Add preliminary Cross Site Scripting detection for Ruby on Rails.
* bin/dawn refactoring using the new Reporting class to produce json, csv, html output
* add config file with setting (css directory, report options, ...)

## Version 1.2.0

Expand Down
13 changes: 9 additions & 4 deletions bin/dawn
Expand Up @@ -17,6 +17,7 @@ $logger = Codesake::Commons::Logging.instance
opts = GetoptLong.new(
[ '--ascii-tabular-report', '-a', GetoptLong::NO_ARGUMENT],
[ '--json', '-j', GetoptLong::NO_ARGUMENT],
[ '--html', '-H', GetoptLong::NO_ARGUMENT],
[ '--rails', '-r', GetoptLong::NO_ARGUMENT],
[ '--sinatra', '-s', GetoptLong::NO_ARGUMENT],
[ '--padrino', '-p', GetoptLong::NO_ARGUMENT],
Expand All @@ -27,11 +28,12 @@ opts = GetoptLong.new(
[ '--debug', '-D', GetoptLong::NO_ARGUMENT],
[ '--count-only', '-C', GetoptLong::NO_ARGUMENT],
[ '--exit-on-warn', '-z', GetoptLong::NO_ARGUMENT],
[ '--file', '-F', GetoptLong::REQUIRED_ARGUMENT],
[ '--version', '-v', GetoptLong::NO_ARGUMENT],
[ '--help', '-h', GetoptLong::NO_ARGUMENT]
)
engine = nil
options = {:verbose=>false, :output=>"console", :dump_kb=>false, :mvc=>"", :gemfile_scan=>false, :gemfile_name=>"", :debug=>false, :exit_on_warn => false}
options = {:verbose=>false, :output=>"console", :dump_kb=>false, :mvc=>"", :gemfile_scan=>false, :gemfile_name=>"", :filename=>nil, :debug=>false, :exit_on_warn => false}

check = ""
guess = {:name=>"", :version=>"", :connected_gems=>[]}
Expand All @@ -46,18 +48,21 @@ opts.each do |opt, val|
options[:output] = "json"
when '--ascii-tabular-report'
options[:output] = "tabular"
when '--html'
options[:output] = "html"
when '--rails'
options[:mvc]=:rails
when '--sinatra'
options[:mvc]=:sinatra
when '--padrino'
options[:mvc]=:padrino
when '--file'
options[:filename] = val
when '--gem-lock'
options[:gemfile_scan] = true
unless val.empty?
options[:gemfile_name] = val
guess = Codesake::Dawn::Core.guess_mvc(val)
puts "Guessed MVC: #{guess[:name]} v#{guess[:version]}"
end

when '--verbose'
Expand Down Expand Up @@ -114,7 +119,7 @@ unless options[:gemfile_scan]
$logger.die(e.message)
end
else
engine = Codesake::Dawn::GemfileLock.new(target, options[:gemfile_name], options[:debug], guess) # if options[:gemfile_scan]
engine = Codesake::Dawn::GemfileLock.new(target, options[:gemfile_name], guess) # if options[:gemfile_scan]
end

engine = Codesake::Dawn::Rails.new(target) if options[:mvc] == :rails && options[:gemfile_scan].nil?
Expand Down Expand Up @@ -149,5 +154,5 @@ if options[:output] == "count"
Kernel.exit(0)
end

Codesake::Dawn::Reporter.new({:engine=>engine, :apply_all_code=>ret, :format=>options[:output].to_sym}).report
Codesake::Dawn::Reporter.new({:engine=>engine, :apply_all_code=>ret, :format=>options[:output].to_sym, :filename=>options[:filename]}).report
$logger.bye
2 changes: 2 additions & 0 deletions lib/codesake/dawn/core.rb
Expand Up @@ -9,6 +9,7 @@ def self.help
puts "\t$ dawn -C the_rails_blog_engine"
puts "\t$ dawn -C --json a_sinatra_webapp_directory"
puts "\t$ dawn --ascii-tabular-report my_rails_blog_ecommerce"
puts "\t$ dawn --html -F my_report.html my_rails_blog_ecommerce"
printf "\n -r, --rails\t\t\t\t\tforce dawn to consider the target a rails application"
printf "\n -s, --sinatra\t\t\t\tforce dawn to consider the target a sinatra application"
printf "\n -p, --padrino\t\t\t\tforce dawn to consider the target a padrino application"
Expand All @@ -21,6 +22,7 @@ def self.help
printf "\n -V, --verbose\t\t\t\tthe output will be more verbose"
printf "\n -C, --count-only\t\t\t\tdawn will only count vulnerabilities (useful for scripts)"
printf "\n -z, --exit-on-warn\t\t\t\tdawn will return number of found vulnerabilities as exit code"
printf "\n -F, --file\t\t\t\t\ttells dawn to write output to filename"
printf "\n -v, --version\t\t\t\tshow version information"
printf "\n -h, --help\t\t\t\t\tshow this help\n"

Expand Down
5 changes: 2 additions & 3 deletions lib/codesake/dawn/gemfile_lock.rb
Expand Up @@ -3,9 +3,8 @@ module Dawn
class GemfileLock
include Codesake::Dawn::Engine

def initialize(dir = "./", filename = "", debug, guessed_mvc)
debug_me "GUESSED MVS IS #{guessed_mvc}"
super(dir, "Gemfile.lock", {:gemfile_name=>filename, :debug=>debug, :guessed_mvc=>guessed_mvc})
def initialize(dir = "./", filename = "", guessed_mvc)
super(dir, "Gemfile.lock", {:gemfile_name=>filename, :guessed_mvc=>guessed_mvc})
end

end
Expand Down
105 changes: 103 additions & 2 deletions lib/codesake/dawn/reporter.rb
Expand Up @@ -6,6 +6,7 @@ def initialize(options={})
@engine = nil
@ret = false

@filename = options[:filename]
@ret = options[:apply_all_code] unless options[:apply_all_code].nil?
@format = options[:format] unless options[:format].nil?
@engine = options[:engine] unless options[:engine].nil?
Expand All @@ -17,15 +18,110 @@ def report
ascii_tabular_report if @format == :tabular
json_report if @format == :json
ascii_plain_report if @format == :console
html_report if @format == :html
end
private

def write(output)

puts output if @filename.nil?

unless @filename.nil?
$logger.warn "I will use codesake.css, bootstrap.min.css and bootstrap.js stored in ./support/ directory" if @format == :html
File.open(@filename, "w") do |f|
f.puts output
end
$logger.ok "#{@filename} created (#{output.length} bytes)"
end
end
def is_valid_format?(format)
return false if format.nil?
return true if (format == :console) || (format == :tabular) || (format == :json) || (format == :html) || (format == :csv)
return false # otherwise
end

def html_report
html_head = "<!doctype html><html><head><title>Codesake::Dawn report for #{File.basename(@engine.target)}</title>"
html_head += "<script src=\"./support/bootstrap.js\"></script>"
html_head += "<link href=\"./support/codesake.css\" media=\"all\" rel=\"stylesheet\" />"
html_head += "<link href=\"./support/bootstrap.min.css\" media=\"all\" rel=\"stylesheet\" />"
html_head += "</head>"
html_body = "<body>"
html_body += ""
html_body += "<div id=\"wrap\">"
html_body += "<div class=\"container-narrow\">"
html_body += "<div class=\"masthead\">"
html_body += "<ul class=\"nav nav-pills pull-right\">"
html_body += "<li class=\"\"><a href=\"https://dawn.codesake.com\">Home</a></li>"
html_body += "<li class=\"active\"><a href=\"https://github.com/codesake/codesake-dawn\">Github repo</a></li>"
html_body += "</ul>"
html_body += "<h3 class=\"muted\">Codesake::Dawn</h3>"
html_body += "</div>"
html_body += "<h1>Security code review results for \"#{File.basename(@engine.target)}\"</h1>"
html_body += "<hr />"
html_body += "<h2>Scan detail</h2>"
html_body += "<div class=\"row\">"
html_body += "<p>The scan was last executed #{@engine.scan_start.strftime("%d %b %Y - %T")} and Codesake::Dawn founds #{@engine.count_vulnerabilities} vulnerabilities</p>"
html_body += "</div>"


html_body += "<hr />"
html_body += "<h2>Scan details</h2>"
html_body += "<table class=\"table-striped table-bordered table\">"
html_body += "<thead><tr><td>Key</td><td>Value</td></tr></thead>"
html_body += "<tbody>"
html_body += "<tr><td>Dawn version</td><td>#{Codesake::Dawn::VERSION}</td></tr>" unless Codesake::Dawn::RELEASE == "(development)"
html_body += "<tr><td>Dawn development version</td><td>#{Codesake::Dawn::VERSION}</td></tr>" if Codesake::Dawn::RELEASE == "(development)"
html_body += "<tr><td>Scan duration</td><td>#{@engine.scan_time.round(3)} sec</td></tr>"
html_body += "<tr><td>Target</td><td>#{@engine.target}</td></tr>"
html_body += "<tr><td>MVC detected framework</td><td>#{@engine.name} v#{@engine.get_mvc_version}</td></tr>" unless @engine.name == "Gemfile.lock"
html_body += "<tr><td>MVC detected framework</td><td>#{@engine.force} v#{@engine.get_mvc_version}</td></tr>" if @engine.name == "Gemfile.lock"
if @ret
html_body += "<tr><td>Applied checks</td><td>#{@engine.applied_checks} security checks</td></tr>"
html_body += "<tr><td>Skipped checks</td><td>#{@engine.skipped_checks} security checks</td></tr>"
else
html_body += "<tr><td>Applied checks</td><td>No security checks in the knowledge base</td></tr>"
end

html_body+="<tr><td>Vulnerabilities found</td><td>#{@engine.count_vulnerabilities}</td></tr>"
html_body+="<tr><td>Mitigated issues found</td><td>#{@engine.mitigated_issues.count}</td></tr>"
html_body+="<tr><td>Reflected XSS</td><td>#{@engine.reflected_xss.count}</td></tr>"
html_body += "</tbody>"
html_body += "</table>"



if @engine.count_vulnerabilities > 0
html_body += "<hr />"
html_body += "<h2>Vulnerabilities found</h2> "
html_body += "<table class=\"table-striped table-bordered table\">"
html_body += "<thead><tr><td>Name</td><td>CVSS score</td><td>Description</td><td>Remediation</td></tr></thead>"

@engine.vulnerabilities.each do |vuln|
html_body += "<tr><td><a href=\"#{vuln[:cve_link]}\">#{vuln[:name]}</a></td><td>#{vuln[:cvss_score]}</td><td>#{vuln[:message]}</td><td>#{vuln[:remediation]}</td></tr>"
end
html_body += "</tbody>"
html_body += "</table>"
end
html_body += "<div id=\"push\"></div>"
html_body += "<div id=\"footer\">"
html_body += "<div class=\"container\">"
html_body += "<p class=\"muted credit\">&copy; <a href=\"http://dawn.codesake.com\">Codesake::Dawn</a> &mdash; #{Time.now.strftime("%Y")} &mdash; engine v#{Codesake::Dawn::VERSION} (#{Codesake::Dawn::RELEASE})</p>"
html_body += "</div>"
html_body +="</div>"
html_body += "</div>"
html_body += "</div>"

html_body += "</body>"
html_body += "</html>"


html = html_head + html_body

write(html)
true
end

def ascii_tabular_report

# 0_First table: executive summary
Expand Down Expand Up @@ -84,6 +180,8 @@ def ascii_tabular_report
table = Terminal::Table.new :title=>"Mitigated issues", :headings=>['Issue', 'Description', 'Evidences'], :rows=>rows
puts table
end

true
end


Expand Down Expand Up @@ -119,8 +217,9 @@ def json_report
result[:reflected_xss] << "request parameter \"#{r[:sink_source]}\""
end

puts result.to_json
end
write(result.to_json)
true
end

def ascii_plain_report

Expand Down Expand Up @@ -166,6 +265,8 @@ def ascii_plain_report
end
end
end

true
end
end
end
Expand Down

0 comments on commit 9634185

Please sign in to comment.