##// END OF EJS Templates
Adds ability to filter watched issues (#846)....
Jean-Philippe Lang -
r2395:e1b828de95ec
parent child
Show More
@@ -165,6 +165,10 class Query < ActiveRecord::Base
165 end
165 end
166 @available_filters["assigned_to_id"] = { :type => :list_optional, :order => 4, :values => user_values } unless user_values.empty?
166 @available_filters["assigned_to_id"] = { :type => :list_optional, :order => 4, :values => user_values } unless user_values.empty?
167 @available_filters["author_id"] = { :type => :list, :order => 5, :values => user_values } unless user_values.empty?
167 @available_filters["author_id"] = { :type => :list, :order => 5, :values => user_values } unless user_values.empty?
168
169 if User.current.logged?
170 @available_filters["watcher_id"] = { :type => :list, :order => 15, :values => [["<< #{l(:label_me)} >>", "me"]] }
171 end
168
172
169 if project
173 if project
170 # project specific filters
174 # project specific filters
@@ -288,31 +292,34 class Query < ActiveRecord::Base
288 next if field == "subproject_id"
292 next if field == "subproject_id"
289 v = values_for(field).clone
293 v = values_for(field).clone
290 next unless v and !v.empty?
294 next unless v and !v.empty?
291
295 operator = operator_for(field)
296
297 # "me" value subsitution
298 if %w(assigned_to_id author_id watcher_id).include?(field)
299 v.push(User.current.logged? ? User.current.id.to_s : "0") if v.delete("me")
300 end
301
292 sql = ''
302 sql = ''
293 is_custom_filter = false
294 if field =~ /^cf_(\d+)$/
303 if field =~ /^cf_(\d+)$/
295 # custom field
304 # custom field
296 db_table = CustomValue.table_name
305 db_table = CustomValue.table_name
297 db_field = 'value'
306 db_field = 'value'
298 is_custom_filter = true
307 is_custom_filter = true
299 sql << "#{Issue.table_name}.id IN (SELECT #{Issue.table_name}.id FROM #{Issue.table_name} LEFT OUTER JOIN #{db_table} ON #{db_table}.customized_type='Issue' AND #{db_table}.customized_id=#{Issue.table_name}.id AND #{db_table}.custom_field_id=#{$1} WHERE "
308 sql << "#{Issue.table_name}.id IN (SELECT #{Issue.table_name}.id FROM #{Issue.table_name} LEFT OUTER JOIN #{db_table} ON #{db_table}.customized_type='Issue' AND #{db_table}.customized_id=#{Issue.table_name}.id AND #{db_table}.custom_field_id=#{$1} WHERE "
309 sql << sql_for_field(field, operator, v, db_table, db_field, true) + ')'
310 elsif field == 'watcher_id'
311 db_table = Watcher.table_name
312 db_field = 'user_id'
313 sql << "#{Issue.table_name}.id #{ operator == '=' ? 'IN' : 'NOT IN' } (SELECT #{db_table}.watchable_id FROM #{db_table} WHERE #{db_table}.watchable_type='Issue' AND "
314 sql << sql_for_field(field, '=', v, db_table, db_field) + ')'
300 else
315 else
301 # regular field
316 # regular field
302 db_table = Issue.table_name
317 db_table = Issue.table_name
303 db_field = field
318 db_field = field
304 sql << '('
319 sql << '(' + sql_for_field(field, operator, v, db_table, db_field) + ')'
305 end
320 end
306
307 # "me" value subsitution
308 if %w(assigned_to_id author_id).include?(field)
309 v.push(User.current.logged? ? User.current.id.to_s : "0") if v.delete("me")
310 end
311
312 sql = sql + sql_for_field(field, v, db_table, db_field, is_custom_filter)
313
314 sql << ')'
315 filters_clauses << sql
321 filters_clauses << sql
322
316 end if filters and valid?
323 end if filters and valid?
317
324
318 (filters_clauses << project_statement).join(' AND ')
325 (filters_clauses << project_statement).join(' AND ')
@@ -320,10 +327,10 class Query < ActiveRecord::Base
320
327
321 private
328 private
322
329
323 # Helper method to generate the WHERE sql for a +field+ with a +value+
330 # Helper method to generate the WHERE sql for a +field+, +operator+ and a +value+
324 def sql_for_field(field, value, db_table, db_field, is_custom_filter)
331 def sql_for_field(field, operator, value, db_table, db_field, is_custom_filter=false)
325 sql = ''
332 sql = ''
326 case operator_for field
333 case operator
327 when "="
334 when "="
328 sql = "#{db_table}.#{db_field} IN (" + value.collect{|val| "'#{connection.quote_string(val)}'"}.join(",") + ")"
335 sql = "#{db_table}.#{db_field} IN (" + value.collect{|val| "'#{connection.quote_string(val)}'"}.join(",") + ")"
329 when "!"
336 when "!"
@@ -706,3 +706,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
706 field_identity_url: OpenID URL
706 field_identity_url: OpenID URL
707 setting_openid: Allow OpenID login and registration
707 setting_openid: Allow OpenID login and registration
708 label_login_with_open_id_option: or login with OpenID
708 label_login_with_open_id_option: or login with OpenID
709 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -711,3 +711,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
711 field_identity_url: OpenID URL
711 field_identity_url: OpenID URL
712 setting_openid: Allow OpenID login and registration
712 setting_openid: Allow OpenID login and registration
713 label_login_with_open_id_option: or login with OpenID
713 label_login_with_open_id_option: or login with OpenID
714 field_watcher: Watcher
@@ -708,3 +708,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -709,3 +709,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
709 field_identity_url: OpenID URL
709 field_identity_url: OpenID URL
710 setting_openid: Allow OpenID login and registration
710 setting_openid: Allow OpenID login and registration
711 label_login_with_open_id_option: or login with OpenID
711 label_login_with_open_id_option: or login with OpenID
712 field_watcher: Watcher
@@ -188,6 +188,7 field_default_value: Default value
188 field_comments_sorting: Display comments
188 field_comments_sorting: Display comments
189 field_parent_title: Parent page
189 field_parent_title: Parent page
190 field_editable: Editable
190 field_editable: Editable
191 field_watcher: Watcher
191
192
192 setting_app_title: Application title
193 setting_app_title: Application title
193 setting_app_subtitle: Application subtitle
194 setting_app_subtitle: Application subtitle
@@ -691,3 +691,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
691 field_identity_url: OpenID URL
691 field_identity_url: OpenID URL
692 setting_openid: Allow OpenID login and registration
692 setting_openid: Allow OpenID login and registration
693 label_login_with_open_id_option: or login with OpenID
693 label_login_with_open_id_option: or login with OpenID
694 field_watcher: Watcher
@@ -706,3 +706,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
706 field_identity_url: OpenID URL
706 field_identity_url: OpenID URL
707 setting_openid: Allow OpenID login and registration
707 setting_openid: Allow OpenID login and registration
708 label_login_with_open_id_option: or login with OpenID
708 label_login_with_open_id_option: or login with OpenID
709 field_watcher: Watcher
@@ -188,6 +188,7 field_comments_sorting: Afficher les commentaires
188 field_parent_title: Page parent
188 field_parent_title: Page parent
189 field_editable: Modifiable
189 field_editable: Modifiable
190 field_identity_url: URL OpenID
190 field_identity_url: URL OpenID
191 field_watcher: Observateur
191
192
192 setting_app_title: Titre de l'application
193 setting_app_title: Titre de l'application
193 setting_app_subtitle: Sous-titre de l'application
194 setting_app_subtitle: Sous-titre de l'application
@@ -691,3 +691,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
691 field_identity_url: OpenID URL
691 field_identity_url: OpenID URL
692 setting_openid: Allow OpenID login and registration
692 setting_openid: Allow OpenID login and registration
693 label_login_with_open_id_option: or login with OpenID
693 label_login_with_open_id_option: or login with OpenID
694 field_watcher: Watcher
@@ -706,3 +706,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
706 field_identity_url: OpenID URL
706 field_identity_url: OpenID URL
707 setting_openid: Allow OpenID login and registration
707 setting_openid: Allow OpenID login and registration
708 label_login_with_open_id_option: or login with OpenID
708 label_login_with_open_id_option: or login with OpenID
709 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: Maximum hΓ‘ny revΓ­ziΓ³ jelenjen meg a fΓ‘
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -706,3 +706,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
706 field_identity_url: OpenID URL
706 field_identity_url: OpenID URL
707 setting_openid: Allow OpenID login and registration
707 setting_openid: Allow OpenID login and registration
708 label_login_with_open_id_option: or login with OpenID
708 label_login_with_open_id_option: or login with OpenID
709 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -706,3 +706,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
706 field_identity_url: OpenID URL
706 field_identity_url: OpenID URL
707 setting_openid: Allow OpenID login and registration
707 setting_openid: Allow OpenID login and registration
708 label_login_with_open_id_option: or login with OpenID
708 label_login_with_open_id_option: or login with OpenID
709 field_watcher: Watcher
@@ -708,3 +708,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -708,3 +708,4 text_custom_field_possible_values_info: 'One line for each value'
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -691,3 +691,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
691 field_identity_url: OpenID URL
691 field_identity_url: OpenID URL
692 setting_openid: Allow OpenID login and registration
692 setting_openid: Allow OpenID login and registration
693 label_login_with_open_id_option: or login with OpenID
693 label_login_with_open_id_option: or login with OpenID
694 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -725,3 +725,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
725 field_identity_url: OpenID URL
725 field_identity_url: OpenID URL
726 setting_openid: Allow OpenID login and registration
726 setting_openid: Allow OpenID login and registration
727 label_login_with_open_id_option: or login with OpenID
727 label_login_with_open_id_option: or login with OpenID
728 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: NΓΊmero mΓ‘ximo de revisΓ΅es exibidas no a
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -708,3 +708,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -706,3 +706,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
706 field_identity_url: OpenID URL
706 field_identity_url: OpenID URL
707 setting_openid: Allow OpenID login and registration
707 setting_openid: Allow OpenID login and registration
708 label_login_with_open_id_option: or login with OpenID
708 label_login_with_open_id_option: or login with OpenID
709 field_watcher: Watcher
@@ -741,3 +741,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
741 field_identity_url: OpenID URL
741 field_identity_url: OpenID URL
742 setting_openid: Allow OpenID login and registration
742 setting_openid: Allow OpenID login and registration
743 label_login_with_open_id_option: or login with OpenID
743 label_login_with_open_id_option: or login with OpenID
744 field_watcher: Watcher
@@ -711,3 +711,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
711 field_identity_url: OpenID URL
711 field_identity_url: OpenID URL
712 setting_openid: Allow OpenID login and registration
712 setting_openid: Allow OpenID login and registration
713 label_login_with_open_id_option: or login with OpenID
713 label_login_with_open_id_option: or login with OpenID
714 field_watcher: Watcher
@@ -708,3 +708,4 text_custom_field_possible_values_info: 'One line for each value'
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -708,3 +708,4 enumeration_activities: Aktiviteter (tidsuppfΓΆljning)
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -709,3 +709,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
709 field_identity_url: OpenID URL
709 field_identity_url: OpenID URL
710 setting_openid: Allow OpenID login and registration
710 setting_openid: Allow OpenID login and registration
711 label_login_with_open_id_option: or login with OpenID
711 label_login_with_open_id_option: or login with OpenID
712 field_watcher: Watcher
@@ -707,3 +707,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
707 field_identity_url: OpenID URL
707 field_identity_url: OpenID URL
708 setting_openid: Allow OpenID login and registration
708 setting_openid: Allow OpenID login and registration
709 label_login_with_open_id_option: or login with OpenID
709 label_login_with_open_id_option: or login with OpenID
710 field_watcher: Watcher
@@ -708,3 +708,4 text_custom_field_possible_values_info: 'One line for each value'
708 field_identity_url: OpenID URL
708 field_identity_url: OpenID URL
709 setting_openid: Allow OpenID login and registration
709 setting_openid: Allow OpenID login and registration
710 label_login_with_open_id_option: or login with OpenID
710 label_login_with_open_id_option: or login with OpenID
711 field_watcher: Watcher
@@ -709,3 +709,4 setting_repository_log_display_limit: Maximum number of revisions displayed on f
709 field_identity_url: OpenID URL
709 field_identity_url: OpenID URL
710 setting_openid: Allow OpenID login and registration
710 setting_openid: Allow OpenID login and registration
711 label_login_with_open_id_option: or login with OpenID
711 label_login_with_open_id_option: or login with OpenID
712 field_watcher: Watcher
@@ -709,3 +709,4 enumeration_activities: ζ΄»ε‹• (ζ™‚ι–“θΏ½θΉ€)
709 field_identity_url: OpenID URL
709 field_identity_url: OpenID URL
710 setting_openid: Allow OpenID login and registration
710 setting_openid: Allow OpenID login and registration
711 label_login_with_open_id_option: or login with OpenID
711 label_login_with_open_id_option: or login with OpenID
712 field_watcher: Watcher
@@ -709,3 +709,4 enumeration_activities: ζ΄»εŠ¨οΌˆζ—Άι—΄θ·ŸθΈͺοΌ‰
709 field_identity_url: OpenID URL
709 field_identity_url: OpenID URL
710 setting_openid: Allow OpenID login and registration
710 setting_openid: Allow OpenID login and registration
711 label_login_with_open_id_option: or login with OpenID
711 label_login_with_open_id_option: or login with OpenID
712 field_watcher: Watcher
@@ -7,4 +7,8 watchers_002:
7 watchable_type: Message
7 watchable_type: Message
8 watchable_id: 1
8 watchable_id: 1
9 user_id: 1
9 user_id: 1
10 watchers_003:
11 watchable_type: Issue
12 watchable_id: 2
13 user_id: 1
10 No newline at end of file
14
@@ -18,7 +18,7
18 require File.dirname(__FILE__) + '/../test_helper'
18 require File.dirname(__FILE__) + '/../test_helper'
19
19
20 class QueryTest < Test::Unit::TestCase
20 class QueryTest < Test::Unit::TestCase
21 fixtures :projects, :enabled_modules, :users, :members, :roles, :trackers, :issue_statuses, :issue_categories, :enumerations, :issues, :custom_fields, :custom_values, :versions, :queries
21 fixtures :projects, :enabled_modules, :users, :members, :roles, :trackers, :issue_statuses, :issue_categories, :enumerations, :issues, :watchers, :custom_fields, :custom_values, :versions, :queries
22
22
23 def test_custom_fields_for_all_projects_should_be_available_in_global_queries
23 def test_custom_fields_for_all_projects_should_be_available_in_global_queries
24 query = Query.new(:project => nil, :name => '_')
24 query = Query.new(:project => nil, :name => '_')
@@ -162,6 +162,26 class QueryTest < Test::Unit::TestCase
162 find_issues_with_query(query)
162 find_issues_with_query(query)
163 end
163 end
164
164
165 def test_filter_watched_issues
166 User.current = User.find(1)
167 query = Query.new(:name => '_', :filters => { 'watcher_id' => {:operator => '=', :values => ['me']}})
168 result = find_issues_with_query(query)
169 assert_not_nil result
170 assert !result.empty?
171 assert_equal Issue.visible.watched_by(User.current).sort_by(&:id), result.sort_by(&:id)
172 User.current = nil
173 end
174
175 def test_filter_unwatched_issues
176 User.current = User.find(1)
177 query = Query.new(:name => '_', :filters => { 'watcher_id' => {:operator => '!', :values => ['me']}})
178 result = find_issues_with_query(query)
179 assert_not_nil result
180 assert !result.empty?
181 assert_equal((Issue.visible - Issue.watched_by(User.current)).sort_by(&:id).size, result.sort_by(&:id).size)
182 User.current = nil
183 end
184
165 def test_default_columns
185 def test_default_columns
166 q = Query.new
186 q = Query.new
167 assert !q.columns.empty?
187 assert !q.columns.empty?
General Comments 0
You need to be logged in to leave comments. Login now