diff options
| -rw-r--r-- | app/assets/images/severity-error.png | bin | 0 -> 1857 bytes | |||
| -rw-r--r-- | app/assets/images/severity-info.png | bin | 0 -> 1443 bytes | |||
| -rw-r--r-- | app/assets/images/severity-warning.png | bin | 0 -> 1445 bytes | |||
| -rw-r--r-- | app/assets/stylesheets/imports.css.scss | 12 | ||||
| -rw-r--r-- | app/models/import.rb | 8 | ||||
| -rw-r--r-- | app/models/import_log_message.rb | 36 | ||||
| -rw-r--r-- | app/views/imports/_import.erb | 4 | ||||
| -rw-r--r-- | app/views/imports/show.html.erb | 38 | ||||
| -rw-r--r-- | config/initializers/apartment.rb | 2 | ||||
| -rw-r--r-- | config/locales/imports.yml | 42 | ||||
| -rw-r--r-- | db/migrate/20120529154848_create_import_log_messages.rb | 14 | ||||
| -rw-r--r-- | db/schema.rb | 14 | ||||
| -rw-r--r-- | spec/factories.rb | 10 | ||||
| -rw-r--r-- | spec/fixtures/neptune.zip | bin | 0 -> 4904 bytes | |||
| -rw-r--r-- | spec/models/import_log_message_spec.rb | 16 | ||||
| -rw-r--r-- | spec/models/import_spec.rb | 32 |
16 files changed, 222 insertions, 6 deletions
diff --git a/app/assets/images/severity-error.png b/app/assets/images/severity-error.png Binary files differnew file mode 100644 index 000000000..516a4d61a --- /dev/null +++ b/app/assets/images/severity-error.png diff --git a/app/assets/images/severity-info.png b/app/assets/images/severity-info.png Binary files differnew file mode 100644 index 000000000..740170cb7 --- /dev/null +++ b/app/assets/images/severity-info.png diff --git a/app/assets/images/severity-warning.png b/app/assets/images/severity-warning.png Binary files differnew file mode 100644 index 000000000..661327276 --- /dev/null +++ b/app/assets/images/severity-warning.png diff --git a/app/assets/stylesheets/imports.css.scss b/app/assets/stylesheets/imports.css.scss index dda468465..bdc3a65cd 100644 --- a/app/assets/stylesheets/imports.css.scss +++ b/app/assets/stylesheets/imports.css.scss @@ -23,3 +23,15 @@ padding-right: 10px; } } + +#workspace.imports.show { + table { + th { + text-align: center; + font-style: italic; + } + td.message, td.created_at, td.position { + padding: 0 20px; + } + } +}
\ No newline at end of file diff --git a/app/models/import.rb b/app/models/import.rb index ec6caa660..64b5b5624 100644 --- a/app/models/import.rb +++ b/app/models/import.rb @@ -9,6 +9,8 @@ class Import < ActiveRecord::Base attr_accessor :resources attr_accessor :loader + has_many :log_messages, :class_name => "ImportLogMessage", :order => :position, :dependent => :destroy + def loader @loader ||= ::Chouette::Loader.new(referential.slug) end @@ -49,8 +51,13 @@ class Import < ActiveRecord::Base "#{root}/#{id}.zip" end + def name + "#{Import.model_name.humanize} #{id}" + end + def import begin + log_messages.create :key => :started if resources with_original_filename do |file| # chouette-command checks the file extension (and requires .zip) :( @@ -64,6 +71,7 @@ class Import < ActiveRecord::Base Rails.logger.error "Import #{id} failed : #{e}, #{e.backtrace}" update_attribute :status, "failed" end + log_messages.create :key => status end end diff --git a/app/models/import_log_message.rb b/app/models/import_log_message.rb new file mode 100644 index 000000000..699c9603d --- /dev/null +++ b/app/models/import_log_message.rb @@ -0,0 +1,36 @@ +class ImportLogMessage < ActiveRecord::Base + belongs_to :import + acts_as_list :scope => :import + + validates_presence_of :key + validates_inclusion_of :severity, :in => %w{info warning error} + + def arguments=(arguments) + write_attribute :arguments, (arguments.to_json if arguments.present?) + end + + def arguments + @decoded_arguments ||= + begin + if (stored_arguments = raw_attributes).present? + ActiveSupport::JSON.decode stored_arguments + else + {} + end + end + end + + def raw_attributes + read_attribute(:arguments) + end + + before_validation :define_default_attributes, :on => :create + def define_default_attributes + self.severity ||= "info" + end + + def full_message + I18n.translate key, arguments.symbolize_keys.merge(:scope => "import_log_messages.messages") + end + +end diff --git a/app/views/imports/_import.erb b/app/views/imports/_import.erb index 643b3f18b..6ccd5bb23 100644 --- a/app/views/imports/_import.erb +++ b/app/views/imports/_import.erb @@ -1,8 +1,8 @@ <%= div_for(import) do %> - <%= link_to("#", :class => "preview") do %> + <%= link_to(referential_import_path(@referential, import), :class => "preview") do %> <%= image_tag "import-#{import.status}.png" %> <% end %> - <%= Import.model_name.humanize %> <%= import.id %> + <%= link_to(import.name, referential_import_path(@referential, import)) %> <div class="info"> <%= l import.created_at %> diff --git a/app/views/imports/show.html.erb b/app/views/imports/show.html.erb new file mode 100644 index 000000000..fe2c89a39 --- /dev/null +++ b/app/views/imports/show.html.erb @@ -0,0 +1,38 @@ +<%= title_tag @import.name %> + +<div class="import_show"> + <div class="summary"> + <p> + <label><%= Import.human_attribute_name(:created_at) %>: </label> + <%= l @import.created_at %> + </p> + <p> + <label><%= Import.human_attribute_name(:status) %>: </label> + <%= t @import.status, :scope => "imports.statuses" %> + </p> + </div> + + <h3><%= t(".report") %></h3> + <table> + <tr> + <th></th> + <th><%= ImportLogMessage.human_attribute_name(:created_at) %></th> + <th><%= ImportLogMessage.human_attribute_name(:position) %></th> + <th><%= ImportLogMessage.human_attribute_name(:full_message) %></th> + </tr> + <% @import.log_messages.each do |message| %> + <tr> + <td class="severity"><%= image_tag "severity-#{message.severity}.png", :alt => t(message.severity, :scope => "import_log_messages.severities") %></td> + <td class="created_at"><%= l message.created_at, :format => :short %></td> + <td class="position"><%= message.position %></td> + <td class="message"><%= message.full_message %></td> + </tr> + <% end %> + </table> +</div> + +<% content_for :sidebar do %> +<ul class="actions"> + <li><%= link_to t('imports.actions.destroy'), referential_import_path(@referential, @import), :method => :delete, :confirm => t('imports.actions.destroy_confirm'), :class => "remove" %></li> +</ul> +<% end %> diff --git a/config/initializers/apartment.rb b/config/initializers/apartment.rb index be6b7e933..20263f5c6 100644 --- a/config/initializers/apartment.rb +++ b/config/initializers/apartment.rb @@ -1,6 +1,6 @@ Apartment.configure do |config| # set your options (described below) here - config.excluded_models = ["Referential", "User", "Import", "Delayed::Backend::ActiveRecord::Job"] # these models will not be multi-tenanted, but remain in the global (public) namespace + config.excluded_models = ["Referential", "User", "Import", "ImportLogMessage", "Delayed::Backend::ActiveRecord::Job"] # these models will not be multi-tenanted, but remain in the global (public) namespace # Dynamically get database names to migrate config.database_names = lambda{ Referential.select(:slug).map(&:slug) } diff --git a/config/locales/imports.yml b/config/locales/imports.yml index d4c8b2d7c..40db6d65e 100644 --- a/config/locales/imports.yml +++ b/config/locales/imports.yml @@ -8,6 +8,21 @@ en: title: New import index: title: Imports + show: + report: Report + statuses: + pending: Pending + completed: Completed + failed: Failed + import_log_messages: + messages: + started: Started import + completed: Completed import + failed: Failed import + severities: + info: Information + warning: Warning + error: Error activerecord: models: import: @@ -17,16 +32,36 @@ en: attributes: import: resources: File to import + status: Status + import_log_message: + created_at: Date + position: N. + full_message: Message fr: imports: actions: new: Nouvel import - destroy: Supprimer + destroy: Supprimer cet import destroy_confirm: Etes vous sûr de détruire cet import ? new: title: Nouvel import index: title: Imports + show: + report: Rapport + statuses: + pending: En cours + completed: Achevé + failed: Echoué + import_log_messages: + messages: + started: Import démarré + completed: Import achevé avec succès + failed: Import interromptu + severities: + info: Information + warning: Alerte + error: Erreur activerecord: models: import: @@ -36,3 +71,8 @@ fr: attributes: import: resources: Fichier à importer + status: Status + import_log_message: + created_at: Date + position: "No" + full_message: Message diff --git a/db/migrate/20120529154848_create_import_log_messages.rb b/db/migrate/20120529154848_create_import_log_messages.rb new file mode 100644 index 000000000..b39a9eda7 --- /dev/null +++ b/db/migrate/20120529154848_create_import_log_messages.rb @@ -0,0 +1,14 @@ +class CreateImportLogMessages < ActiveRecord::Migration + def change + create_table :import_log_messages do |t| + t.belongs_to :import + t.string :key + t.string :arguments + t.integer :position + t.string :severity + + t.timestamps + end + add_index :import_log_messages, :import_id + end +end diff --git a/db/schema.rb b/db/schema.rb index 86aebcd98..ed4c93693 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,7 +10,7 @@ # # It's strongly recommended to check this file into your version control system. -ActiveRecord::Schema.define(:version => 20120516172252) do +ActiveRecord::Schema.define(:version => 20120529154848) do create_table "company", :force => true do |t| t.string "objectid" @@ -70,6 +70,18 @@ ActiveRecord::Schema.define(:version => 20120516172252) do add_index "delayed_jobs", ["priority", "run_at"], :name => "delayed_jobs_priority" + create_table "import_log_messages", :force => true do |t| + t.integer "import_id" + t.string "key" + t.string "arguments" + t.integer "position" + t.string "severity" + t.datetime "created_at" + t.datetime "updated_at" + end + + add_index "import_log_messages", ["import_id"], :name => "index_import_log_messages_on_import_id" + create_table "imports", :force => true do |t| t.integer "referential_id" t.string "status" diff --git a/spec/factories.rb b/spec/factories.rb index b77102321..c5c1c0ff0 100644 --- a/spec/factories.rb +++ b/spec/factories.rb @@ -11,4 +11,14 @@ FactoryGirl.define do f.password_confirmation "secret" end + factory :import do |f| + f.resources { Rack::Test::UploadedFile.new 'spec/fixtures/neptune.zip', 'application/zip', false } + f.association :referential + end + + factory :import_log_message do |f| + f.association :import + f.sequence(:key) { "key_#{n}" } + end + end diff --git a/spec/fixtures/neptune.zip b/spec/fixtures/neptune.zip Binary files differnew file mode 100644 index 000000000..86b688b51 --- /dev/null +++ b/spec/fixtures/neptune.zip diff --git a/spec/models/import_log_message_spec.rb b/spec/models/import_log_message_spec.rb new file mode 100644 index 000000000..dab951255 --- /dev/null +++ b/spec/models/import_log_message_spec.rb @@ -0,0 +1,16 @@ +require 'spec_helper' + +describe ImportLogMessage do + + describe "#attributes" do + + subject { create :import_log_message } + + it "should read json stored in database" do + subject.update_attribute :arguments, { "key" => "value"} + subject.raw_attributes.should == { "key" => "value"}.to_json + end + + end + +end diff --git a/spec/models/import_spec.rb b/spec/models/import_spec.rb index 734445b8b..f307b59db 100644 --- a/spec/models/import_spec.rb +++ b/spec/models/import_spec.rb @@ -1,7 +1,37 @@ require 'spec_helper' describe Import do + + subject { create :import } + + RSpec::Matchers.define :be_log_message do |expected| + match do |actual| + actual and expected.all? { |k,v| actual[k.to_s] == v } + end + end - + describe "#import" do + + before(:each) do + subject.stub :loader => mock(:import => true) + end + + it "should create a ImportLogmessage :started when started" do + subject.import + subject.log_messages.first.should be_log_message(:key => "started") + end + + it "should create a ImportLogmessage :completed when completed" do + subject.import + subject.log_messages.last.should be_log_message(:key => "completed") + end + + it "should create a ImportLogmessage :failed when failed" do + subject.loader.stub(:import).and_raise("import failed") + subject.import + subject.log_messages.last.should be_log_message(:key => "failed") + end + + end end |
