Class: Kiba::Extend::Transforms::Sort::ByFieldValue

Inherits:
Object
  • Object
show all
Defined in:
lib/kiba/extend/transforms/sort/by_field_value.rb

Overview

Returns all rows, sorted by the values of the given field.

Sort modes

:smart: Values consisting only of digits are converted to Integers for sort. Values consisting only of digits and a single “.” are converted to Floats. Everything else is treated as a String.

:string: All values treated as Strings

Examples:

With defaults

# Used in pipeline as:
# transform Sort::ByFieldValue, field: :id
xform = Sort::ByFieldValue.new(field: :id)
input = [
  {id: "40.75"},
  {id: "a"},
  {id: "41"},
  {id: "400"},
  {id: ""},
  {pid: "40"},
  {id: "40.5"},
  {id: nil},
  {id: "40_ex"},
  {id: "ex"},
  {id: "40"},
  {id: "ex ab"},
  {id: "a|b"},
  {id: "40|41"},
]
result = Kiba::StreamingRunner.transform_stream(input, xform)
  .map{ |row| row }
expected = [
  {id: "40"},
  {id: "40.5"},
  {id: "40.75"},
  {id: "41"},
  {id: "400"},
  {id: "40_ex"},
  {id: "40|41"},
  {id: "a"},
  {id: "a|b"},
  {id: "ex"},
  {id: "ex ab"},
  {id: ""},
  {pid: "40"},
  {id: nil},
]
expect(result).to eq(expected)

With mode = :string and order = :desc

# Used in pipeline as:
# transform Sort::ByFieldValue,
#   field: :id,
#   mode: :string,
#   order: :desc
xform = Sort::ByFieldValue.new(field: :id, mode: :string,
  order: :desc)
input = [
  {id: "40.75"},
  {id: "a"},
  {id: "41"},
  {id: "400"},
  {id: ""},
  {id: "40.5"},
  {id: nil},
  {id: "40_ex"},
  {id: "ex"},
  {id: "40"},
  {id: "ex ab"},
  {id: "a|b"},
  {id: "40|41"},
]
result = Kiba::StreamingRunner.transform_stream(input, xform)
  .map{ |row| row }
expected = [
  {id: "ex ab"},
  {id: "ex"},
  {id: "a|b"},
  {id: "a"},
  {id: "41"},
  {id: "40|41"},
  {id: "40_ex"},
  {id: "400"},
  {id: "40.75"},
  {id: "40.5"},
  {id: "40"},
  {id: ""},
  {id: nil},
]
expect(result).to eq(expected)

With blanks = :first

# Used in pipeline as:
# transform Sort::ByFieldValue,
#   field: :id,
#   blanks: :first
xform = Sort::ByFieldValue.new(field: :id, blanks: :first)
input = [
  {id: "400"},
  {id: ""},
  {id: "a"},
  {id: nil},
  {id: "41"},
]
result = Kiba::StreamingRunner.transform_stream(input, xform)
  .map{ |row| row }
expected = [
  {id: ""},
  {id: nil},
  {id: "41"},
  {id: "400"},
  {id: "a"},
]
expect(result).to eq(expected)

With delim

# Used in pipeline as:
# transform Sort::ByFieldValue,
#   field: :id,
#   delim: "|"
xform = Sort::ByFieldValue.new(field: :id, delim: "|")
input = [
  {id: "an"},
  {id: "400"},
  {id: "a|z"},
  {id: "40"},
  {id: "40|41"},
]
result = Kiba::StreamingRunner.transform_stream(input, xform)
  .map{ |row| row }
expected = [
  {id: "40"},
  {id: "40|41"},
  {id: "400"},
  {id: "a|z"},
  {id: "an"},
]
expect(result).to eq(expected)

Since:

  • 4.0.0

Instance Method Summary collapse

Constructor Details

#initialize(field:, blanks: :last, delim: nil, mode: :smart, order: :asc) ⇒ ByFieldValue

Returns a new instance of ByFieldValue.

Parameters:

  • field (Symbol)

    Field whose values will be used for sort

  • blanks (:first, :last) (defaults to: :last)

    Whether rows with blank values should be sorted first or last

  • delim (String, nil) (defaults to: nil)

    if given, values will be split and only the first of multiple values will be used for sort. If not specified, the whole multivalue string will be used for sort

  • mode (:smart, :string) (defaults to: :smart)
  • order (:asc, :desc) (defaults to: :asc)

    of sortable rows. This does not change where blank values are placed

Since:

  • 4.0.0



157
158
159
160
161
162
163
164
165
# File 'lib/kiba/extend/transforms/sort/by_field_value.rb', line 157

def initialize(field:, blanks: :last, delim: nil, mode: :smart,
  order: :asc)
  @field = field
  @blanks = blanks
  @delim = delim
  @mode = mode
  @order = order
  @rows = {string: [], numeric: [], blank: []}
end

Instance Method Details

#closeObject

Since:

  • 4.0.0



179
180
181
182
183
# File 'lib/kiba/extend/transforms/sort/by_field_value.rb', line 179

def close
  rows[:blank].each { |row| yield row } if blanks == :first
  sorted.each { |entry| yield entry[1] }
  rows[:blank].each { |row| yield row } if blanks == :last
end

#process(row) ⇒ Object

Parameters:

  • row (Hash{ Symbol => String, nil })

Since:

  • 4.0.0



168
169
170
171
172
173
174
175
176
177
# File 'lib/kiba/extend/transforms/sort/by_field_value.rb', line 168

def process(row)
  if row.key?(field)
    val = row[field]
    val.blank? ? rows[:blank] << row : sortable(row, val)
  else
    rows[:blank] << row
  end

  nil
end