Page MenuHomeGRNET

No OneTemporary

File Metadata

Created
Thu, Apr 3, 7:26 AM
diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js
index d4087f7..31d3872 100644
--- a/app/assets/javascripts/application.js
+++ b/app/assets/javascripts/application.js
@@ -1,40 +1,67 @@
// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//
//= require jquery
//= require jquery_ujs
//= require bootstrap.min
//= require_tree .
//= require highcharts
$(document).ready(function() {
$(".include_files-plus-sign").click(function() {
addIncludedFileTextArea();
});
$(".exclude_directions-plus-sign").click(function() {
addExcludeDirectionsTextArea();
});
+ $(".schedule_run_form_plus").click(function() {
+ addScheduleRun();
+ });
+ $(".schedule_run_form_remove").click(function() {
+ removeScheduleRun();
+ });
});
function addIncludedFileTextArea() {
var textArrea = $('.include_files:last').clone(true).val("");
$('.include_files-plus-sign:first').parent().remove();
textArrea.insertAfter('.include_files:last');
$('.include_files:last input').val("");
}
function addExcludeDirectionsTextArea() {
var textArrea = $('.exclude_directions:last').clone(true).val("");
$('.exclude_directions-plus-sign:first').parent().remove();
textArrea.insertAfter('.exclude_directions:last');
$('.exclude_directions:last input').val("");
}
+
+function addScheduleRun() {
+ var scheduleRun = $('.schedule_run_form:last').clone();
+ scheduleRun.insertAfter('.schedule_run_form:last');
+ $('.schedule_run_form:last input').val('');
+ if ($('.schedule_run_form').size() > 1) {
+ $(".schedule_run_form_remove").show();
+ };
+}
+
+function removeScheduleRun() {
+ if ($('.schedule_run_form').size() > 1) {
+ $('.schedule_run_form:last').remove();
+ if ($('.schedule_run_form').size() == 1) {
+ $(".schedule_run_form_remove").hide();
+ };
+ }
+ else {
+ alert('nothing to remove');
+ };
+}
diff --git a/app/controllers/schedules_controller.rb b/app/controllers/schedules_controller.rb
index c5ef177..4824a49 100644
--- a/app/controllers/schedules_controller.rb
+++ b/app/controllers/schedules_controller.rb
@@ -1,51 +1,52 @@
class SchedulesController < ApplicationController
before_action :fetch_host, only: [:new, :create]
before_action :fetch_job_id, only: [:new, :create]
def new
@schedule = @host.schedules.new
end
def show
end
def edit
end
def update
end
def create
@schedule = @host.schedules.new(fetch_params)
@schedule.runtime = params[:schedule][:runtime] if params[:schedule][:runtime]
if @schedule.save
flash[:success] = 'Schedule created successfully'
if @job_id.present?
redirect_to edit_host_job_path(@host, @job_id, schedule_id: @schedule.id)
else
redirect_to new_host_job_path(@host, schedule_id: @schedule.id)
end
else
render :new
end
end
def destroy
end
private
def fetch_host
@host = current_user.hosts.find(params[:host_id])
end
def fetch_job_id
@job_id = @host.job_templates.find(params[:job_id]).id if params[:job_id].present?
end
def fetch_params
- params.require(:schedule).permit(:name)
+ params.require(:schedule).
+ permit(:name, { schedule_runs_attributes: [[:level, :month, :day, :time]] })
end
end
diff --git a/app/models/schedule.rb b/app/models/schedule.rb
index a026cee..ccad7ab 100644
--- a/app/models/schedule.rb
+++ b/app/models/schedule.rb
@@ -1,45 +1,22 @@
class Schedule < ActiveRecord::Base
- DEFAULT_RUNS = [
- 'Level=Full 1st sun at ',
- 'Level=Differential 2nd-5th sun at ',
- 'Level=Incremental mon-sat at '
- ]
-
- attr_accessor :runtime
-
- serialize :runs, JSON
+ has_many :schedule_runs
belongs_to :host
- validates :name, :runs, presence: true
+ validates :name, presence: true
validates :name, uniqueness: { scope: :host }
validates_with NameValidator
- before_validation :set_runs, if: Proc.new { |s| s.runtime.present? }
+ accepts_nested_attributes_for :schedule_runs
def to_bacula_config_array
['Schedule {'] +
[" Name = \"#{name_for_config}\""] +
- runs.map {|r| " Run = #{r}" } +
+ schedule_runs.map {|r| " Run = #{r.schedule_line}" } +
['}']
end
def name_for_config
[host.name, name].join(' ')
end
-
- private
-
- def set_runs
- if valid_runtime?
- self.runs = DEFAULT_RUNS.map { |r| r + runtime }
- else
- self.errors.add(:runtime, :not_valid_24h_time)
- false
- end
- end
-
- def valid_runtime?
- runtime && runtime[/^([01]?[0-9]|2[0-3]):[0-5][0-9]$/]
- end
end
diff --git a/app/views/schedules/_form.html.erb b/app/views/schedules/_form.html.erb
index 4ebd63e..f53d299 100644
--- a/app/views/schedules/_form.html.erb
+++ b/app/views/schedules/_form.html.erb
@@ -1,27 +1,49 @@
<%= bootstrap_form_for(@schedule, url: host_schedules_path(@host), layout: :horizontal,
label_col: 'col-xs-3', control_col: 'col-xs-8') do |f| %>
- <% if @schedule.errors.any? %>
- <div id="error_explanation">
- <h2><%= pluralize(@schedule.errors.count, "error") %> prohibited this schedule from being saved:</h2>
+ <%= f.text_field :name, required: true %>
+ <hr />
+ <% if ['schedule_runs.day','schedule_runs.month','scheduled_runs.time'] - @schedule.errors.keys %>
+ <div id="error_explanation" class="has-error">
<ul>
- <% @schedule.errors.full_messages.each do |message| %>
- <li><%= message %></li>
- <% end %>
+ <% @schedule.errors.full_messages.each do |message| %>
+ <li><span class="help-block"><%= message %></span></li>
+ <% end %>
</ul>
</div>
<% end %>
- <div>
- <%= f.text_field :name %>
- <%= f.time_field :runtime, placeholder: 'HH:MM' %>
- <%= (hidden_field_tag :job_id, @job_id) if @job_id%>
+ <%= f.fields_for :schedule_runs_attributes, index: nil do |r| %>
+ <div class="schedule_run_form">
+ <%= r.select :level, options_for_select(ScheduleRun.levels.keys) %>
+ <%= r.text_field :month, placeholder: '[month | month-range]' %>
+ <p class="col-xs-10 col-xs-offset-1 help-block text-right">eg: jan-mar, feb, monthly</p>
+ <%= r.text_field :day, placeholder: '[week | week-range] day | day-range',
+ required: true %>
+ <p class="col-xs-10 col-xs-offset-1 help-block text-right">
+eg: first sun, second-fifth mon, mon-sat
+ </p>
+ <%= r.time_field :time, placeholder: 'HH:MM', required: true %>
+ </div>
+ <hr />
+ <% end %>
+
+ <div class="col-xs-1 col-xs-offset-10">
+ <%= link_to '#', class: 'schedule_run_form_remove', style: 'display:none;' do %>
+ <span class="glyphicon glyphicon-remove text-danger"></span>
+ <% end %>
+ </div>
+ <div class="col-xs-1 col-xs-offset-10">
+ <%= link_to '#', class: 'schedule_run_form_plus' do %>
+ <span class="glyphicon glyphicon-plus text-success"></span>
+ <% end %>
</div>
+ <%= (hidden_field_tag :job_id, @job_id) if @job_id%>
<div class="form-group">
<div class="col-xs-offset-3 col-xs-8">
<%= f.submit class: 'btn btn-success' %>
</div>
</div>
<% end %>
diff --git a/spec/controllers/schedules_controller_spec.rb b/spec/controllers/schedules_controller_spec.rb
index 9a1e4a9..cc4d7f7 100644
--- a/spec/controllers/schedules_controller_spec.rb
+++ b/spec/controllers/schedules_controller_spec.rb
@@ -1,95 +1,95 @@
require 'spec_helper'
describe SchedulesController do
let(:host) { FactoryGirl.create(:host) }
let(:user) { FactoryGirl.create(:user) }
before do
host.users << user
controller.stub(:current_user) { user }
end
describe 'GET #new' do
before { get :new, host_id: host.id }
it 'initializes a schedule' do
expect(assigns(:schedule)).to be
end
it 'sets the schedule\'s host' do
expect(assigns(:schedule).host).to eq(host)
end
it 'renders' do
expect(response).to render_template(:new)
end
end
describe 'POST #create' do
context 'with valid params' do
let(:params) do
{
host_id: host.id,
- schedule: { name: FactoryGirl.build(:schedule).name, runtime: '19:17' }
+ schedule: { name: FactoryGirl.build(:schedule).name }
}
end
it 'creates the schedule' do
expect { post :create, params }.
to change { host.schedules(true).count }.by(1)
end
it 'redirects to a new job form' do
post :create, params
expect(response).to redirect_to(new_host_job_path(host, schedule_id: Schedule.last.id))
end
context 'and an existing job' do
let(:job) { FactoryGirl.create(:job_template, host: host) }
it 'redirects to the job\'s edit form' do
post :create, params.merge(job_id: job.id)
expect(response).
to redirect_to(edit_host_job_path(host, job, schedule_id: Schedule.last.id))
end
end
end
context 'with invalid host' do
it 'raises not found error' do
expect {
post :create, { host_id: -1, schedule: { invalid: true } }
}.to raise_error(ActiveRecord::RecordNotFound)
end
end
context 'with invalid params' do
let(:params) do
{
host_id: host.id,
schedule: { invalide: :foo }
}
end
it 'initializes a schedule with errors' do
post :create, params
expect(assigns(:schedule)).to be
end
it 'does not create the schedule' do
expect { post :create, params }.
to_not change { Schedule.count }
end
it 'renders :new' do
post :create, params
expect(response).to render_template(:new)
end
it 'assigns the host to schedule' do
post :create, params
expect(assigns(:schedule).host).to eq(host)
end
end
end
end
diff --git a/spec/factories/schedule.rb b/spec/factories/schedule.rb
index f4c49a3..cc83ac3 100644
--- a/spec/factories/schedule.rb
+++ b/spec/factories/schedule.rb
@@ -1,9 +1,6 @@
FactoryGirl.define do
factory :schedule do
host
sequence(:name) { |n| "Schedule #{n}" }
- runs ['Level=Full 1st sun at 2:05',
- 'Level=Differential 2nd-5th sun at 2:05',
- 'Level=Incremental mon-sat at 2:05']
end
end
diff --git a/spec/factories/schedule_run.rb b/spec/factories/schedule_run.rb
new file mode 100644
index 0000000..375bdc5
--- /dev/null
+++ b/spec/factories/schedule_run.rb
@@ -0,0 +1,8 @@
+FactoryGirl.define do
+ factory :schedule_run do
+ schedule
+ level 0
+ day 'first sun'
+ time '12:34'
+ end
+end
diff --git a/spec/models/schedule_spec.rb b/spec/models/schedule_spec.rb
index 3725d4a..dd92bc0 100644
--- a/spec/models/schedule_spec.rb
+++ b/spec/models/schedule_spec.rb
@@ -1,58 +1,46 @@
require 'spec_helper'
describe Schedule do
context 'validates' do
it 'presence of name' do
expect(Schedule.new).to have(2).errors_on(:name)
end
- it 'presence of runs' do
- expect(Schedule.new).to have(1).errors_on(:runs)
- end
-
context 'schedule name is unique in the host\'s scope' do
let!(:schedule_1) { FactoryGirl.create(:schedule, name: 'Schedule_1') }
let(:schedule_2) { FactoryGirl.build(:schedule, name: 'Schedule_1') }
let(:schedule_3) { FactoryGirl.build(:schedule, name: 'Schedule_1', host: schedule_1.host) }
it 'two schedules of diferent hosts can have the same name' do
expect(schedule_2).to be_valid
end
it 'two schedules of the same host can NOT have the same name' do
expect(schedule_3).to_not be_valid
end
end
end
describe '#to_bacula_config_array' do
- let(:runs) do
- [
- 'Full 1st sun at 23:05',
- 'Differential 2nd-5th sun at 23:50',
- 'Incremental mon-sat at 23:50'
- ]
- end
-
let(:schedule) do
- FactoryGirl.create(:schedule, name: 'Test Schedule', runs: runs)
+ FactoryGirl.create(:schedule, name: 'Test Schedule')
end
+ let!(:schedule_run) { FactoryGirl.create(:schedule_run, schedule: schedule) }
+
subject { schedule.to_bacula_config_array }
it 'is a schedule type resource' do
expect(subject.first).to eq('Schedule {')
expect(subject.last).to eq('}')
end
it 'contains the name' do
expect(subject).to include(" Name = \"#{[schedule.host.name, schedule.name].join(' ')}\"")
end
it 'contains the runs' do
- runs.each do |r|
- expect(subject).to include(" Run = #{r}")
- end
+ expect(subject).to include(" Run = #{schedule.schedule_runs.first.schedule_line}")
end
end
end

Event Timeline