diff --git a/app/jobs/regular/export_user_archive.rb b/app/jobs/regular/export_user_archive.rb index fe5d0ea7c0f..e5a8a6b7e7d 100644 --- a/app/jobs/regular/export_user_archive.rb +++ b/app/jobs/regular/export_user_archive.rb @@ -18,6 +18,7 @@ module Jobs badges bookmarks category_preferences + queued_posts visits ) @@ -29,6 +30,7 @@ module Jobs badges: ['badge_id', 'badge_name', 'granted_at', 'post_id', 'seq', 'granted_manually', 'notification_id', 'featured_rank'], bookmarks: ['post_id', 'topic_id', 'post_number', 'link', 'name', 'created_at', 'updated_at', 'reminder_type', 'reminder_at', 'reminder_last_sent_at', 'reminder_set_at', 'auto_delete_preference'], category_preferences: ['category_id', 'category_names', 'notification_level', 'dismiss_new_timestamp'], + queued_posts: ['id', 'verdict', 'category_id', 'topic_id', 'post_raw', 'other_json'], visits: ['visited_at', 'posts_read', 'mobile', 'time_read'], ) @@ -265,6 +267,25 @@ module Jobs end end + def queued_posts_export + return enum_for(:queued_posts_export) unless block_given? + + # Most Reviewable fields staff-private, but post content needs to be exported. + ReviewableQueuedPost + .where(created_by: @current_user.id) + .each do |rev| + + yield [ + rev.id, + Reviewable.statuses[rev.status], + rev.category_id, + rev.topic_id, + rev.payload['raw'], + MultiJson.dump(rev.payload.slice(*queued_posts_payload_permitted_keys)), + ] + end + end + def visits_export return enum_for(:visits_export) unless block_given? @@ -354,6 +375,23 @@ module Jobs user_archive_profile end + def queued_posts_payload_permitted_keys + # Generated with: + # + # SELECT distinct json_object_keys(payload) from reviewables + # where type = 'ReviewableQueuedPost' and (payload->'old_queued_post_id') IS NULL + # + # except raw, created_topic_id, created_post_id + %w{ + composer_open_duration_msecs + is_poll + reply_to_post_number + tags + title + typing_duration_msecs + } + end + def notify_user(upload, export_title) post = nil diff --git a/spec/jobs/export_user_archive_spec.rb b/spec/jobs/export_user_archive_spec.rb index 7327429c029..cc70e7ca888 100644 --- a/spec/jobs/export_user_archive_spec.rb +++ b/spec/jobs/export_user_archive_spec.rb @@ -14,6 +14,10 @@ describe Jobs::ExportUserArchive do } let(:component) { raise 'component not set' } + let(:category) { Fabricate(:category_with_definition) } + let(:subcategory) { Fabricate(:category_with_definition, parent_category_id: category.id) } + let(:topic) { Fabricate(:topic, category: category) } + def make_component_csv data_rows = [] csv_out = CSV.generate do |csv| @@ -90,13 +94,10 @@ describe Jobs::ExportUserArchive do context 'user_archive posts' do let(:component) { 'user_archive' } let(:user2) { Fabricate(:user) } - let(:category) { Fabricate(:category_with_definition) } - let(:subcategory) { Fabricate(:category_with_definition, parent_category_id: category.id) } let(:subsubcategory) { Fabricate(:category_with_definition, parent_category_id: subcategory.id) } let(:subsubtopic) { Fabricate(:topic, category: subsubcategory) } let(:subsubpost) { Fabricate(:post, user: user, topic: subsubtopic) } - let(:topic) { Fabricate(:topic, category: category) } let(:normal_post) { Fabricate(:post, user: user, topic: topic) } let(:reply) { PostCreator.new(user2, raw: 'asdf1234qwert7896', topic_id: topic.id, reply_to_post_number: normal_post.post_number).create } @@ -297,11 +298,8 @@ describe Jobs::ExportUserArchive do context 'category_preferences' do let(:component) { 'category_preferences' } - let(:category) { Fabricate(:category_with_definition) } - let(:subcategory) { Fabricate(:category_with_definition, parent_category_id: category.id) } let(:subsubcategory) { Fabricate(:category_with_definition, parent_category_id: subcategory.id) } let(:announcements) { Fabricate(:category_with_definition) } - let(:deleted_category) { Fabricate(:category) } let(:reset_at) { DateTime.parse('2017-03-01 12:00') } @@ -353,6 +351,32 @@ describe Jobs::ExportUserArchive do end end + context 'queued posts' do + let(:component) { 'queued_posts' } + let(:reviewable_post) { Fabricate(:reviewable_queued_post, topic: topic, created_by: user) } + let(:reviewable_topic) { Fabricate(:reviewable_queued_post_topic, category: category, created_by: user) } + let(:admin) { Fabricate(:admin) } + + it 'correctly exports queued posts' do + SiteSetting.tagging_enabled = true + + reviewable_post.perform(admin, :reject_post) + reviewable_topic.payload['tags'] = ['example_tag'] + result = reviewable_topic.perform(admin, :approve_post) + expect(result.success?).to eq(true) + + data, csv_out = make_component_csv + expect(data.length).to eq(2) + data.sort { |e| e['id'].to_i } + + expect(csv_out).to_not match(admin.username) + + expect(data[0]['post_raw']).to eq('hello world post contents.') + expect(data[0]['other_json']).to match('reply_to_post_number') + expect(data[1]['other_json']).to match('example_tag') + end + end + context 'visits' do let(:component) { 'visits' } let(:user2) { Fabricate(:user) }