From e67a2faf36a9d9f497df3dd387d68b08d1eb831d Mon Sep 17 00:00:00 2001 From: Chikako OHNO Date: Mon, 11 Mar 2019 23:41:14 +0900 Subject: [PATCH 1/4] =?UTF-8?q?#395=20dojo=5Fevent=5Fservices:upsert=20?= =?UTF-8?q?=E3=81=A7=E3=80=81URL=20=E3=81=AE=E3=81=BF=E7=95=B0=E3=81=AA?= =?UTF-8?q?=E3=82=8B=20dojo=5Fevent=5Fservices=20=E3=82=92=E4=BA=8C?= =?UTF-8?q?=E9=87=8D=E7=99=BB=E9=8C=B2=E3=81=97=E3=81=AA=E3=81=84=E3=82=88?= =?UTF-8?q?=E3=81=86=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- lib/tasks/dojo_event_services.rake | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/lib/tasks/dojo_event_services.rake b/lib/tasks/dojo_event_services.rake index 4224bee92..1f6b952bc 100644 --- a/lib/tasks/dojo_event_services.rake +++ b/lib/tasks/dojo_event_services.rake @@ -16,8 +16,10 @@ namespace :dojo_event_services do result[:skipped] << [des['dojo_id'], 'Not found record in `dojos` table'] next end - + # 比較対象は URL を除く dojo_id, name, group_id + url = des.delete('url') dojo_event_service = dojo.dojo_event_services.find_or_initialize_by(des) + dojo.dojo_event_services.where(des).where.not(id: dojo_event_service.id).destroy_all if dojo_event_service.changed? changes = dojo_event_service.changes new_record = dojo_event_service.new_record? From ec7b0ae3999e74ee7f00444a5521f21053bb2b31 Mon Sep 17 00:00:00 2001 From: Chikako OHNO Date: Thu, 28 Mar 2019 00:05:36 +0900 Subject: [PATCH 2/4] =?UTF-8?q?#395=20dojo=5Fevent=5Fservices:upsert=20?= =?UTF-8?q?=E3=81=AE=E4=BF=AE=E6=AD=A3=20+=20RSpec=20=E8=BF=BD=E5=8A=A0=20?= =?UTF-8?q?with=20factory=5Fbot=5Frails?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Gemfile | 1 + Gemfile.lock | 6 ++ lib/tasks/dojo_event_services.rake | 22 ++++-- spec/factories/dojo_event_services.rb | 10 +++ spec/factories/dojos.rb | 8 ++ spec/lib/tasks/dojo_event_services_spec.rb | 85 ++++++++++++++++++++++ spec/rails_helper.rb | 2 + 7 files changed, 126 insertions(+), 8 deletions(-) create mode 100644 spec/factories/dojo_event_services.rb create mode 100644 spec/factories/dojos.rb create mode 100644 spec/lib/tasks/dojo_event_services_spec.rb diff --git a/Gemfile b/Gemfile index f73e1fc5c..e7a77f3f0 100644 --- a/Gemfile +++ b/Gemfile @@ -62,6 +62,7 @@ group :development, :test do gem 'selenium-webdriver' gem 'capybara' gem 'rspec-rails', '~> 3.5' + gem 'factory_bot_rails' gem 'dotenv-rails' end diff --git a/Gemfile.lock b/Gemfile.lock index cae2d2191..6e29f8b79 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -90,6 +90,11 @@ GEM ethon (0.11.0) ffi (>= 1.3.0) execjs (2.7.0) + factory_bot (5.0.2) + activesupport (>= 4.2.0) + factory_bot_rails (5.0.1) + factory_bot (~> 5.0.0) + railties (>= 4.2.0) faraday (0.15.4) multipart-post (>= 1.2, < 3) faraday_middleware (0.12.2) @@ -400,6 +405,7 @@ DEPENDENCIES coffee-rails dotenv-rails dumper + factory_bot_rails faraday faraday_middleware flamegraph diff --git a/lib/tasks/dojo_event_services.rake b/lib/tasks/dojo_event_services.rake index 1f6b952bc..eedf54920 100644 --- a/lib/tasks/dojo_event_services.rake +++ b/lib/tasks/dojo_event_services.rake @@ -1,12 +1,12 @@ namespace :dojo_event_services do desc '現在のyamlファイルを元にデータベースを更新します' task upsert: :environment do - result = { inserted: [], updated: [], kept: [], skipped: [] } + result = { inserted: [], updated: [], deleted: [], kept: [], skipped: [] } list = YAML.load_file(Rails.root.join('db','dojo_event_services.yaml')) list.each do |des| unless DojoEventService.names.keys.include?(des['name']) - event_names = DojoEventService.names.keys.map {|s| "`#{s}`" } + event_names = DojoEventService.names.keys.map { |s| "`#{s}`" } result[:skipped] << [des['dojo_id'], "Not used #{event_names.join(' or ')}"] next end @@ -19,7 +19,14 @@ namespace :dojo_event_services do # 比較対象は URL を除く dojo_id, name, group_id url = des.delete('url') dojo_event_service = dojo.dojo_event_services.find_or_initialize_by(des) - dojo.dojo_event_services.where(des).where.not(id: dojo_event_service.id).destroy_all + overlapped = dojo.dojo_event_services.where(des).where.not(id: dojo_event_service.id) + if overlapped.present? + overlapped.each do |d| + result[:deleted] << ["#{d.dojo_id}:#{d.id}"] + end + overlapped.destroy_all + end + dojo_event_service.url = url if dojo_event_service.changed? changes = dojo_event_service.changes new_record = dojo_event_service.new_record? @@ -31,14 +38,13 @@ namespace :dojo_event_services do end # Dump result - if !result[:inserted].empty? || !result[:updated].empty? - result[:skipped] = result[:skipped].uniq {|s| s.first } + if result[:inserted] || result[:updated] + result[:skipped] = result[:skipped].uniq { |s| s.first } result.except!(:kept, :skipped) unless ENV.key?('DEBUG') - sorted = result.sort_by {|_, v| v.length }.reverse.to_h - puts + sorted = result.sort_by { |_, v| v.length }.reverse.to_h sorted.each do |k, v| puts "#{k.to_s.camelcase}: #{v.length}" - v.each {|x| puts " #{x.join(': ')}"} + v.each { |x| puts " #{x.join(': ')}" } end end end diff --git a/spec/factories/dojo_event_services.rb b/spec/factories/dojo_event_services.rb new file mode 100644 index 000000000..5c575263c --- /dev/null +++ b/spec/factories/dojo_event_services.rb @@ -0,0 +1,10 @@ +require 'factory_bot' + +FactoryBot.define do + factory :dojo_event_service do + # dojo_id + name { :connpass } + url { '' } + group_id { '9999' } + end +end diff --git a/spec/factories/dojos.rb b/spec/factories/dojos.rb new file mode 100644 index 000000000..e01f1fd73 --- /dev/null +++ b/spec/factories/dojos.rb @@ -0,0 +1,8 @@ +FactoryBot.define do + factory :dojo do + name { 'dojo name' } + email { '' } + description { '' } + prefecture_id { 13 } + end +end diff --git a/spec/lib/tasks/dojo_event_services_spec.rb b/spec/lib/tasks/dojo_event_services_spec.rb new file mode 100644 index 000000000..5e8163883 --- /dev/null +++ b/spec/lib/tasks/dojo_event_services_spec.rb @@ -0,0 +1,85 @@ +require 'rails_helper' +require 'rake' + +RSpec.describe 'dojo_event_services' do + before(:all) do + @rake = Rake::Application.new + Rake.application = @rake + Rake.application.rake_require 'tasks/dojo_event_services' + Rake::Task.define_task(:environment) + end + + before(:each) do + @rake[task].reenable + end + + describe 'dojo_event_services:upsert' do + before :each do + @dojo_1 = create(:dojo, name: 'dojo_1', email: 'mail_1@test', tags: %w(Scratch ラズベリーパイ), description: '月1回開催', prefecture_id: 13) + @dojo_2 = create(:dojo, name: 'dojo_2', email: 'mail_2@test', tags: %w(Scratch), description: '隔週開催', prefecture_id: 13) + @dojo_3 = create(:dojo, name: 'dojo_3', email: 'mail_3@test', tags: %w(Scratch ラズベリーパイ Webサイト), description: '月1回開催', prefecture_id: 13) + + create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10001', url: 'https://coder-dojo-11.doorkeeper.jp/') + create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002', url: 'https://coder-dojo-12.doorkeeper.jp/abc') + create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002', url: 'https://coder-dojo-12.doorkeeper.jp/') + create(:dojo_event_service, dojo_id: @dojo_2.id, name: :connpass, group_id: '20001', url: 'https://coder-dojo-21.connpass.jp/') + end + + let(:task) { 'dojo_event_services:upsert' } + + it '単純追加' do + allow(YAML).to receive(:load_file).and_return([ + { 'dojo_id' => @dojo_3.id, "name" => 'facebook', 'group_id' => '30001', 'url' => 'https://coder-dojo-31.facebook.com/' } + ]) + + # before + expect(DojoEventService.count).to eq(4) + + # exec + expect(@rake[task].invoke).to be_truthy + + # after + expect(DojoEventService.count).to eq(5) + new_records = DojoEventService.where(dojo_id: @dojo_3.id, name: :facebook, group_id: '30001') + expect(new_records.count).to eq(1) + expect(new_records.first.url).to eq('https://coder-dojo-31.facebook.com/') + end + + it '単純更新' do + allow(YAML).to receive(:load_file).and_return([ + { 'dojo_id' => @dojo_2.id, "name" => 'connpass', 'group_id' => '20001', 'url' => 'https://coder-dojo-21.connpass.jp/zzz' } + ]) + + # before + expect(DojoEventService.count).to eq(4) + + # exec + expect(@rake[task].invoke).to be_truthy + + # after + expect(DojoEventService.count).to eq(4) + mod_records = DojoEventService.where(dojo_id: @dojo_2.id, name: :connpass, group_id: '20001') + expect(mod_records.count).to eq(1) + expect(mod_records.first.url).to eq('https://coder-dojo-21.connpass.jp/zzz') + end + + it '余剰データ削除 & 更新' do + allow(YAML).to receive(:load_file).and_return([ + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10002', 'url' => 'https://coder-dojo-12.doorkeeper.jp/12345' } + ]) + + # before + expect(DojoEventService.count).to eq(4) + expect(DojoEventService.where(dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002').size).to eq(2) + + # exec + expect(@rake[task].invoke).to be_truthy + + # after + expect(DojoEventService.count).to eq(3) + mod_records = DojoEventService.where(dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002') + expect(mod_records.count).to eq(1) + expect(mod_records.first.url).to eq('https://coder-dojo-12.doorkeeper.jp/12345') + end + end +end diff --git a/spec/rails_helper.rb b/spec/rails_helper.rb index 7483c82d9..cfa487ade 100644 --- a/spec/rails_helper.rb +++ b/spec/rails_helper.rb @@ -62,4 +62,6 @@ example.skip end end + + config.include FactoryBot::Syntax::Methods end From f7b3048470d48a1e1b12fc400ed51f8bbc31d375 Mon Sep 17 00:00:00 2001 From: chicaco ohno <1582945+chicaco@users.noreply.github.com> Date: Thu, 28 Mar 2019 09:35:30 +0900 Subject: [PATCH 3/4] =?UTF-8?q?db:seed=20=E3=82=92=E8=BF=BD=E5=8A=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit RSpec の中の処理で prefectures T にマスタデータが必要なため、db:seed を追加 --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index 191f49473..0e4ab82ba 100644 --- a/.travis.yml +++ b/.travis.yml @@ -22,6 +22,7 @@ before_script: - psql -c 'create database coderdojo_jp_test;' -U postgres script: - bundle exec rake db:migrate --trace +- bundle exec rake db:seed --trace - if [ "$TRAVIS_PULL_REQUEST" = "false" ]; then bundle exec rspec spec; fi - if [ "$TRAVIS_PULL_REQUEST" != "false" ] && [ "$TRAVIS_PULL_REQUEST_SLUG" = "coderdojo-japan/coderdojo.jp" ]; then bundle exec rspec spec; fi From 7b554dd8587008ab4212791f1aacefa50ed17a68 Mon Sep 17 00:00:00 2001 From: Chikako OHNO Date: Thu, 28 Mar 2019 23:37:34 +0900 Subject: [PATCH 4/4] =?UTF-8?q?#395=20dojo=5Fevent=5Fservices:upsert=20?= =?UTF-8?q?=E3=81=AE=E4=BF=AE=E6=AD=A3(=E3=83=AC=E3=83=93=E3=83=A5?= =?UTF-8?q?=E3=83=BC=E6=8C=87=E6=91=98=E4=BA=8B=E9=A0=85=E5=8F=8D=E6=98=A0?= =?UTF-8?q?+=E5=87=A6=E7=90=86=E8=A6=8B=E7=9B=B4=E3=81=97)=20+=20RSpec=20?= =?UTF-8?q?=E4=BF=AE=E6=AD=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- lib/tasks/dojo_event_services.rake | 14 ++++++------- spec/lib/tasks/dojo_event_services_spec.rb | 24 ++++++++++++++-------- 2 files changed, 23 insertions(+), 15 deletions(-) diff --git a/lib/tasks/dojo_event_services.rake b/lib/tasks/dojo_event_services.rake index eedf54920..1bedc322b 100644 --- a/lib/tasks/dojo_event_services.rake +++ b/lib/tasks/dojo_event_services.rake @@ -2,6 +2,7 @@ namespace :dojo_event_services do desc '現在のyamlファイルを元にデータベースを更新します' task upsert: :environment do result = { inserted: [], updated: [], deleted: [], kept: [], skipped: [] } + reserved_ids = [] list = YAML.load_file(Rails.root.join('db','dojo_event_services.yaml')) list.each do |des| @@ -19,13 +20,6 @@ namespace :dojo_event_services do # 比較対象は URL を除く dojo_id, name, group_id url = des.delete('url') dojo_event_service = dojo.dojo_event_services.find_or_initialize_by(des) - overlapped = dojo.dojo_event_services.where(des).where.not(id: dojo_event_service.id) - if overlapped.present? - overlapped.each do |d| - result[:deleted] << ["#{d.dojo_id}:#{d.id}"] - end - overlapped.destroy_all - end dojo_event_service.url = url if dojo_event_service.changed? changes = dojo_event_service.changes @@ -35,6 +29,12 @@ namespace :dojo_event_services do else result[:kept] << ["#{des['dojo_id']}:#{dojo_event_service.id}"] end + reserved_ids << dojo_event_service.id + end + + DojoEventService.where.not(id: reserved_ids).find_each do |d| + result[:deleted] << ["#{d.dojo_id}:#{d.id}"] + d.destroy end # Dump result diff --git a/spec/lib/tasks/dojo_event_services_spec.rb b/spec/lib/tasks/dojo_event_services_spec.rb index 5e8163883..7c0338ced 100644 --- a/spec/lib/tasks/dojo_event_services_spec.rb +++ b/spec/lib/tasks/dojo_event_services_spec.rb @@ -20,7 +20,6 @@ @dojo_3 = create(:dojo, name: 'dojo_3', email: 'mail_3@test', tags: %w(Scratch ラズベリーパイ Webサイト), description: '月1回開催', prefecture_id: 13) create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10001', url: 'https://coder-dojo-11.doorkeeper.jp/') - create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002', url: 'https://coder-dojo-12.doorkeeper.jp/abc') create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002', url: 'https://coder-dojo-12.doorkeeper.jp/') create(:dojo_event_service, dojo_id: @dojo_2.id, name: :connpass, group_id: '20001', url: 'https://coder-dojo-21.connpass.jp/') end @@ -29,17 +28,20 @@ it '単純追加' do allow(YAML).to receive(:load_file).and_return([ - { 'dojo_id' => @dojo_3.id, "name" => 'facebook', 'group_id' => '30001', 'url' => 'https://coder-dojo-31.facebook.com/' } + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10001', 'url' => 'https://coder-dojo-11.doorkeeper.jp/' }, + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10002', 'url' => 'https://coder-dojo-12.doorkeeper.jp/' }, + { 'dojo_id' => @dojo_2.id, "name" => 'connpass', 'group_id' => '20001', 'url' => 'https://coder-dojo-21.connpass.jp/' }, + { 'dojo_id' => @dojo_3.id, "name" => 'facebook', 'group_id' => '30001', 'url' => 'https://coder-dojo-31.facebook.com/' } ]) # before - expect(DojoEventService.count).to eq(4) + expect(DojoEventService.count).to eq(3) # exec expect(@rake[task].invoke).to be_truthy # after - expect(DojoEventService.count).to eq(5) + expect(DojoEventService.count).to eq(4) new_records = DojoEventService.where(dojo_id: @dojo_3.id, name: :facebook, group_id: '30001') expect(new_records.count).to eq(1) expect(new_records.first.url).to eq('https://coder-dojo-31.facebook.com/') @@ -47,25 +49,31 @@ it '単純更新' do allow(YAML).to receive(:load_file).and_return([ - { 'dojo_id' => @dojo_2.id, "name" => 'connpass', 'group_id' => '20001', 'url' => 'https://coder-dojo-21.connpass.jp/zzz' } + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10001', 'url' => 'https://coder-dojo-11.doorkeeper.jp/' }, + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10002', 'url' => 'https://coder-dojo-12.doorkeeper.jp/' }, + { 'dojo_id' => @dojo_2.id, "name" => 'connpass', 'group_id' => '20001', 'url' => 'https://coder-dojo-21.connpass.jp/zzz' } ]) # before - expect(DojoEventService.count).to eq(4) + expect(DojoEventService.count).to eq(3) # exec expect(@rake[task].invoke).to be_truthy # after - expect(DojoEventService.count).to eq(4) + expect(DojoEventService.count).to eq(3) mod_records = DojoEventService.where(dojo_id: @dojo_2.id, name: :connpass, group_id: '20001') expect(mod_records.count).to eq(1) expect(mod_records.first.url).to eq('https://coder-dojo-21.connpass.jp/zzz') end it '余剰データ削除 & 更新' do + create(:dojo_event_service, dojo_id: @dojo_1.id, name: :doorkeeper, group_id: '10002', url: 'https://coder-dojo-12.doorkeeper.jp/abc') + allow(YAML).to receive(:load_file).and_return([ - { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10002', 'url' => 'https://coder-dojo-12.doorkeeper.jp/12345' } + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10001', 'url' => 'https://coder-dojo-11.doorkeeper.jp/' }, + { 'dojo_id' => @dojo_1.id, "name" => 'doorkeeper', 'group_id' => '10002', 'url' => 'https://coder-dojo-12.doorkeeper.jp/12345' }, + { 'dojo_id' => @dojo_2.id, "name" => 'connpass', 'group_id' => '20001', 'url' => 'https://coder-dojo-21.connpass.jp/' } ]) # before