Skip to content
This repository has been archived by the owner on Dec 8, 2022. It is now read-only.

Commit

Permalink
Add support for Exports. Refs #41
Browse files Browse the repository at this point in the history
  • Loading branch information
Alban Peignier committed Jun 7, 2012
1 parent 1d72c64 commit 7c0ae62
Show file tree
Hide file tree
Showing 32 changed files with 563 additions and 6 deletions.
Binary file added app/assets/images/download-small.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added app/assets/images/export-completed.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added app/assets/images/export-failed.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added app/assets/images/export-pending.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
3 changes: 3 additions & 0 deletions app/assets/javascripts/exports.js.coffee
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://jashkenas.github.com/coffee-script/
3 changes: 3 additions & 0 deletions app/assets/stylesheets/common.css.scss
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,9 @@
a.remove {
background: url(image-path('user_interface/ui/remove-small.png')) no-repeat 0% 50%;
}
a.download {
background: url(image-path('download-small.png')) no-repeat 0% 50%;
}
}

p {
Expand Down
41 changes: 41 additions & 0 deletions app/assets/stylesheets/exports.css.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
// Place all the styles related to the Exports controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/

@import "common";

#workspace.exports.index
{
.export:after {
@include after_div_for_object;
}

.exports {
margin-top: 20px;
}

.exports:after {
@include content_to_clear;
}

.export {
@include div_for_object;

/* to create multi-column index */
width: 300px;
float: left;
padding-right: 10px;
}
}

#workspace.exports.show {
table {
th {
text-align: center;
font-style: italic;
}
td.message, td.created_at, td.position {
padding: 0 20px;
}
}
}
34 changes: 34 additions & 0 deletions app/controllers/exports_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
class ExportsController < ChouetteController

respond_to :html, :xml, :json
respond_to :zip, :only => :show

belongs_to :referential

def create
create! do |success, failure|
success.html { redirect_to referential_exports_path(@referential) }
end
end

def show
show! do |format|
format.zip { send_file @export.file, :type => :zip }
end
end


protected

# FIXME why #resource_id is nil ??
def build_resource
super.tap do |export|
export.referential_id = @referential.id
end
end

def collection
@exports ||= end_of_association_chain.paginate(:page => params[:page])
end

end
2 changes: 2 additions & 0 deletions app/helpers/exports_helper.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
module ExportsHelper
end
84 changes: 84 additions & 0 deletions app/models/export.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
class Export < ActiveRecord::Base

belongs_to :referential
validates_presence_of :referential_id

validates_inclusion_of :status, :in => %w{ pending completed failed }

has_many :log_messages, :class_name => "ExportLogMessage", :order => :position, :dependent => :destroy

serialize :options

def self.option(name)
name = name.to_s

define_method(name) do
self.options[name]
end

define_method("#{name}=") do |prefix|
self.options[name] = prefix
end
end

def options
read_attribute(:options) || write_attribute(:options, {})
end

@@root = "#{Rails.root}/tmp/exports"
cattr_accessor :root

after_destroy :destroy_file
def destroy_file
FileUtils.rm file if File.exists? file
end

def file
"#{root}/#{id}.zip"
end

def name
"#{self.class.model_name.human} #{id}"
end

def export_options
{ :export_id => self.id, :output_file => file }
end

before_validation :define_default_attributes, :on => :create
def define_default_attributes
self.status ||= "pending"
end

after_create :delayed_export
def delayed_export
delay.export
end

def export
FileUtils.mkdir_p root

begin
log_messages.create :key => :started

# TODO
# Make real export here

update_attribute :status, "completed"
rescue => e
Rails.logger.error "Export #{id} failed : #{e}, #{e.backtrace}"
update_attribute :status, "failed"
end

log_messages.create :key => status
end

def self.new(attributes = {}, options = {}, &block)
if self == Export
Object.const_get(attributes.delete(:type) || "NeptuneExport").new(attributes, options)
else
super
end
end

end
36 changes: 36 additions & 0 deletions app/models/export_log_message.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
class ExportLogMessage < ActiveRecord::Base
belongs_to :export

acts_as_list :scope => :export

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 => "export_log_messages.messages")
end
end
7 changes: 7 additions & 0 deletions app/models/neptune_export.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
class NeptuneExport < Export

def export_options
super.merge(:format => :neptune)
end

end
1 change: 1 addition & 0 deletions app/models/referential.rb
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ class Referential < ActiveRecord::Base
validates_format_of :prefix, :with => %r{\A[0-9a-zA-Z_]+\Z}

has_many :imports, :dependent => :destroy
has_many :exports, :dependent => :destroy

def human_attribute_name(*args)
self.class.human_attribute_name(*args)
Expand Down
14 changes: 14 additions & 0 deletions app/views/exports/_export.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<%= div_for(export, :class => :export) do %>
<%= link_to(referential_export_path(@referential, export), :class => "preview") do %>
<%= image_tag "export-#{export.status}.png" %>
<% end %>
<%= link_to(export.name, referential_export_path(@referential, export)) %>
<div class="info">
<%= l export.created_at %>

<div class="actions">
<%= link_to t("exports.actions.download"), referential_export_path(@referential, export, :format => :zip), :class => "download" %>
<%= link_to t("actions.destroy"), referential_export_path(@referential, export), :method => :delete, :confirm => t('exports.actions.destroy_confirm'), :class => "remove" %>
</div>
</div>
<% end %>
20 changes: 20 additions & 0 deletions app/views/exports/index.html.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
<%= title_tag t('.title') %>

<div class="pagination">
<div class="page_info">
<%= page_entries_info @exports %>
</div>
<%= will_paginate @exports, :container => false %>
</div>
<div class="exports paginated_content">
<%= render :partial => "export", :collection => @exports %>
</div>
<div class="pagination">
<%= will_paginate @exports, :container => false %>
</div>

<% content_for :sidebar do %>
<ul class="actions">
<li><%= link_to t('exports.actions.new'), new_referential_export_path(@referential), :class => "add" %></li>
</ul>
<% end %>
9 changes: 9 additions & 0 deletions app/views/exports/new.html.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<%= title_tag t(".title") %>

<%= semantic_form_for [@referential, @export], :as => :export, :url => referential_exports_path(@referential) do |form| %>
<%= form.buttons do %>
<%= form.commit_button true %>
<li><%= t('or') %></li>
<li><%= link_to t('cancel'), :back %></li>
<% end %>
<% end %>
39 changes: 39 additions & 0 deletions app/views/exports/show.html.erb
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
<%= title_tag @export.name %>

<div class="export_show">
<div class="summary">
<p>
<label><%= Export.human_attribute_name(:created_at) %>: </label>
<%= l @export.created_at %>
</p>
<p>
<label><%= Export.human_attribute_name(:status) %>: </label>
<%= t @export.status, :scope => "exports.statuses" %>
</p>
</div>

<h3><%= t(".report") %></h3>
<table>
<tr>
<th></th>
<th><%= ExportLogMessage.human_attribute_name(:created_at) %></th>
<th><%= ExportLogMessage.human_attribute_name(:position) %></th>
<th><%= ExportLogMessage.human_attribute_name(:full_message) %></th>
</tr>
<% @export.log_messages.each do |message| %>
<tr>
<td class="severity"><%= image_tag "severity-#{message.severity}.png", :alt => t(message.severity, :scope => "export_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('exports.actions.download'), referential_export_path(@referential, @export, :format => :zip), :class => "download" %></li>
<li><%= link_to t('exports.actions.destroy'), referential_export_path(@referential, @export), :method => :delete, :confirm => t('exports.actions.destroy_confirm'), :class => "remove" %></li>
</ul>
<% end %>
1 change: 1 addition & 0 deletions app/views/layouts/application.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@
<li><%= tab_link_to Chouette::TimeTable, referential_time_tables_path(@referential) %></li>

<li><%= tab_link_to Import, referential_imports_path(@referential) %></li>
<li><%= tab_link_to Export, referential_exports_path(@referential) %></li>
<% end %>
</ul>
</div>
Expand Down
2 changes: 1 addition & 1 deletion config/initializers/apartment.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
Apartment.configure do |config|
# set your options (described below) here
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
config.excluded_models = ["Referential", "User", "Import", "ImportLogMessage", "Export", "ExportLogMessage", "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) }
Expand Down
2 changes: 2 additions & 0 deletions config/initializers/mime_types.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,5 @@
# Add new mime types for use in respond_to blocks:
# Mime::Type.register "text/richtext", :rtf
# Mime::Type.register_alias "text/html", :iphone

Mime::Type.register "application/zip", :zip
Loading

0 comments on commit 7c0ae62

Please sign in to comment.