class ExcelParser::Workbook

Constants

FORMATS
STANDARD_FORMATS

Public Class Methods

new(file, user_defined_formats = {}) click to toggle source
# File lib/excel_parser.rb, line 51
def initialize(file, user_defined_formats = {})
  @file = file
  zipfile = Tempfile.new("file")
  zipfile.binmode
  zipfile.write(HTTParty.get(@file).body)
  zipfile.close
  @file = zipfile.path
  @zipfs = Zip::File.open(@file)
  @user_defined_formats = user_defined_formats
  read_styles
end

Public Instance Methods

attribute_to_type(t, s) click to toggle source
# File lib/excel_parser.rb, line 128
def attribute_to_type(t, s)
  if t == 's'
    :shared
  elsif t == 'b'
    :boolean
  else
    id = @cell_xfs[s.to_i].to_i
    result = @num_formats[id]

    if result == nil
      if STANDARD_FORMATS.has_key? id
        result = STANDARD_FORMATS[id]
      end
    end
    format = result.downcase.sub('\\', '')

    if @user_defined_formats.has_key? format
      @user_defined_formats[format]
    else
      FORMATS[format] || :string
    end
  end
end
close() click to toggle source
# File lib/excel_parser.rb, line 156
def close
  @zipfs.close
end
read_string_table() click to toggle source
# File lib/excel_parser.rb, line 78
def read_string_table
  return [] unless @zipfs.file.exist? ExcelParser::SharedStringPath

  begin
    shared_string = @zipfs.file.open(ExcelParser::SharedStringPath)
  rescue Zip::Error
    raise ExcelParser::Error, 'Invalid file, could not open shared string file.'
  end

  entry = ''
  @string_table = []
  Nokogiri::XML::Reader(shared_string).each do |node|
    if node.name == "si" and node.node_type == Nokogiri::XML::Reader::TYPE_ELEMENT
      entry = ''
    elsif node.name == "si" and node.node_type == Nokogiri::XML::Reader::TYPE_END_ELEMENT
      @string_table << entry
    elsif node.value?
      entry << node.value
    end
  end
  @string_table
end
read_styles() click to toggle source
# File lib/excel_parser.rb, line 101
def read_styles
  @num_formats = {}
  @cell_xfs = []
  return unless @zipfs.file.exist? ExcelParser::StylesPath

  begin
    doc = Nokogiri::XML(@zipfs.file.open(ExcelParser::StylesPath))
  rescue Zip::Error
    raise ExcelParser::Error, 'Invalid file, could not open styles'
  end

  doc.css('/styleSheet/numFmts/numFmt').each do |numFmt|
    if numFmt.attributes['numFmtId'] && numFmt.attributes['formatCode']
      numFmtId = numFmt.attributes['numFmtId'].value.to_i
      formatCode = numFmt.attributes['formatCode'].value
      @num_formats[numFmtId] = formatCode
    end
  end

  doc.css('/styleSheet/cellXfs/xf').each do |xf|
    if xf.attributes['numFmtId']
      numFmtId = xf.attributes['numFmtId'].value.to_i
      @cell_xfs << numFmtId
    end
  end
end
sheets() click to toggle source
# File lib/excel_parser.rb, line 63
def sheets
  begin
    workbook = Nokogiri::XML::Document.parse(@zipfs.file.open('xl/workbook.xml'))
  rescue Zip::Error
    raise ExcelParser::Error, 'Invalid file, could not open xl/workbook.xml'
  end
  @sheets = workbook.css('sheet').each_with_index.map do |n, i|
    ExcelParser::Sheet.new(self, n.attr('name'), n.attr('sheetId'), i+1)
  end
end
string_table() click to toggle source
# File lib/excel_parser.rb, line 74
def string_table
  @string_table ||= read_string_table
end
zipfs() click to toggle source
# File lib/excel_parser.rb, line 152
def zipfs
  @zipfs
end