module RaptorIO::Protocol::HTTP::Request::Manipulators

Namespace holding all Request manipulators and providing some helper methods for management.

@author Tasos Laskos <tasos_laskos@rapid7.com>

Attributes

library[R]

@return [String] Directory of the manipulators’ repository.

Public Class Methods

available() click to toggle source

@return [Array<Symbol>] Names of all manipulators.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 81
def available
  paths.map { |path| path_to_name path }
end
class_to_name( klass ) click to toggle source

@param [Class] klass Manipulator class. @return [String, nil]

Manipulator shortname, `nil` if the manipulator isn't loaded.
# File lib/raptor-io/protocol/http/request/manipulators.rb, line 194
def class_to_name( klass )
  @manipulators.select { |name, k| return name if k == klass }
  nil
end
each( &block ) click to toggle source

@param [Block] block

Block to be passed each manipulator name=>class.

@return [Enumerator, Manipulators]

`Enumerator` if no `block` is given, `self` otherwise.
# File lib/raptor-io/protocol/http/request/manipulators.rb, line 146
def each( &block )
  return enum_for( __method__ ) if !block_given?
  @manipulators.each( &block )
  self
end
exist?( name ) click to toggle source

@param [String] name Manipulator name. @return [Bool] ‘true` if the given manipulator exists, `false` otherwise.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 181
def exist?( name )
  File.exist? name_to_path( name )
end
library=( directory ) click to toggle source

@param [String] directory Directory including manipulators.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 71
def library=( directory )
  @library = File.expand_path( directory ) + '/'
end
load( manipulator ) click to toggle source

@param [Symbol] manipulator

Loads a manipulator by name.

@return [Class] Loaded manipulator.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 89
def load( manipulator )
  manipulator = normalize_name( manipulator )
  return @manipulators[manipulator] if @manipulators.include? manipulator

  Kernel.load name_to_path( manipulator )
  @manipulators[manipulator]
end
load_all() click to toggle source

Loads all manipulators.

@return [Hash] All manipulators.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 100
def load_all
  paths.each { |path| load path_to_name( path ) }
  loaded
end
loaded() click to toggle source

@return [Hash] All manipulators as a frozen hash.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 153
def loaded
  @manipulators.dup.freeze
end
name_to_path( name ) click to toggle source

@param [String] name Manipulator shortname. @return [String] Manipulator FS path.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 201
def name_to_path( name )
  File.expand_path "#{library}/#{name}.rb"
end
normalize_name( name ) click to toggle source

@param [String, Symbol] name Manipulator name. @return [String] Manipulator name.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 207
def normalize_name( name )
  name.to_s
end
path_to_name( path ) click to toggle source

@param [String] path FS path to a manipulator. @return [String] Manipulator shortname.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 187
def path_to_name( path )
  normalize_name path.gsub( library, '' ).gsub( /(.+)\.rb$/, '\1' )
end
paths() click to toggle source

@return [Array<String>] Paths of all manipulators.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 76
def paths
  Dir.glob( "#{library}**/*.rb" )
end
process( manipulator, client, request, options = {} ) click to toggle source

@param [String] manipulator

Manipulator to run -- will be loaded if needed.

@param [HTTP::Client] client

Applicable client.

@param [HTTP::Request] request

Request to process.

@param [Hash] options

Manipulator options.
# File lib/raptor-io/protocol/http/request/manipulators.rb, line 28
def process( manipulator, client, request, options = {} )
  load( manipulator ).new( client, request, options ).run
end
register( name, klass ) click to toggle source

Registers a manipulator.

@param [Symbol] name @param [Base] klass

@return [Manipulator] ‘self`

@private

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 165
def register( name, klass )
  @manipulators[normalize_name( name )] = klass
  self
end
reset() click to toggle source

Resets the manipulators by unloading all and settings the {#library} to its default setting.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 172
def reset
  unload_all if @manipulators

  @library      = File.expand_path( File.dirname( __FILE__ ) + '/manipulators' ) + '/'
  @manipulators = {}
end
unload( manipulator ) click to toggle source

@param [Symbol] manipulator

Unloads a manipulator by name.

@return [Bool]

`true` if the manipulator was unloaded successfully, `false` if no
matching one was found.
# File lib/raptor-io/protocol/http/request/manipulators.rb, line 111
def unload( manipulator )
  klass = @manipulators.delete( normalize_name( manipulator ) )
  return false if !klass

  container = self
  klass.to_s.gsub( "#{self}::", '' ).split( '::' )[0...-1].each do |c|
    container = container.const_get( c.to_sym )
  end

  container.instance_eval do
    remove_const klass.to_s.split( ':' ).last.to_sym
  end

  # Remove the container namespaces themselves if they're now empty.
  container = self
  klass.to_s.gsub( "#{self}::", '' ).split( '::' )[0...-1].each do |c|
    container = container.const_get( c.to_sym )
    if container != self && container.constants.empty?
      remove_const container.to_s.split( ':' ).last.to_sym
    end
  end

  true
end
unload_all() click to toggle source

Unloads all manipulators.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 137
def unload_all
  @manipulators.keys.each { |manipulator| unload manipulator }
  nil
end
validate_batch_options( manipulators, client ) click to toggle source

Performs batch validation of manipulator options.

@param [Hash{String=>Hash}] manipulators

Manipulators for keys and their options as values.

@param [HTTP::Client] client

Applicable client.

@return [Hash{String=>Hash}]

Manipulators for keys and error hashes as values.
# File lib/raptor-io/protocol/http/request/manipulators.rb, line 42
def validate_batch_options( manipulators, client )
  errors = {}
  manipulators.each do |manipulator, options|
    errors[manipulator] =
        validate_options( manipulator, options, client )
  end
  errors.reject { |_, errs| errs.empty? }
end
validate_batch_options!( manipulators, client ) click to toggle source

Same as {.validate_batch_options} but raises exception on errors.

# File lib/raptor-io/protocol/http/request/manipulators.rb, line 52
def validate_batch_options!( manipulators, client )
  errors = validate_batch_options( manipulators, client )
  if errors.any?
    fail Request::Manipulator::Error::InvalidOptions, errors.to_s
  end
  nil
end
validate_options( manipulator, options, client ) click to toggle source

@param [String] manipulator @param [Hash] options Manipulator options. @param [HTTP::Client] client Applicable client.

@return [Hash{Symbol=>Array<String>}]

Option names keys for and error messages for values.
# File lib/raptor-io/protocol/http/request/manipulators.rb, line 66
def validate_options( manipulator, options, client )
  load( manipulator ).validate_options!( options, client )
end