comparison test/integration/api_test/issues_test.rb @ 1526:404aa68d4227

Merge from live branch
author Chris Cannam
date Thu, 11 Sep 2014 12:46:20 +0100
parents dffacf8a6908
children
comparison
equal deleted inserted replaced
1493:a5f2bdf3b486 1526:404aa68d4227
1 # Redmine - project management software 1 # Redmine - project management software
2 # Copyright (C) 2006-2012 Jean-Philippe Lang 2 # Copyright (C) 2006-2014 Jean-Philippe Lang
3 # 3 #
4 # This program is free software; you can redistribute it and/or 4 # This program is free software; you can redistribute it and/or
5 # modify it under the terms of the GNU General Public License 5 # modify it under the terms of the GNU General Public License
6 # as published by the Free Software Foundation; either version 2 6 # as published by the Free Software Foundation; either version 2
7 # of the License, or (at your option) any later version. 7 # of the License, or (at your option) any later version.
15 # along with this program; if not, write to the Free Software 15 # along with this program; if not, write to the Free Software
16 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 16 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17 17
18 require File.expand_path('../../../test_helper', __FILE__) 18 require File.expand_path('../../../test_helper', __FILE__)
19 19
20 class ApiTest::IssuesTest < ActionController::IntegrationTest 20 class Redmine::ApiTest::IssuesTest < Redmine::ApiTest::Base
21 fixtures :projects, 21 fixtures :projects,
22 :users, 22 :users,
23 :roles, 23 :roles,
24 :members, 24 :members,
25 :member_roles, 25 :member_roles,
136 context "with custom field filter" do 136 context "with custom field filter" do
137 should "show only issues with the custom field value" do 137 should "show only issues with the custom field value" do
138 get '/issues.xml', 138 get '/issues.xml',
139 {:set_filter => 1, :f => ['cf_1'], :op => {:cf_1 => '='}, 139 {:set_filter => 1, :f => ['cf_1'], :op => {:cf_1 => '='},
140 :v => {:cf_1 => ['MySQL']}} 140 :v => {:cf_1 => ['MySQL']}}
141 expected_ids = Issue.visible.all( 141 expected_ids = Issue.visible.
142 :include => :custom_values, 142 joins(:custom_values).
143 :conditions => {:custom_values => {:custom_field_id => 1, :value => 'MySQL'}}).map(&:id) 143 where(:custom_values => {:custom_field_id => 1, :value => 'MySQL'}).map(&:id)
144 assert_select 'issues > issue > id', :count => expected_ids.count do |ids| 144 assert_select 'issues > issue > id', :count => expected_ids.count do |ids|
145 ids.each { |id| assert expected_ids.delete(id.children.first.content.to_i) } 145 ids.each { |id| assert expected_ids.delete(id.children.first.content.to_i) }
146 end 146 end
147 end 147 end
148 end 148 end
149 149
150 context "with custom field filter (shorthand method)" do 150 context "with custom field filter (shorthand method)" do
151 should "show only issues with the custom field value" do 151 should "show only issues with the custom field value" do
152 get '/issues.xml', { :cf_1 => 'MySQL' } 152 get '/issues.xml', { :cf_1 => 'MySQL' }
153 153
154 expected_ids = Issue.visible.all( 154 expected_ids = Issue.visible.
155 :include => :custom_values, 155 joins(:custom_values).
156 :conditions => {:custom_values => {:custom_field_id => 1, :value => 'MySQL'}}).map(&:id) 156 where(:custom_values => {:custom_field_id => 1, :value => 'MySQL'}).map(&:id)
157 157
158 assert_select 'issues > issue > id', :count => expected_ids.count do |ids| 158 assert_select 'issues > issue > id', :count => expected_ids.count do |ids|
159 ids.each { |id| assert expected_ids.delete(id.children.first.content.to_i) } 159 ids.each { |id| assert expected_ids.delete(id.children.first.content.to_i) }
160 end 160 end
161 end 161 end
162 end 162 end
163 end
164
165 def test_index_should_allow_timestamp_filtering
166 Issue.delete_all
167 Issue.generate!(:subject => '1').update_column(:updated_on, Time.parse("2014-01-02T10:25:00Z"))
168 Issue.generate!(:subject => '2').update_column(:updated_on, Time.parse("2014-01-02T12:13:00Z"))
169
170 get '/issues.xml',
171 {:set_filter => 1, :f => ['updated_on'], :op => {:updated_on => '<='},
172 :v => {:updated_on => ['2014-01-02T12:00:00Z']}}
173 assert_select 'issues>issue', :count => 1
174 assert_select 'issues>issue>subject', :text => '1'
175
176 get '/issues.xml',
177 {:set_filter => 1, :f => ['updated_on'], :op => {:updated_on => '>='},
178 :v => {:updated_on => ['2014-01-02T12:00:00Z']}}
179 assert_select 'issues>issue', :count => 1
180 assert_select 'issues>issue>subject', :text => '2'
181
182 get '/issues.xml',
183 {:set_filter => 1, :f => ['updated_on'], :op => {:updated_on => '>='},
184 :v => {:updated_on => ['2014-01-02T08:00:00Z']}}
185 assert_select 'issues>issue', :count => 2
163 end 186 end
164 187
165 context "/index.json" do 188 context "/index.json" do
166 should_allow_api_authentication(:get, "/projects/private-child/issues.json") 189 should_allow_api_authentication(:get, "/projects/private-child/issues.json")
167 end 190 end
168 191
169 context "/index.xml with filter" do 192 context "/index.xml with filter" do
170 should "show only issues with the status_id" do 193 should "show only issues with the status_id" do
171 get '/issues.xml?status_id=5' 194 get '/issues.xml?status_id=5'
172 195
173 expected_ids = Issue.visible.all(:conditions => {:status_id => 5}).map(&:id) 196 expected_ids = Issue.visible.where(:status_id => 5).map(&:id)
174 197
175 assert_select 'issues > issue > id', :count => expected_ids.count do |ids| 198 assert_select 'issues > issue > id', :count => expected_ids.count do |ids|
176 ids.each { |id| assert expected_ids.delete(id.children.first.content.to_i) } 199 ids.each { |id| assert expected_ids.delete(id.children.first.content.to_i) }
177 end 200 end
178 end 201 end
451 end 474 end
452 end 475 end
453 end 476 end
454 end 477 end
455 478
479 test "GET /issues/:id.xml?include=watchers should include watchers" do
480 Watcher.create!(:user_id => 3, :watchable => Issue.find(1))
481
482 get '/issues/1.xml?include=watchers', {}, credentials('jsmith')
483
484 assert_response :ok
485 assert_equal 'application/xml', response.content_type
486 assert_select 'issue' do
487 assert_select 'watchers', Issue.find(1).watchers.count
488 assert_select 'watchers' do
489 assert_select 'user[id=3]'
490 end
491 end
492 end
493
456 context "POST /issues.xml" do 494 context "POST /issues.xml" do
457 should_allow_api_authentication( 495 should_allow_api_authentication(
458 :post, 496 :post,
459 '/issues.xml', 497 '/issues.xml',
460 {:issue => {:project_id => 1, :subject => 'API test', :tracker_id => 2, :status_id => 3}}, 498 {:issue => {:project_id => 1, :subject => 'API test', :tracker_id => 2, :status_id => 3}},
464 assert_difference('Issue.count') do 502 assert_difference('Issue.count') do
465 post '/issues.xml', 503 post '/issues.xml',
466 {:issue => {:project_id => 1, :subject => 'API test', 504 {:issue => {:project_id => 1, :subject => 'API test',
467 :tracker_id => 2, :status_id => 3}}, credentials('jsmith') 505 :tracker_id => 2, :status_id => 3}}, credentials('jsmith')
468 end 506 end
469 issue = Issue.first(:order => 'id DESC') 507 issue = Issue.order('id DESC').first
470 assert_equal 1, issue.project_id 508 assert_equal 1, issue.project_id
471 assert_equal 2, issue.tracker_id 509 assert_equal 2, issue.tracker_id
472 assert_equal 3, issue.status_id 510 assert_equal 3, issue.status_id
473 assert_equal 'API test', issue.subject 511 assert_equal 'API test', issue.subject
474 512
475 assert_response :created 513 assert_response :created
476 assert_equal 'application/xml', @response.content_type 514 assert_equal 'application/xml', @response.content_type
477 assert_tag 'issue', :child => {:tag => 'id', :content => issue.id.to_s} 515 assert_tag 'issue', :child => {:tag => 'id', :content => issue.id.to_s}
478 end 516 end
517 end
518
519 test "POST /issues.xml with watcher_user_ids should create issue with watchers" do
520 assert_difference('Issue.count') do
521 post '/issues.xml',
522 {:issue => {:project_id => 1, :subject => 'Watchers',
523 :tracker_id => 2, :status_id => 3, :watcher_user_ids => [3, 1]}}, credentials('jsmith')
524 assert_response :created
525 end
526 issue = Issue.order('id desc').first
527 assert_equal 2, issue.watchers.size
528 assert_equal [1, 3], issue.watcher_user_ids.sort
479 end 529 end
480 530
481 context "POST /issues.xml with failure" do 531 context "POST /issues.xml with failure" do
482 should "have an errors tag" do 532 should "have an errors tag" do
483 assert_no_difference('Issue.count') do 533 assert_no_difference('Issue.count') do
501 {:issue => {:project_id => 1, :subject => 'API test', 551 {:issue => {:project_id => 1, :subject => 'API test',
502 :tracker_id => 2, :status_id => 3}}, 552 :tracker_id => 2, :status_id => 3}},
503 credentials('jsmith') 553 credentials('jsmith')
504 end 554 end
505 555
506 issue = Issue.first(:order => 'id DESC') 556 issue = Issue.order('id DESC').first
507 assert_equal 1, issue.project_id 557 assert_equal 1, issue.project_id
508 assert_equal 2, issue.tracker_id 558 assert_equal 2, issue.tracker_id
509 assert_equal 3, issue.status_id 559 assert_equal 3, issue.status_id
510 assert_equal 'API test', issue.subject 560 assert_equal 'API test', issue.subject
511 end 561 end
718 768
719 assert_nil Issue.find_by_id(6) 769 assert_nil Issue.find_by_id(6)
720 end 770 end
721 end 771 end
722 772
773 test "POST /issues/:id/watchers.xml should add watcher" do
774 assert_difference 'Watcher.count' do
775 post '/issues/1/watchers.xml', {:user_id => 3}, credentials('jsmith')
776
777 assert_response :ok
778 assert_equal '', response.body
779 end
780 watcher = Watcher.order('id desc').first
781 assert_equal Issue.find(1), watcher.watchable
782 assert_equal User.find(3), watcher.user
783 end
784
785 test "DELETE /issues/:id/watchers/:user_id.xml should remove watcher" do
786 Watcher.create!(:user_id => 3, :watchable => Issue.find(1))
787
788 assert_difference 'Watcher.count', -1 do
789 delete '/issues/1/watchers/3.xml', {}, credentials('jsmith')
790
791 assert_response :ok
792 assert_equal '', response.body
793 end
794 assert_equal false, Issue.find(1).watched_by?(User.find(3))
795 end
796
723 def test_create_issue_with_uploaded_file 797 def test_create_issue_with_uploaded_file
724 set_tmp_attachments_directory 798 set_tmp_attachments_directory
725 # upload the file 799 # upload the file
726 assert_difference 'Attachment.count' do 800 assert_difference 'Attachment.count' do
727 post '/uploads.xml', 'test_create_with_upload', 801 post '/uploads.xml', 'test_create_with_upload',
728 {"CONTENT_TYPE" => 'application/octet-stream'}.merge(credentials('jsmith')) 802 {"CONTENT_TYPE" => 'application/octet-stream'}.merge(credentials('jsmith'))
729 assert_response :created 803 assert_response :created
730 end 804 end
731 xml = Hash.from_xml(response.body) 805 xml = Hash.from_xml(response.body)
732 token = xml['upload']['token'] 806 token = xml['upload']['token']
733 attachment = Attachment.first(:order => 'id DESC') 807 attachment = Attachment.order('id DESC').first
734 808
735 # create the issue with the upload's token 809 # create the issue with the upload's token
736 assert_difference 'Issue.count' do 810 assert_difference 'Issue.count' do
737 post '/issues.xml', 811 post '/issues.xml',
738 {:issue => {:project_id => 1, :subject => 'Uploaded file', 812 {:issue => {:project_id => 1, :subject => 'Uploaded file',
739 :uploads => [{:token => token, :filename => 'test.txt', 813 :uploads => [{:token => token, :filename => 'test.txt',
740 :content_type => 'text/plain'}]}}, 814 :content_type => 'text/plain'}]}},
741 credentials('jsmith') 815 credentials('jsmith')
742 assert_response :created 816 assert_response :created
743 end 817 end
744 issue = Issue.first(:order => 'id DESC') 818 issue = Issue.order('id DESC').first
745 assert_equal 1, issue.attachments.count 819 assert_equal 1, issue.attachments.count
746 assert_equal attachment, issue.attachments.first 820 assert_equal attachment, issue.attachments.first
747 821
748 attachment.reload 822 attachment.reload
749 assert_equal 'test.txt', attachment.filename 823 assert_equal 'test.txt', attachment.filename
774 {"CONTENT_TYPE" => 'application/octet-stream'}.merge(credentials('jsmith')) 848 {"CONTENT_TYPE" => 'application/octet-stream'}.merge(credentials('jsmith'))
775 assert_response :created 849 assert_response :created
776 end 850 end
777 xml = Hash.from_xml(response.body) 851 xml = Hash.from_xml(response.body)
778 token = xml['upload']['token'] 852 token = xml['upload']['token']
779 attachment = Attachment.first(:order => 'id DESC') 853 attachment = Attachment.order('id DESC').first
780 854
781 # update the issue with the upload's token 855 # update the issue with the upload's token
782 assert_difference 'Journal.count' do 856 assert_difference 'Journal.count' do
783 put '/issues/1.xml', 857 put '/issues/1.xml',
784 {:issue => {:notes => 'Attachment added', 858 {:issue => {:notes => 'Attachment added',