Project

General

Profile

« Previous | Next » 

Revision 13252

Added by Toshi MARUYAMA almost 11 years ago

use references

On Rails 4.0:

DEPRECATION WARNING: It looks like you are eager loading table(s) (one of: issues, projects, em)
that are referenced in a string SQL snippet. For example:

    Post.includes(:comments).where("comments.title = 'foo'")

Currently, Active Record recognizes the table in the string, and knows to JOIN the comments table to the query,
rather than loading comments in a separate query.
However, doing this without writing a full-blown SQL parser is inherently flawed.
Since we don't want to write an SQL parser, we are removing this functionality.
From now on, you must explicitly tell Active Record when you are referencing a table from a string:

    Post.includes(:comments).where("comments.title = 'foo'").references(:comments)

If you don't rely on implicit join references you can disable the feature entirely
by setting `config.active_record.disable_implicit_join_references = true`.

View differences:

sandbox/rails-4.1/app/controllers/boards_controller.rb
46 46
        @topics =  @board.topics.
47 47
          reorder("#{Message.table_name}.sticky DESC").
48 48
          joins("LEFT OUTER JOIN #{Message.table_name} last_replies_messages ON last_replies_messages.id = #{Message.table_name}.last_reply_id").
49
          references(:last_reply).
49 50
          limit(@topic_pages.per_page).
50 51
          offset(@topic_pages.offset).
51 52
          order(sort_clause).
sandbox/rails-4.1/app/controllers/issues_controller.rb
104 104
  end
105 105

  
106 106
  def show
107
    @journals = @issue.journals.includes(:user, :details).reorder("#{Journal.table_name}.id ASC").to_a
107
    @journals = @issue.journals.includes(:user, :details).
108
                    references(:user, :details).
109
                    reorder("#{Journal.table_name}.id ASC").to_a
108 110
    @journals.each_with_index {|j,i| j.indice = i+1}
109 111
    @journals.reject!(&:private_notes?) unless User.current.allowed_to?(:view_private_notes, @issue.project)
110 112
    Journal.preload_journals_details_custom_fields(@journals)
sandbox/rails-4.1/app/helpers/my_helper.rb
23 23
      where(:project_id => User.current.projects.map(&:id)).
24 24
      where("(start_date>=? and start_date<=?) or (due_date>=? and due_date<=?)", startdt, enddt, startdt, enddt).
25 25
      includes(:project, :tracker, :priority, :assigned_to).
26
      references(:project, :tracker, :priority, :assigned_to).
26 27
      to_a
27 28
  end
28 29

  
......
35 36
      where(:assigned_to_id => ([User.current.id] + User.current.group_ids)).
36 37
      limit(10).
37 38
      includes(:status, :project, :tracker, :priority).
39
      references(:status, :project, :tracker, :priority).
38 40
      order("#{IssuePriority.table_name}.position DESC, #{Issue.table_name}.updated_on DESC").
39 41
      to_a
40 42
  end
......
44 46
      where(:author_id => User.current.id).
45 47
      limit(10).
46 48
      includes(:status, :project, :tracker).
49
      references(:status, :project, :tracker).
47 50
      order("#{Issue.table_name}.updated_on DESC").
48 51
      to_a
49 52
  end
......
57 60
      where(:project_id => User.current.projects.map(&:id)).
58 61
      limit(10).
59 62
      includes(:project, :author).
63
      references(:project, :author).
60 64
      order("#{News.table_name}.created_on DESC").
61 65
      to_a
62 66
  end
......
65 69
    TimeEntry.
66 70
      where("#{TimeEntry.table_name}.user_id = ? AND #{TimeEntry.table_name}.spent_on BETWEEN ? AND ?", User.current.id, Date.today - 6, Date.today).
67 71
      joins(:activity, :project, {:issue => [:tracker, :status]}).
72
      references(:activity, :project, {:issue => [:tracker, :status]}).
68 73
      order("#{TimeEntry.table_name}.spent_on DESC, #{Project.table_name}.name ASC, #{Tracker.table_name}.position ASC, #{Issue.table_name}.id ASC").
69 74
      to_a
70 75
  end
sandbox/rails-4.1/app/models/board.rb
32 32
  attr_protected :id
33 33

  
34 34
  scope :visible, lambda {|*args|
35
    joins(:project).where(Project.allowed_to_condition(args.shift || User.current, :view_messages, *args))
35
    joins(:project).
36
    references(:project).
37
    where(Project.allowed_to_condition(args.shift || User.current, :view_messages, *args))
36 38
  }
37 39

  
38 40
  safe_attributes 'name', 'description', 'parent_id', 'move_to'
sandbox/rails-4.1/app/models/changeset.rb
49 49
  attr_protected :id
50 50

  
51 51
  scope :visible, lambda {|*args|
52
    joins(:repository => :project).where(Project.allowed_to_condition(args.shift || User.current, :view_changesets, *args))
52
    joins(:repository => :project).
53
    references(:repository => :project).
54
    where(Project.allowed_to_condition(args.shift || User.current, :view_changesets, *args))
53 55
  }
54 56

  
55 57
  after_create :scan_for_issues
sandbox/rails-4.1/app/models/document.rb
35 35
  after_create :send_notification
36 36

  
37 37
  scope :visible, lambda {|*args|
38
    joins(:project).where(Project.allowed_to_condition(args.shift || User.current, :view_documents, *args))
38
    joins(:project).
39
    references(:project).
40
    where(Project.allowed_to_condition(args.shift || User.current, :view_documents, *args))
39 41
  }
40 42

  
41 43
  safe_attributes 'category_id', 'title', 'description'
sandbox/rails-4.1/app/models/issue.rb
77 77
  attr_protected :id
78 78

  
79 79
  scope :visible, lambda {|*args|
80
    joins(:project).where(Issue.visible_condition(args.shift || User.current, *args))
80
    joins(:project).
81
    references(:project).
82
    where(Issue.visible_condition(args.shift || User.current, *args))
81 83
  }
82 84

  
83 85
  scope :open, lambda {|*args|
84 86
    is_closed = args.size > 0 ? !args.first : false
85
    joins(:status).where("#{IssueStatus.table_name}.is_closed = ?", is_closed)
87
    joins(:status).
88
    references(:status).
89
    where("#{IssueStatus.table_name}.is_closed = ?", is_closed)
86 90
  }
87 91

  
88 92
  scope :recently_updated, lambda { order("#{Issue.table_name}.updated_on DESC") }
89 93
  scope :on_active_project, lambda {
90
    joins(:project).where("#{Project.table_name}.status = ?", Project::STATUS_ACTIVE)
94
    joins(:project).
95
    references(:project).
96
    where("#{Project.table_name}.status = ?", Project::STATUS_ACTIVE)
91 97
  }
92 98
  scope :fixed_version, lambda {|versions|
93 99
    ids = [versions].flatten.compact.map {|v| v.is_a?(Version) ? v.id : v}
......
886 892
    if issues.any?
887 893
      issue_ids = issues.map(&:id)
888 894
      # Relations with issue_from in given issues and visible issue_to
889
      relations_from = IssueRelation.joins(:issue_to => :project).where(visible_condition(user)).where(:issue_from_id => issue_ids).to_a
895
      relations_from = IssueRelation.joins(:issue_to => :project).
896
                         references(:issue_to => :project).
897
                         where(visible_condition(user)).where(:issue_from_id => issue_ids).to_a
890 898
      # Relations with issue_to in given issues and visible issue_from
891
      relations_to = IssueRelation.joins(:issue_from => :project).where(visible_condition(user)).where(:issue_to_id => issue_ids).to_a
892

  
899
      relations_to = IssueRelation.joins(:issue_from => :project).
900
                         references(:issue_from => :project).
901
                         where(visible_condition(user)).
902
                         where(:issue_to_id => issue_ids).to_a
893 903
      issues.each do |issue|
894 904
        relations =
895 905
          relations_from.select {|relation| relation.issue_from_id == issue.id} +
......
1400 1410
    # Only need to update issues with a fixed_version from
1401 1411
    # a different project and that is not systemwide shared
1402 1412
    Issue.joins(:project, :fixed_version).
1413
      references(:version, :fixed_version).
1403 1414
      where("#{Issue.table_name}.fixed_version_id IS NOT NULL" +
1404 1415
        " AND #{Issue.table_name}.project_id <> #{Version.table_name}.project_id" +
1405 1416
        " AND #{Version.table_name}.sharing <> 'system'").
sandbox/rails-4.1/app/models/issue_query.rb
46 46
    user = args.shift || User.current
47 47
    base = Project.allowed_to_condition(user, :view_issues, *args)
48 48
    scope = joins("LEFT OUTER JOIN #{Project.table_name} ON #{table_name}.project_id = #{Project.table_name}.id").
49
      references(:project).
49 50
      where("#{table_name}.project_id IS NULL OR (#{base})")
50 51

  
51 52
    if user.admin?
......
360 361
      joins(:status, :project).
361 362
      where(statement).
362 363
      includes(([:status, :project] + (options[:include] || [])).uniq).
364
      references(([:status, :project] + (options[:include] || [])).uniq).
363 365
      where(options[:conditions]).
364 366
      order(order_option).
365 367
      joins(joins_for_order_statement(order_option.join(','))).
......
392 394
      where(project_statement).
393 395
      where(options[:conditions]).
394 396
      includes(:project).
397
      references(:project).
395 398
      to_a
396 399
  rescue ::ActiveRecord::StatementInvalid => e
397 400
    raise StatementInvalid.new(e.message)
sandbox/rails-4.1/app/models/journal.rb
45 45

  
46 46
  scope :visible, lambda {|*args|
47 47
    user = args.shift || User.current
48

  
49 48
    joins(:issue => :project).
49
    references(:project).
50 50
      where(Issue.visible_condition(user, *args)).
51 51
      where("(#{Journal.table_name}.private_notes = ? OR (#{Project.allowed_to_condition(user, :view_private_notes, *args)}))", false)
52 52
  }
sandbox/rails-4.1/app/models/message.rb
49 49
  after_create :send_notification
50 50

  
51 51
  scope :visible, lambda {|*args|
52
    joins(:board => :project).where(Project.allowed_to_condition(args.shift || User.current, :view_messages, *args))
52
    joins(:board => :project).
53
    references(:board => :project).
54
    where(Project.allowed_to_condition(args.shift || User.current, :view_messages, *args))
53 55
  }
54 56

  
55 57
  safe_attributes 'subject', 'content'
sandbox/rails-4.1/app/models/news.rb
38 38
  after_create :send_notification
39 39

  
40 40
  scope :visible, lambda {|*args|
41
    joins(:project).where(Project.allowed_to_condition(args.shift || User.current, :view_news, *args))
41
    joins(:project).
42
    references([:author, :project]).
43
    where(Project.allowed_to_condition(args.shift || User.current, :view_news, *args))
42 44
  }
43 45

  
44 46
  safe_attributes 'title', 'summary', 'description'
sandbox/rails-4.1/app/models/project.rb
28 28

  
29 29
  # Specific overridden Activities
30 30
  has_many :time_entry_activities
31
  has_many :members, lambda {joins(:principal, :roles).where("#{Principal.table_name}.type='User' AND #{Principal.table_name}.status=#{Principal::STATUS_ACTIVE}")}
31
  has_many :members,
32
           lambda { joins(:principal, :roles).
33
                    references(:principal, :roles).
34
                    where("#{Principal.table_name}.type='User' AND #{Principal.table_name}.status=#{Principal::STATUS_ACTIVE}") }
32 35
  has_many :memberships, :class_name => 'Member'
33
  has_many :member_principals, lambda {joins(:principal).where("#{Principal.table_name}.type='Group' OR (#{Principal.table_name}.type='User' AND #{Principal.table_name}.status=#{Principal::STATUS_ACTIVE})")},
36
  has_many :member_principals,
37
           lambda { joins(:principal).
38
                    references(:principal).
39
                    where("#{Principal.table_name}.type='Group' OR (#{Principal.table_name}.type='User' AND #{Principal.table_name}.status=#{Principal::STATUS_ACTIVE})")},
34 40
    :class_name => 'Member'
35 41
  has_many :enabled_modules, :dependent => :delete_all
36 42
  has_and_belongs_to_many :trackers, lambda {order("#{Tracker.table_name}.position")}
......
428 434
    @rolled_up_trackers ||=
429 435
      Tracker.
430 436
        joins(:projects).
437
        references(:project).
431 438
        joins("JOIN #{EnabledModule.table_name} ON #{EnabledModule.table_name}.project_id = #{Project.table_name}.id AND #{EnabledModule.table_name}.name = 'issue_tracking'").
432 439
        select("DISTINCT #{Tracker.table_name}.*").
433 440
        where("#{Project.table_name}.lft >= ? AND #{Project.table_name}.rgt <= ? AND #{Project.table_name}.status <> #{STATUS_ARCHIVED}", lft, rgt).
......
451 458
    @rolled_up_versions ||=
452 459
      Version.
453 460
        joins(:project).
461
        references(:project).
454 462
        where("#{Project.table_name}.lft >= ? AND #{Project.table_name}.rgt <= ? AND #{Project.table_name}.status <> ?", lft, rgt, STATUS_ARCHIVED)
455 463
  end
456 464

  
......
459 467
    if new_record?
460 468
      Version.
461 469
        joins(:project).
470
        references(:project).
462 471
        preload(:project).
463 472
        where("#{Project.table_name}.status <> ? AND #{Version.table_name}.sharing = 'system'", STATUS_ARCHIVED)
464 473
    else
......
466 475
        r = root? ? self : root
467 476
        Version.
468 477
          joins(:project).
478
          references(:project).
469 479
          preload(:project).
470 480
          where("#{Project.table_name}.id = #{id}" +
471 481
                  " OR (#{Project.table_name}.status <> #{Project::STATUS_ARCHIVED} AND (" +
sandbox/rails-4.1/app/models/time_entry.rb
45 45
  validate :validate_time_entry
46 46

  
47 47
  scope :visible, lambda {|*args|
48
    joins(:project).where(Project.allowed_to_condition(args.shift || User.current, :view_time_entries, *args))
48
    joins(:project).
49
    references(:project).
50
    where(Project.allowed_to_condition(args.shift || User.current, :view_time_entries, *args))
49 51
  }
50 52
  scope :on_issue, lambda {|issue|
51
    joins(:issue).where("#{Issue.table_name}.root_id = #{issue.root_id} AND #{Issue.table_name}.lft >= #{issue.lft} AND #{Issue.table_name}.rgt <= #{issue.rgt}")
53
    joins(:issue).
54
    references(:issue).
55
    where("#{Issue.table_name}.root_id = #{issue.root_id} AND #{Issue.table_name}.lft >= #{issue.lft} AND #{Issue.table_name}.rgt <= #{issue.rgt}")
52 56
  }
53 57
  scope :on_project, lambda {|project, include_subprojects|
54
    joins(:project).where(project.project_condition(include_subprojects))
58
    joins(:project).
59
    references(:project).
60
    where(project.project_condition(include_subprojects))
55 61
  }
56 62
  scope :spent_between, lambda {|from, to|
57 63
    if from && to
sandbox/rails-4.1/app/models/version.rb
38 38
  scope :named, lambda {|arg| where("LOWER(#{table_name}.name) = LOWER(?)", arg.to_s.strip)}
39 39
  scope :open, lambda { where(:status => 'open') }
40 40
  scope :visible, lambda {|*args|
41
    joins(:project).where(Project.allowed_to_condition(args.first || User.current, :view_issues))
41
    joins(:project).
42
    references(:project).
43
    where(Project.allowed_to_condition(args.first || User.current, :view_issues))
42 44
  }
43 45

  
44 46
  safe_attributes 'name',
sandbox/rails-4.1/test/unit/query_test.rb
103 103
  def find_issues_with_query(query)
104 104
    Issue.joins(:status, :tracker, :project, :priority).where(
105 105
         query.statement
106
       ).to_a
106
       ).references([:assigned_to, :status, :tracker, :project, :priority]).to_a
107 107
  end
108 108

  
109 109
  def assert_find_issues_with_query_is_successful(query)

Also available in: Unified diff