diff --git a/lib/split/dashboard.rb b/lib/split/dashboard.rb index ef02f1e8..478a2354 100755 --- a/lib/split/dashboard.rb +++ b/lib/split/dashboard.rb @@ -45,6 +45,12 @@ class Dashboard < Sinatra::Base redirect url('/') end + post '/reopen/:experiment' do + @experiment = Split::Experiment.find(params[:experiment]) + @experiment.reset_winner + redirect url('/') + end + delete '/:experiment' do @experiment = Split::Experiment.find(params[:experiment]) @experiment.delete diff --git a/lib/split/dashboard/public/dashboard.js b/lib/split/dashboard/public/dashboard.js index a64782ab..0f779046 100644 --- a/lib/split/dashboard/public/dashboard.js +++ b/lib/split/dashboard/public/dashboard.js @@ -16,4 +16,9 @@ function confirmWinner() { function confirmStep(step) { var agree = confirm(step); return agree ? true : false; -} \ No newline at end of file +} + +function confirmReopen() { + var agree = confirm("This will reopen the experiment. Are you sure?"); + return agree ? true : false; +} diff --git a/lib/split/dashboard/views/_controls.erb b/lib/split/dashboard/views/_controls.erb index 3be00041..47bc3563 100644 --- a/lib/split/dashboard/views/_controls.erb +++ b/lib/split/dashboard/views/_controls.erb @@ -1,3 +1,8 @@ +<% if experiment.has_winner? %> +
" method='post' onclick="return confirmReopen()"> + +
+<% end %> <% if experiment.start_time %>
" method='post' onclick="return confirmReset()"> diff --git a/lib/split/dashboard/views/_experiment.erb b/lib/split/dashboard/views/_experiment.erb index f55a5332..83266ecc 100644 --- a/lib/split/dashboard/views/_experiment.erb +++ b/lib/split/dashboard/views/_experiment.erb @@ -59,7 +59,7 @@ <%= confidence_level(alternative.z_score(goal)) %> - <% if experiment.winner %> + <% if experiment.has_winner? %> <% if experiment.winner.name == alternative.name %> Winner <% else %> diff --git a/lib/split/experiment.rb b/lib/split/experiment.rb index d85c0e38..74f98622 100644 --- a/lib/split/experiment.rb +++ b/lib/split/experiment.rb @@ -149,6 +149,10 @@ def winner end end + def has_winner? + !winner.nil? + end + def winner=(winner_name) Split.redis.hset(:experiment_winner, name, winner_name.to_s) end diff --git a/lib/split/helper.rb b/lib/split/helper.rb index 3b7baf48..d47067e2 100644 --- a/lib/split/helper.rb +++ b/lib/split/helper.rb @@ -55,7 +55,7 @@ def reset!(experiment) end def finish_experiment(experiment, options = {:reset => true}) - return true unless experiment.winner.nil? + return true if experiment.has_winner? should_reset = experiment.resettable? && options[:reset] if ab_user[experiment.finished_key] && !should_reset return true @@ -168,7 +168,7 @@ def start_trial(trial) if override_present?(experiment.name) ret = override_alternative(experiment.name) ab_user[experiment.key] = ret if Split.configuration.store_override - elsif ! experiment.winner.nil? + elsif experiment.has_winner? ret = experiment.winner.name else clean_old_versions(experiment) diff --git a/lib/split/trial.rb b/lib/split/trial.rb index 323f9d09..030888f6 100644 --- a/lib/split/trial.rb +++ b/lib/split/trial.rb @@ -10,7 +10,7 @@ def initialize(attrs = {}) end def alternative - @alternative ||= if experiment.winner + @alternative ||= if experiment.has_winner? experiment.winner end end diff --git a/spec/dashboard_spec.rb b/spec/dashboard_spec.rb index 989c91f2..620bd0a5 100644 --- a/spec/dashboard_spec.rb +++ b/spec/dashboard_spec.rb @@ -59,6 +59,53 @@ def link(color) end end + describe "index page" do + context "with winner" do + before { experiment.winner = 'red' } + + it "displays `Reopen Experiment` button" do + get '/' + + expect(last_response.body).to include('Reopen Experiment') + end + end + + context "without winner" do + it "should not display `Reopen Experiment` button" do + get '/' + + expect(last_response.body).to_not include('Reopen Experiment') + end + end + end + + describe "reopen experiment" do + before { experiment.winner = 'red' } + + it 'redirects' do + post "/reopen/#{experiment.name}" + + expect(last_response).to be_redirect + end + + it "removes winner" do + post "/reopen/#{experiment.name}" + + expect(experiment).to_not have_winner + end + + it "keeps existing stats" do + red_link.participant_count = 5 + blue_link.participant_count = 7 + experiment.winner = 'blue' + + post "/reopen/#{experiment.name}" + + expect(red_link.participant_count).to eq(5) + expect(blue_link.participant_count).to eq(7) + end + end + it "should reset an experiment" do red_link.participant_count = 5 blue_link.participant_count = 7 diff --git a/spec/experiment_spec.rb b/spec/experiment_spec.rb index 418e51b5..ee43496f 100644 --- a/spec/experiment_spec.rb +++ b/spec/experiment_spec.rb @@ -201,6 +201,22 @@ def alternative(color) end end + describe 'has_winner?' do + context 'with winner' do + before { experiment.winner = 'red' } + + it 'returns true' do + expect(experiment).to have_winner + end + end + + context 'without winner' do + it 'returns false' do + expect(experiment).to_not have_winner + end + end + end + describe 'reset' do before { experiment.save } it 'should reset all alternatives' do