Class: Ratonvirus::Scanner::Base

Inherits:
Object
  • Object
show all
Includes:
Support::Callbacks
Defined in:
lib/ratonvirus/scanner/base.rb

Direct Known Subclasses

Eicar

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(configuration = {}) ⇒ Base

Returns a new instance of Base.



17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
# File 'lib/ratonvirus/scanner/base.rb', line 17

def initialize(configuration = {})
  @config = default_config.merge!(configuration)

  # Make the following callbacks available:
  # - before_process_scan
  # - before_scan
  # - after_scan
  # - after_process_scan
  #
  # Usage:
  #   module CustomAddon
  #     def self.extended(validator)
  #       validator.before_process_scan :around_scan
  #       validator.before_scan :do_something
  #       validator.after_scan :do_something
  #       validator.before_process_scan :around_scan
  #     end
  #
  #     private
  #       def around_scan(resource)
  #         puts resource.inspect
  #         # Depends on the provided resource, e.g.
  #         # => #<ActiveStorage::Attached::One: ...>
  #         # => #<ActiveStorage::Attached::Many: ...>
  #         # => #<CarrierWave::Uploader::Base: ...>
  #         # => #<File: ...>
  #         # => #<String: ...>
  #       end
  #
  #       def do_something(processable)
  #         puts processable.inspect
  #         # => #<Ratonvirus::Processable: ...>
  #       end
  #   end
  define_callbacks :process_scan # Around the scan for the whole resource
  define_callbacks :scan # The actual scan for individual assets

  setup
end

Instance Attribute Details

#configObject (readonly)

:errors - Only available after ‘virus?` has been called.



15
16
17
# File 'lib/ratonvirus/scanner/base.rb', line 15

def config
  @config
end

#errorsObject (readonly)

:errors - Only available after ‘virus?` has been called.



15
16
17
# File 'lib/ratonvirus/scanner/base.rb', line 15

def errors
  @errors
end

Class Method Details

.executable?Boolean

Returns:

  • (Boolean)


9
10
11
# File 'lib/ratonvirus/scanner/base.rb', line 9

def executable?
  false
end

Instance Method Details

#available?Boolean

Returns:

  • (Boolean)


67
68
69
70
71
# File 'lib/ratonvirus/scanner/base.rb', line 67

def available?
  return @available unless @available.nil?

  @available = self.class.executable?
end

#setupObject

This method can be overridden in the scanner implementations in case the setup needs to be customized.



59
60
61
62
63
64
65
# File 'lib/ratonvirus/scanner/base.rb', line 59

def setup
  if config[:force_availability]
    @available = true
  else
    available?
  end
end

#virus?(resource) ⇒ Boolean

The virus? method runs the scan and returns a boolean indicating whether the scanner rejected the given resource or detected a virus. Scanning is mainly used to detect viruses but the scanner can reject the resource also because of other reasons than it detecting a virus.

All these cases, however, should be interpreted as the resource containing a virus because in case there is e.g. a client error, we cannot be sure whether the file contains a virus and therefore it’s safer to assume the worst.

Possible errors are:

  • :antivirus_virus_detected - A virus was detected.

  • :antivirus_file_not_found - The scanner did not find the file for the given resource.

  • :antivirus_client_error - There was a client error at the scanner, e.g. it is temporarily unavailable.

Returns:

  • (Boolean)


89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
# File 'lib/ratonvirus/scanner/base.rb', line 89

def virus?(resource)
  prepare

  @errors = []

  run_callbacks :process_scan, resource do
    storage.process(resource) do |processable|
      # In case multiple processables are processed, make sure that the
      # local errors for each scan refer only to that scan.
      errors_before = @errors
      @errors = []

      begin
        scan(processable)
      ensure
        # Make sure that after the scan, the errors are reverted back to
        # all errors.
        @errors = errors_before + @errors
      end
    end
  end

  # Only show unique errors
  errors.uniq!

  errors.any?
end