class ActiveRecord::Associations::JoinDependency::JoinAssociation

:nodoc:
:nodoc:

def append_constraints(join, constraints)

def append_constraints(join, constraints)
  if join.is_a?(Arel::Nodes::StringJoin)
    join_string = Arel::Nodes::And.new(constraints.unshift join.left)
    join.left = Arel.sql(base_klass.connection.visitor.compile(join_string))
  else
    right = join.right
    right.expr = Arel::Nodes::And.new(constraints.unshift right.expr)
  end
end

def initialize(reflection, children)

def initialize(reflection, children)
  super(reflection.klass, children)
  @reflection = reflection
end

def join_constraints(foreign_table, foreign_klass, join_type, alias_tracker)

def join_constraints(foreign_table, foreign_klass, join_type, alias_tracker)
  joins = []
  chain = []
  reflection.chain.each do |reflection|
    table, terminated = yield reflection
    @table ||= table
    if terminated
      foreign_table, foreign_klass = table, reflection.klass
      break
    end
    chain << [reflection, table]
  end
  # The chain starts with the target table, but we want to end with it here (makes
  # more sense in this context), so we reverse
  chain.reverse_each do |reflection, table|
    klass = reflection.klass
    scope = reflection.join_scope(table, foreign_table, foreign_klass)
    unless scope.references_values.empty?
      associations = scope.eager_load_values | scope.includes_values
      unless associations.empty?
        scope.joins! scope.construct_join_dependency(associations, Arel::Nodes::OuterJoin)
      end
    end
    arel = scope.arel(alias_tracker.aliases)
    nodes = arel.constraints.first
    if nodes.is_a?(Arel::Nodes::And)
      others = nodes.children.extract! do |node|
        !Arel.fetch_attribute(node) { |attr| attr.relation.name == table.name }
      end
    end
    joins << join_type.new(table, Arel::Nodes::On.new(nodes))
    if others && !others.empty?
      joins.concat arel.join_sources
      append_constraints(joins.last, others)
    end
    # The current table in this iteration becomes the foreign table in the next
    foreign_table, foreign_klass = table, klass
  end
  joins
end

def match?(other)

def match?(other)
  return true if self == other
  super && reflection == other.reflection
end

def readonly?

def readonly?
  return @readonly if defined?(@readonly)
  @readonly = reflection.scope && reflection.scope_for(base_klass.unscoped).readonly_value
end

def strict_loading?

def strict_loading?
  return @strict_loading if defined?(@strict_loading)
  @strict_loading = reflection.scope && reflection.scope_for(base_klass.unscoped).strict_loading_value
end