Class: Brakeman::Checks

Inherits:
Object
  • Object
show all
Defined in:
lib/brakeman/checks.rb

Overview

Collects up results from running different checks.

Checks can be added with Check.add(check_class)

All .rb files in checks/ will be loaded.

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(options = { }) ⇒ Checks

No need to use this directly.



59
60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/brakeman/checks.rb', line 59

def initialize options = { }
  if options[:min_confidence]
    @min_confidence = options[:min_confidence]
  else
    @min_confidence = Brakeman.get_defaults[:min_confidence]
  end

  @warnings = []
  @template_warnings = []
  @model_warnings = []
  @controller_warnings = []
  @checks_run = []
end

Instance Attribute Details

#checks_runObject (readonly)

Returns the value of attribute checks_run.



13
14
15
# File 'lib/brakeman/checks.rb', line 13

def checks_run
  @checks_run
end

#controller_warningsObject (readonly)

Returns the value of attribute controller_warnings.



13
14
15
# File 'lib/brakeman/checks.rb', line 13

def controller_warnings
  @controller_warnings
end

#model_warningsObject (readonly)

Returns the value of attribute model_warnings.



13
14
15
# File 'lib/brakeman/checks.rb', line 13

def model_warnings
  @model_warnings
end

#template_warningsObject (readonly)

Returns the value of attribute template_warnings.



13
14
15
# File 'lib/brakeman/checks.rb', line 13

def template_warnings
  @template_warnings
end

#warningsObject (readonly)

Returns the value of attribute warnings.



13
14
15
# File 'lib/brakeman/checks.rb', line 13

def warnings
  @warnings
end

Class Method Details

.actually_run_checks(checks, check_runner, app_tree, tracker) ⇒ Object



119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
# File 'lib/brakeman/checks.rb', line 119

def self.actually_run_checks(checks, check_runner, app_tree, tracker)
  threads = [] # Results for parallel
  results = [] # Results for sequential
  parallel = tracker.options[:parallel_checks]
  error_mutex = Mutex.new

  checks.each do |c|
    check_name = get_check_name c
    Brakeman.notify " - #{check_name}"

    if parallel
      threads << Thread.new do
        self.run_a_check(c, error_mutex, app_tree, tracker)
      end
    else
      results << self.run_a_check(c, error_mutex, app_tree, tracker)
    end

    #Maintain list of which checks were run
    #mainly for reporting purposes
    check_runner.checks_run << check_name[5..-1]
  end

  threads.each { |t| t.join }

  Brakeman.notify "Checks finished, collecting results..."

  if parallel
    threads.each do |thread|
      thread.value.each do |warning|
        check_runner.add_warning warning
      end
    end
  else
    results.each do |warnings|
      warnings.each do |warning|
        check_runner.add_warning warning
      end
    end
  end

  check_runner
end

.add(klass) ⇒ Object

Add a check. This will call klass.new when running tests



16
17
18
# File 'lib/brakeman/checks.rb', line 16

def self.add klass
  @checks << klass unless @checks.include? klass
end

.add_optional(klass) ⇒ Object

Add an optional check



21
22
23
# File 'lib/brakeman/checks.rb', line 21

def self.add_optional klass
  @optional_checks << klass unless @checks.include? klass
end

.checksObject



25
26
27
# File 'lib/brakeman/checks.rb', line 25

def self.checks
  @checks + @optional_checks
end

.initialize_checks(check_directory = "") ⇒ Object



33
34
35
36
37
38
# File 'lib/brakeman/checks.rb', line 33

def self.initialize_checks check_directory = ""
  #Load all files in check_directory
  Dir.glob(File.join(check_directory, "*.rb")).sort.each do |f|
    require f
  end
end

.missing_checks(included_checks, excluded_checks) ⇒ Object



40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
# File 'lib/brakeman/checks.rb', line 40

def self.missing_checks included_checks, excluded_checks
  included_checks = included_checks.map(&:to_s).to_set
  excluded_checks = excluded_checks.map(&:to_s).to_set

  if included_checks == Set['CheckNone']
    return []
  else
    loaded = self.checks.map { |name| name.to_s.gsub('Brakeman::', '') }.to_set
    missing = (included_checks - loaded) + (excluded_checks - loaded)

    unless missing.empty?
      return missing
    end
  end

  []
end

.optional_checksObject



29
30
31
# File 'lib/brakeman/checks.rb', line 29

def self.optional_checks
  @optional_checks
end

.run_checks(app_tree, tracker) ⇒ Object

Run all the checks on the given Tracker. Returns a new instance of Checks with the results.



113
114
115
116
117
# File 'lib/brakeman/checks.rb', line 113

def self.run_checks(app_tree, tracker)
  checks = self.checks_to_run(tracker)
  check_runner = self.new :min_confidence => tracker.options[:min_confidence]
  self.actually_run_checks(checks, check_runner, app_tree, tracker)
end

Instance Method Details

#add_warning(warning) ⇒ Object

Add Warning to list of warnings to report. Warnings are split into four different arrays for template, controller, model, and generic warnings.

Will not add warnings which are below the minimum confidence level.



78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
# File 'lib/brakeman/checks.rb', line 78

def add_warning warning
  unless warning.confidence > @min_confidence
    case warning.warning_set
    when :template
      @template_warnings << warning
    when :warning
      @warnings << warning
    when :controller
      @controller_warnings << warning
    when :model
      @model_warnings << warning
    else
      raise "Unknown warning: #{warning.warning_set}"
    end
  end
end

#all_warningsObject

Return an array of all warnings found.



107
108
109
# File 'lib/brakeman/checks.rb', line 107

def all_warnings
  @warnings + @template_warnings + @controller_warnings + @model_warnings
end

#diff(other_checks) ⇒ Object

Return a hash of arrays of new and fixed warnings

diff = checks.diff old_checks
diff[:fixed]  # [...]
diff[:new]    # [...]


100
101
102
103
104
# File 'lib/brakeman/checks.rb', line 100

def diff other_checks
  my_warnings = self.all_warnings
  other_warnings = other_checks.all_warnings
  Brakeman::Differ.new(my_warnings, other_warnings).diff
end