module Dyph::TwoWayDiffers::OutputConverter
rubocop:disable Metrics/ModuleLength
Public Instance Methods
convert_to_dyph_output(old_text, new_text)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 7 def convert_to_dyph_output(old_text, new_text) actions = merge_and_partition(old_text, new_text) selected_actions = extract_add_deletes_changes(actions) correct_offsets(selected_actions) end
merge_results(old_text, new_text)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 33 def merge_results(old_text, new_text) merged_text = [] if (new_text.empty?) no_new_text(old_text, merged_text) else prepend_old_text(old_text, merged_text) gather_up_actions(old_text, new_text, merged_text) end merged_text end
objectify(merge_results)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 13 def objectify(merge_results) merge_results.map do |result| action = result[:action] line = result[:line] old_index = result[:old_index] new_index = result[:new_index] case action when :add Dyph::Action::Add.new(value: line, old_index: old_index, new_index: new_index) when :delete Dyph::Action::Delete.new(value: line, old_index: old_index, new_index: new_index) when :no_change Dyph::Action::NoChange.new(value: line.text, old_index: old_index, new_index: new_index) else raise "unhandled action" end end end
Private Instance Methods
change_or_delete(old_text, line, prev_no_change_old, merged_text, index)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 80 def change_or_delete(old_text, line, prev_no_change_old, merged_text, index) merged_text << {action: :no_change, line: line, old_index: line.row, new_index: index} ((prev_no_change_old+1) ... old_text.length).each do |n| break if old_text[n].is_a?(TextNode) merged_text << {action: :delete, line: old_text[n], old_index: n+1, new_index: index+1} end end
collapse_action(actions)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 128 def collapse_action(actions) actions.inject({}) do | hash, action | hash[:action] ||= action[:action] hash[:old_lo] ||= action[:old_lo] hash[:old_hi] = action[:old_hi] hash[:new_lo] ||= action[:new_lo] hash[:new_hi] = action[:new_hi] hash end end
correct_offsets(selected_actions)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 58 def correct_offsets(selected_actions) fix_offsets = set_offset(selected_actions) fix_offsets.map { |r| Dyph::Support::AssignAction.get_action( lo_a: r[:old_lo]-1 , lo_b: r[:new_lo]-1, hi_a: r[:old_hi]-1, hi_b: r[:new_hi]-1 )} end
extract_add_deletes_changes(actions)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 52 def extract_add_deletes_changes(actions) collapsed_actions = actions.map { |action| collapse_action(action) } paired_results = pair_up_add_deletes collapsed_actions paired_results.reject { |res| res[:action] == :no_change} end
gather_up_actions(old_text, new_text, merged_text)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 68 def gather_up_actions(old_text, new_text, merged_text) prev_no_change_old = - 1 new_text.map.with_index.each do |line, i| if !line.is_a?(TextNode) merged_text << {action: :add, line: line, old_index: prev_no_change_old + 1, new_index: i+1} else prev_no_change_old = line.row change_or_delete(old_text, line, prev_no_change_old, merged_text, i) end end end
is_a_pair?(actions, i)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 139 def is_a_pair?(actions, i) action_one = actions[i-1][:action] if actions[i-1] action_two = actions[i][:action] if actions[i] Set.new([action_one, action_two]) == Set.new([:add, :delete]) end
merge_and_partition(old_text, new_text)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 46 def merge_and_partition(old_text, new_text) merged_text = merge_results(old_text, new_text) merge_output_lines = merged_text.map { |x| to_output_format x } partition_into_actions(merge_output_lines) end
no_new_text(old_text, merged_text)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 98 def no_new_text(old_text, merged_text) old_text.map.with_index do |line, i| merged_text << { action: :delete, line: line, old_index: i+1, new_index: i} end end
pair_up_add_deletes(actions)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 145 def pair_up_add_deletes(actions) results = [] found_change = false (1 .. actions.length).each do |i| if is_a_pair?(actions, i) results << { action: :change, old_lo: actions[i-1][:old_lo], old_hi: actions[i-1][:old_hi], new_lo: actions[i][:new_lo], new_hi: actions[i][:new_hi] } found_change = true elsif found_change found_change = false else results << actions[i-1] end end results end
partition_into_actions(array)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 167 def partition_into_actions(array) array.inject([]) do |acc, x| if acc.length == 0 || acc.last.last[:action] != x[:action] acc << [x] else acc.last << x end acc end end
prepend_old_text(old_text, merged_text)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 89 def prepend_old_text(old_text, merged_text) if !old_text.first.is_a?(TextNode) old_text.map.with_index.each do |line, i| break if line.is_a?(TextNode) merged_text << {action: :delete, line: line, old_index:i+1, new_index: i} end end end
set_offset(results)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 104 def set_offset(results) results.map do |result_row| if result_row[:action] == :add result_row[:old_lo] += 1 result_row elsif result_row[:action] == :delete result_row[:new_lo] += 1 result_row else result_row end end end
to_output_format(result_row)
click to toggle source
# File lib/dyph/two_way_differs/output_converter.rb, line 118 def to_output_format(result_row) { action: result_row[:action], old_lo: result_row[:old_index], old_hi: result_row[:old_index], new_lo: result_row[:new_index], new_hi: result_row[:new_index] } end