lundi 2 novembre 2015

How to test a method that does a *lot* of argument processing?

I have the following method defined in my app:

def self.analyze(params)
  processed_params = params.flat_map do |metric, value|
    Moods::Processors.processors[metric].map { |p| p.process(value) }
  end

  weighted_moods = processed_params.inject(Hash.new(0)) do |memo, pp|
    memo.merge(pp) { |_, left, right| left + right }
  end

  normalized_moods = Moods.pairs.each_with_object({}) do |(pos, neg), memo|
    normalized_weight = weighted_moods[pos] - weighted_moods[neg]
    if normalized_weight > 0.0
      memo[pos] = normalized_weight
    elsif normalized_weight < 0.0
      memo[neg] = normalized_weight.abs
    end
  end

  sorted_moods = normalized_moods.sort_by { |_, v| -v }.map(&:first)

  mood_combinations = sorted_moods.size.downto(1).flat_map do |i|
    sorted_moods.combination(i).to_a
  end
end

My main concern is: how do I test this method? The only approachable way I see is compute some generic scenarios that roughly go through each case/branch in the code. But this isn't thorough testing.

Another idea is to separate each snippet of code in a private method and unit test it. But private methods shouldn't be tested...

If I want to the everything thorough, I would probably end up with some very complicated matrix.

So, which is the desired way to test this method?

Aucun commentaire:

Enregistrer un commentaire