class Libis::Services::Sharepoint::Search

Constants

MAX_QUERY_RETRY
MY_QUERY_SYMBOLS

Public Class Methods

new(options = {}) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 34
def initialize(options = {})
  options[:server_url] = (options[:url] || 'https://www.groupware.kuleuven.be/sites/lias') + (options[:url_ext] || '/_vti_bin')
  options[:ssl] = true if options[:server_url] =~ /^https:/
  # options[:soap_url] = options[:server_url].gsub(/^(https?):\/\/)/,"\\1#{CGI.escape(username)}:#{CGI.escape(password)}@") + '/Lists.asmx'
  options[:wsse_auth] = [options[:username], options[:password]]
  options[:soap_url] = options[:server_url] + '/Lists.asmx'
  options[:wsdl_url] = options[:soap_url] + '?wsdl'
  configure options[:wsdl_url], options
  options
end

Public Instance Methods

each(options) { |options[:records][options| ... } click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 62
def each(options)

  # we start with a new search
  restart_query options
  get_next_set options

  while records_to_process? options

    yield options[:result][:records][options[:current]]

    options[:current] += 1

    get_next_set(options) if require_next_set?(options)

  end

  restart_query(options)

end
query(term, options = {}) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 45
def query(term, options = {})

  options[:term] = term

  options[:limit] ||= 100
  options[:value_type] ||= 'Text'
  options[:query_operator] = MY_QUERY_SYMBOLS[options[:query_operator] || '==']

  options[:query_operator] = 'BeginsWith' if term =~ /^[^*]+\*$/
  options[:query_operator] = 'Contains' if term =~ /^\*[^*]+\*$/

  restart_query options

  options

end

Protected Instance Methods

clean_row(row, options) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 212
def clean_row(row, options)

  options[:fields_found] ||= Set.new
  row.keys.each { |k| options[:fields_found] << k }

  fields_to_be_removed = [:ows_MetaInfo]
  fields_to_be_removed = row.keys - options[:field_selection] if options[:field_selection]

  record = SharepointRecord.new

  row.each do |k, v|
    key = k.to_s.gsub(/^@/, '').to_sym
    next if fields_to_be_removed.include? key
    record[key] = v.dot_net_clean
  end

  record

end
get_next_set(options) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 100
def get_next_set(options)

  options[:current] = 0
  options[:set_count] = 0

  retry_count = MAX_QUERY_RETRY

  while retry_count > 0

    warn "Retrying (#{retry_count}) ..." if retry_count < MAX_QUERY_RETRY

    query = {
        'Query' => {
            'Where' => {
                options[:query_operator] => {
                    'FieldRef' => '',
                    'Value' => options[:term],
                    :attributes! => {
                        'FieldRef' => {
                            'Name' => options[:index]
                        },
                        'Value' => {
                            'Type' => options[:value_type]
                        }
                    }
                }
            }
        }
    }

    query_options = {
        'QueryOptions' => {
            'ViewAttributes' => '',
            :attributes! => {
                'ViewAttributes' => {
                    'Scope' => 'RecursiveAll'
                }
            }
        }
    }

    now = Time.now
    window_start = Time.new(now.year, now.month, now.day, 12, 15)
    window_end = Time.new(now.year, now.month, now.day, 13, 15)
    if options[:selection] and now > window_start and now < window_end
      query_options['QueryOptions']['Folder'] = options[:server_url] + 'Gedeelde%20documenten/' + options[:selection] + '/.'
    end

    if options[:next_set]
      query_options['QueryOptions']['Paging'] = ''
      query_options['QueryOptions'][:attributes!]['Paging'] = {'ListItemCollectionPositionNext' => options[:next_set]}
    end

    result = request 'GetListItems', {
                                       soap_options: {
                                           endpoint: options[:soap_url]
                                       },
                                       wsse_auth: options[:wsse_auth],
                                       listName: options[:base],
                                       viewName: '',
                                       query: query,
                                       viewFields: {'ViewFields' => ''},
                                       rowLimit: options[:limit].to_s,
                                       query_options: query_options,
                                       webID: ''
                                   }, {}, options

    if result[:error]
      warn "SOAP error: '#{result[:error]}'"
      raise RuntimeError, 'Too many SOAP errors, giving up.' unless retry_count > 0
    elsif result[:exception]
      warn "SOAP exception: '#{result[:exception].message}'"
      raise result[:exception] unless retry_count > 0
    else
      options[:result] = result
      options[:set_count] = result[:count]
      options[:next_set] = result[:next_set]
      retry_count = 0
      retry_count = MAX_QUERY_RETRY + 1 if options[:set_count] == 0 and options[:next_set]
    end

    retry_count -= 1

  end

end
records_to_process?(options) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 92
def records_to_process?(options)
  options[:current] < options[:set_count]
end
require_next_set?(options) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 96
def require_next_set?(options)
  options[:current] >= options[:set_count] and options[:next_set]
end
restart_query(options) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 84
def restart_query(options)
  options[:start_id] = 0
  options[:result] = nil
  options[:current] = 0
  options[:set_count] = 0
  options[:next_set] = nil
end
result_parser(result, options) click to toggle source
# File lib/libis/services/sharepoint/connector.rb, line 187
def result_parser(result, options)

  records = []
  result = result[:get_list_items_response][:get_list_items_result]

  data = result[:listitems][:data]

  rows = data[:row]
  rows = [rows] unless rows.is_a? Array

  rows.each do |row|
    if options[:selection].nil? or row[:ows_FileRef] =~ /^\d+;#sites\/lias\/Gedeelde documenten\/#{options[:selection]}(|\/.*)$/
      records << clean_row(row, options)
    end
  end

  next_set = data[:@list_item_collection_position_next]

  # the itemcount in the response is not interesting. We count only the records that match our selection criteria.
  count = records.size

  {next_set: next_set, records: records, count: count}

end