Class: Bash::Merge::SmartMerger

Inherits:
Ast::Merge::SmartMergerBase
  • Object
show all
Defined in:
lib/bash/merge/smart_merger.rb

Overview

Main entry point for intelligent Bash script merging. SmartMerger orchestrates the merge process using FileAnalysis, ConflictResolver, and MergeResult to merge two Bash scripts intelligently.

Examples:

Basic merge (destination customizations preserved)

merger = SmartMerger.new(template_bash, dest_bash)
result = merger.merge
File.write("output.sh", result)

Template updates win

merger = SmartMerger.new(
  template_bash,
  dest_bash,
  preference: :template,
  add_template_only_nodes: true
)
result = merger.merge

With custom signature generator

sig_gen = ->(node) {
  if node.is_a?(NodeWrapper) && node.function_definition? && node.function_name == "main"
    [:special_main]
  else
    node # Fall through to default
  end
}
merger = SmartMerger.new(template, dest, signature_generator: sig_gen)

With node_typing for per-node-type preferences

merger = SmartMerger.new(template, dest,
  node_typing: { "function_definition" => ->(n) { NodeTyping.with_merge_type(n, :func) } },
  preference: { default: :destination, func: :template })

Instance Method Summary collapse

Constructor Details

#initialize(template_content, dest_content, signature_generator: nil, preference: :destination, add_template_only_nodes: false, freeze_token: nil, match_refiner: nil, regions: nil, region_placeholder: nil, node_typing: nil, **options) ⇒ SmartMerger

Note:

To specify a custom parser path, use the TREE_SITTER_BASH_PATH environment variable. This is handled by tree_haver’s GrammarFinder.

Creates a new SmartMerger for intelligent Bash script merging.

Parameters:

  • template_content (String)

    Template Bash source code

  • dest_content (String)

    Destination Bash source code

  • signature_generator (Proc, nil) (defaults to: nil)

    Custom signature generator

  • preference (Symbol, Hash) (defaults to: :destination)

    :destination, :template, or per-type Hash

  • add_template_only_nodes (Boolean) (defaults to: false)

    Whether to add nodes only in template

  • freeze_token (String) (defaults to: nil)

    Token for freeze block markers

  • match_refiner (#call, nil) (defaults to: nil)

    Match refiner for fuzzy matching

  • regions (Array<Hash>, nil) (defaults to: nil)

    Region configurations for nested merging

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

    Custom placeholder for regions

  • node_typing (Hash{Symbol,String => #call}, nil) (defaults to: nil)

    Node typing configuration

  • options (Hash)

    Additional options for forward compatibility

Raises:



57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
# File 'lib/bash/merge/smart_merger.rb', line 57

def initialize(
  template_content,
  dest_content,
  signature_generator: nil,
  preference: :destination,
  add_template_only_nodes: false,
  freeze_token: nil,
  match_refiner: nil,
  regions: nil,
  region_placeholder: nil,
  node_typing: nil,
  **options
)
  super(
    template_content,
    dest_content,
    signature_generator: signature_generator,
    preference: preference,
    add_template_only_nodes: add_template_only_nodes,
    freeze_token: freeze_token,
    match_refiner: match_refiner,
    regions: regions,
    region_placeholder: region_placeholder,
    node_typing: node_typing,
    **options
  )
end

Instance Method Details

#errorsArray

Get any parse errors from template or destination.

Returns:

  • (Array)

    Array of errors



125
126
127
128
129
130
# File 'lib/bash/merge/smart_merger.rb', line 125

def errors
  errors = []
  errors.concat(@template_analysis.errors.map { |e| {source: :template, error: e} })
  errors.concat(@dest_analysis.errors.map { |e| {source: :destination, error: e} })
  errors
end

#mergeString

Perform the merge and return the result as a Bash string.

Returns:

  • (String)

    Merged Bash content



88
89
90
# File 'lib/bash/merge/smart_merger.rb', line 88

def merge
  merge_result.to_bash
end

#merge_with_debugHash

Perform the merge and return detailed results including debug info.

Returns:

  • (Hash)

    Hash containing :content, :statistics, :decisions



95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
# File 'lib/bash/merge/smart_merger.rb', line 95

def merge_with_debug
  content = merge

  {
    content: content,
    statistics: @result.statistics,
    decisions: @result.decision_summary,
    template_analysis: {
      valid: @template_analysis.valid?,
      nodes: @template_analysis.nodes.size,
      freeze_blocks: @template_analysis.freeze_blocks.size,
    },
    dest_analysis: {
      valid: @dest_analysis.valid?,
      nodes: @dest_analysis.nodes.size,
      freeze_blocks: @dest_analysis.freeze_blocks.size,
    },
  }
end

#valid?Boolean

Check if both files were parsed successfully.

Returns:

  • (Boolean)


118
119
120
# File 'lib/bash/merge/smart_merger.rb', line 118

def valid?
  @template_analysis.valid? && @dest_analysis.valid?
end