diff --git a/Gemfile b/Gemfile index cb6fd18c..7e82755e 100644 --- a/Gemfile +++ b/Gemfile @@ -46,7 +46,7 @@ gem 'rubyzip' gem 'actionmailer-with-request', '~> 0.3.0', :require => 'actionmailer_with_request' gem 'httparty', '~> 0.8.1' gem 'delayed_job', '~> 3.0.0.pre4' -gem 'delayed_job_mongoid', '~> 1.0.6' +gem 'delayed_job_mongoid', '~> 1.0.7' gem 'SystemTimer', :platforms => :ruby_18 # The rest of the dependencies are for use when in the locomotive dev environment diff --git a/Gemfile.lock b/Gemfile.lock index 61a1d09a..137697ac 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -16,14 +16,6 @@ GIT carrierwave-mongoid (~> 0.1.3) mongoid (~> 2.3.3) -GIT - remote: git://github.com/nragaz/uploadify-rails.git - revision: 18353ceb8a8ed1b9839cc642d5806bcffb62eb15 - specs: - uploadify-rails (1.0.1) - railties (~> 3.0) - thor (~> 0.14) - GIT remote: git://github.com/plataformatec/devise.git revision: ede004169c6af7416f8c4e3fc29a653bee133f60 @@ -133,8 +125,8 @@ GEM delayed_job (3.0.0.pre4) activesupport (~> 3.0) daemons (= 1.0.10) - delayed_job_mongoid (1.0.6) - delayed_job (= 3.0.0.pre4) + delayed_job_mongoid (1.0.7) + delayed_job (~> 3.0.0.pre) mongoid (>= 2.0) diff-lcs (1.1.3) dragonfly (0.9.8) @@ -325,7 +317,7 @@ DEPENDENCIES custom_fields! database_cleaner delayed_job (~> 3.0.0.pre4) - delayed_job_mongoid (~> 1.0.6) + delayed_job_mongoid (~> 1.0.7) devise! dragonfly (~> 0.9.8) factory_girl_rails (~> 1.1) @@ -360,5 +352,4 @@ DEPENDENCIES tinymce-rails uglifier (~> 1.0.4) unicorn - uploadify-rails! xpath (~> 0.1.4) diff --git a/app/assets/javascripts/locomotive.js b/app/assets/javascripts/locomotive.js index 0efbc85e..b9085115 100644 --- a/app/assets/javascripts/locomotive.js +++ b/app/assets/javascripts/locomotive.js @@ -10,7 +10,6 @@ //= require underscore //= require handlebars //= require backbone -//= require uploadify //= require codemirror //= require tinymce-jquery //= require codemirror/overlay diff --git a/app/assets/javascripts/locomotive/views/import/new_view.js.coffee b/app/assets/javascripts/locomotive/views/import/new_view.js.coffee new file mode 100644 index 00000000..b8dfd304 --- /dev/null +++ b/app/assets/javascripts/locomotive/views/import/new_view.js.coffee @@ -0,0 +1,13 @@ +Locomotive.Views.Import ||= {} + +class Locomotive.Views.Import.NewView extends Backbone.View + + el: '#content' + + render: -> + super() + + @enable_checkboxes() + + enable_checkboxes: -> + @$('.formtastic input[type=checkbox]').checkToggle() \ No newline at end of file diff --git a/app/controllers/locomotive/import_controller.rb b/app/controllers/locomotive/import_controller.rb index c5db218a..06ce9c2e 100644 --- a/app/controllers/locomotive/import_controller.rb +++ b/app/controllers/locomotive/import_controller.rb @@ -8,40 +8,18 @@ module Locomotive before_filter :authorize_import def show - @job = Delayed::Job.where({ :job_type => 'import', :site_id => current_site.id }).last - - respond_to do |format| - format.html do - redirect_to new_import_url if @job.nil? - end - format.json { render :json => { - :step => @job.nil? ? 'done' : @job.step, - :failed => @job && @job.last_error.present? - } } - end + @import = Locomotive::Import::Model.current(current_site) + respond_with @import end def new + @import = Locomotive::Import::Model.new + respond_with @import end def create - begin - Locomotive::Import::Job.run!(params[:zipfile], current_site, { - :samples => Boolean.set(params[:samples]), - :reset => Boolean.set(params[:reset]) - }) - - flash[:notice] = t("fash.locomotive.import.create.#{Locomotive.config.delayed_job ? 'notice' : 'done'}") - - redirect_to Locomotive.config.delayed_job ? import_url : new_import_url - rescue Exception => e - logger.error "[Locomotive import] #{e.message} / #{e.backtrace}" - - @error = e.message - flash[:alert] = t('fash.locomotive.import.create.alert') - - render 'new' - end + @import = Locomotive::Import::Model.create(params[:import].merge(:site => current_site)) + respond_with @import, :location => Locomotive.config.delayed_job ? import_url : new_import_url end protected @@ -52,3 +30,36 @@ module Locomotive end end + + +# begin +# Locomotive::Import::Job.run!(params[:zipfile], current_site, { +# :samples => Boolean.set(params[:samples]), +# :reset => Boolean.set(params[:reset]) +# }) +# +# flash[:notice] = t("fash.locomotive.import.create.#{Locomotive.config.delayed_job ? 'notice' : 'done'}") +# +# redirect_to Locomotive.config.delayed_job ? import_url : new_import_url +# rescue Exception => e +# logger.error "[Locomotive import] #{e.message} / #{e.backtrace}" +# +# @error = e.message +# flash[:alert] = t('fash.locomotive.import.create.alert') +# +# render 'new' +# end + +# def show +# @job = Delayed::Job.where({ :job_type => 'import', :site_id => current_site.id }).last +# +# respond_to do |format| +# format.html do +# redirect_to new_import_url if @job.nil? +# end +# format.json { render :json => { +# :step => @job.nil? ? 'done' : @job.step, +# :failed => @job && @job.last_error.present? +# } } +# end +# end \ No newline at end of file diff --git a/app/models/locomotive/page.rb b/app/models/locomotive/page.rb index 0fe7dffa..bfa28144 100644 --- a/app/models/locomotive/page.rb +++ b/app/models/locomotive/page.rb @@ -84,8 +84,12 @@ module Locomotive Locomotive::Liquid::Drops::Page.new(self) end + def to_presenter + Locomotive::PagePresenter.new(self) + end + def as_json(options = {}) - Locomotive::PagePresenter.new(self).as_json + self.to_presenter.as_json end protected diff --git a/app/models/locomotive/snippet.rb b/app/models/locomotive/snippet.rb index d5835721..22923321 100644 --- a/app/models/locomotive/snippet.rb +++ b/app/models/locomotive/snippet.rb @@ -26,8 +26,12 @@ module Locomotive ## methods ## + def to_presenter + Locomotive::SnippetPresenter.new(self) + end + def as_json(options = {}) - Locomotive::SnippetPresenter.new(self).as_json + self.to_presenter.as_json end protected diff --git a/app/presenters/locomotive/base_presenter.rb b/app/presenters/locomotive/base_presenter.rb index 648dad19..6f7e0c8f 100644 --- a/app/presenters/locomotive/base_presenter.rb +++ b/app/presenters/locomotive/base_presenter.rb @@ -30,9 +30,10 @@ class Locomotive::BasePresenter %w(id created_at updated_at) end - def as_json + def as_json(methods = nil) + methods ||= self.included_methods {}.tap do |hash| - self.included_methods.map(&:to_sym).each do |meth| + methods.map(&:to_sym).each do |meth| hash[meth] = self.send(meth) rescue nil end end diff --git a/app/presenters/locomotive/page_presenter.rb b/app/presenters/locomotive/page_presenter.rb index e0538ae0..1fe9c363 100644 --- a/app/presenters/locomotive/page_presenter.rb +++ b/app/presenters/locomotive/page_presenter.rb @@ -3,6 +3,10 @@ module Locomotive delegate :title, :slug, :fullpath, :raw_template, :published, :template_changed, :cache_strategy, :to => :source + def escaped_raw_template + h(self.source.raw_template) + end + def editable_elements self.source.enabled_editable_elements.collect(&:as_json) end @@ -11,5 +15,10 @@ module Locomotive super + %w(title slug fullpath raw_template published published cache_strategy template_changed editable_elements) end + def as_json_for_html_view + methods = included_methods.clone - %w(raw_template) + self.as_json(methods) + end + end end \ No newline at end of file diff --git a/app/presenters/locomotive/snippet_presenter.rb b/app/presenters/locomotive/snippet_presenter.rb index 3e2a6e30..4f58f3c1 100644 --- a/app/presenters/locomotive/snippet_presenter.rb +++ b/app/presenters/locomotive/snippet_presenter.rb @@ -11,5 +11,10 @@ module Locomotive super + %w(name slug template updated_at) end + def as_json_for_html_view + methods = included_methods.clone - %w(template) + self.as_json(methods) + end + end end \ No newline at end of file diff --git a/app/uploaders/locomotive/theme_asset_uploader.rb b/app/uploaders/locomotive/theme_asset_uploader.rb index a34e1157..1fad6743 100644 --- a/app/uploaders/locomotive/theme_asset_uploader.rb +++ b/app/uploaders/locomotive/theme_asset_uploader.rb @@ -18,7 +18,7 @@ module Locomotive end def self.build(site, path) - asset = ThemeAsset.new(:site => site, :folder => File.dirname(path)) + asset = site.theme_assets.build(:folder => File.dirname(path)) uploader = ThemeAssetUploader.new(asset) uploader.retrieve_from_store!(File.basename(path)) uploader diff --git a/app/views/locomotive/import/new.html.haml b/app/views/locomotive/import/new.html.haml index fe42ff81..e6827824 100644 --- a/app/views/locomotive/import/new.html.haml +++ b/app/views/locomotive/import/new.html.haml @@ -5,29 +5,11 @@ %p!= t('.help') -= form_tag import_url, :multipart => true, :class => 'formtastic import' do += semantic_form_for @import, :as => 'import', :url => import_url, :html => { :multipart => true } do |f| - %fieldset.inputs - %legend - %span= t('formtastic.titles.upload') - %ol - %li{ :class => "file #{'error' if @error} required" } - = label_tag 'zipfile', t('formtastic.labels.import.new.source') - = file_field_tag 'zipfile' - - if @error - .inline-errors - %p= @error - %p.inline-hints= t('formtastic.hints.import.source') + = f.inputs :name => :upload do + = f.input :source, :as => 'file' + = f.input :samples, :as => :'Locomotive::Toggle' + = f.input :reset, :as => :'Locomotive::Toggle' - %li.input.toggle - = label_tag 'samples', t('formtastic.labels.import.new.samples') - = check_box_tag 'samples' - %p.inline-hints= t('formtastic.hints.import.samples') - - %li.input.toggle - = label_tag 'reset', t('formtastic.labels.import.new.reset') - = check_box_tag 'reset' - %p.inline-hints= t('formtastic.hints.import.reset') - - - = render 'locomotive/shared/form_actions', :button_label => :send \ No newline at end of file + = render 'locomotive/shared/form_actions', :back_url => edit_current_site_url, :button_label => :create \ No newline at end of file diff --git a/app/views/locomotive/pages/_form.html.haml b/app/views/locomotive/pages/_form.html.haml index 1fe3431c..ae40dce1 100644 --- a/app/views/locomotive/pages/_form.html.haml +++ b/app/views/locomotive/pages/_form.html.haml @@ -6,7 +6,7 @@ - if @page.persisted? - content_for :backbone_view_data do :plain - { page: #{@page.to_json} } + { page: #{@page.to_presenter.as_json_for_html_view.to_json} } - if can?(:manage, @page) diff --git a/app/views/locomotive/snippets/_form.html.haml b/app/views/locomotive/snippets/_form.html.haml index 69890447..a46c89c0 100644 --- a/app/views/locomotive/snippets/_form.html.haml +++ b/app/views/locomotive/snippets/_form.html.haml @@ -3,7 +3,7 @@ - content_for :backbone_view_data do :plain - { snippet: #{@snippet.persisted? ? @snippet.to_json : 'null'} } + { snippet: #{@snippet.persisted? ? @snippet.to_presenter.as_json_for_html_view.to_json : 'null'} } = f.inputs :name => :information do = f.input :name, :wrapper_html => { :class => 'highlighted' } diff --git a/doc/TODO b/doc/TODO index b4166865..71a007c5 100644 --- a/doc/TODO +++ b/doc/TODO @@ -30,7 +30,8 @@ x edit my site x delete in ajax x upload many files at once - import/export - - QU + - export + - replace DJ by QU - site picker - content types - change in main menu diff --git a/lib/locomotive/delayed_job.rb b/lib/locomotive/delayed_job.rb index dacd27e3..e8806d7c 100644 --- a/lib/locomotive/delayed_job.rb +++ b/lib/locomotive/delayed_job.rb @@ -40,7 +40,8 @@ module Delayed class Job field :job_type field :step - referenced_in :site + field :site_id, :type => BSON::ObjectId + # referenced_in :site end end end diff --git a/lib/locomotive/engine.rb b/lib/locomotive/engine.rb index 4d3788bf..edb5315d 100644 --- a/lib/locomotive/engine.rb +++ b/lib/locomotive/engine.rb @@ -27,9 +27,5 @@ module Locomotive ActionController::Base.wrap_parameters :format => [:json] end - rake_tasks do - load "railties/tasks.rake" - end - end end diff --git a/lib/locomotive/import.rb b/lib/locomotive/import.rb index 2d42bee6..b407b799 100644 --- a/lib/locomotive/import.rb +++ b/lib/locomotive/import.rb @@ -1,5 +1,6 @@ require 'locomotive/import/logger' require 'locomotive/import/base' +require 'locomotive/import/model' require 'locomotive/import/job' require 'locomotive/import/site' require 'locomotive/import/assets' diff --git a/lib/locomotive/import/assets.rb b/lib/locomotive/import/assets.rb index 186782c2..7d295186 100644 --- a/lib/locomotive/import/assets.rb +++ b/lib/locomotive/import/assets.rb @@ -5,7 +5,7 @@ module Locomotive def process self.add_theme_assets - self.add_other_assets + self.add_content_assets end protected @@ -33,16 +33,16 @@ module Locomotive end end - def add_other_assets + def add_content_assets Dir[File.join(theme_path, 'public', 'samples', '*')].each do |asset_path| next if File.directory?(asset_path) self.log "other asset = #{asset_path}" - asset = site.assets.where(:source_filename => File.basename(asset_path)).first + asset = site.content_assets.where(:source_filename => File.basename(asset_path)).first - asset ||= self.site.assets.build + asset ||= self.site.content_assets.build asset.attributes = { :source => File.open(asset_path) } diff --git a/lib/locomotive/import/job.rb b/lib/locomotive/import/job.rb index 63e2cb43..9809b86d 100644 --- a/lib/locomotive/import/job.rb +++ b/lib/locomotive/import/job.rb @@ -7,7 +7,7 @@ module Locomotive include Logger def initialize(zipfile, site, options = {}) - @site = site + @site_id = site._id.to_s @options = { :reset => false, :samples => false, @@ -18,15 +18,20 @@ module Locomotive raise "Theme identifier not found" if @identifier.blank? - @uploader = nil # fix issue with Ruby 1.9.2 and serialization + # empty instance variables before serialization (issue with ruby 1.9.2) + @uploader = @site = nil end def before(worker) @worker = worker end + def site + @site ||= Locomotive::Site.find(@site_id) + end + def perform - self.log "theme identifier #{@identifier}" + self.log "theme identifier #{@identifier} / site_id #{@site_id}" self.unzip! @@ -34,7 +39,7 @@ module Locomotive context = { :database => @database, - :site => @site, + :site => self.site, :theme_path => @theme_path, :error => nil, :worker => @worker @@ -42,20 +47,22 @@ module Locomotive self.reset! if @options[:reset] - %w(site content_types content_assets snippets pages).each do |step| + # %w(site content_types content_assets snippets pages).each do |step| + %w(site assets snippets pages).each do |step| if @options[:enabled][step] != false "Locomotive::Import::#{step.camelize}".constantize.process(context, @options) @worker.update_attributes :step => step if @worker else self.log "skipping #{step}" end + sleep 10 # FIXME DEBUG PURPOSE end end def success(worker) self.log 'deleting original zip file' - uploader = self.get_uploader(@site) + uploader = self.get_uploader(self.site) uploader.retrieve_from_store!(@identifier) @@ -70,8 +77,7 @@ module Locomotive job = self.new(zipfile, site, options) if Locomotive.config.delayed_job - puts "delayed::JOB !" - Delayed::Job.enqueue job, { :site => site, :job_type => 'import' } + Delayed::Job.enqueue job, { :site_id => site._id, :job_type => 'import' } else job.perform end @@ -80,7 +86,7 @@ module Locomotive protected def themes_folder - File.join(Rails.root, 'tmp', 'themes', @site.id.to_s) + File.join(Rails.root, 'tmp', 'themes', self.site._id.to_s) end def prepare_folder @@ -92,7 +98,7 @@ module Locomotive def store_zipfile(zipfile) return nil if zipfile.blank? - uploader = self.get_uploader(@site) + uploader = self.get_uploader(self.site) begin if zipfile.is_a?(String) && zipfile =~ /^https?:\/\// @@ -109,7 +115,7 @@ module Locomotive end def retrieve_zipfile - uploader = self.get_uploader(@site) + uploader = self.get_uploader(self.site) uploader.retrieve_from_store!(@identifier) @@ -161,10 +167,10 @@ module Locomotive end def reset! - @site.pages.destroy_all - @site.content_assets.destroy_all - @site.theme_assets.destroy_all - @site.content_types.destroy_all + self.site.pages.destroy_all + self.site.content_assets.destroy_all + self.site.theme_assets.destroy_all + self.site.content_types.destroy_all end def get_uploader(site) diff --git a/lib/locomotive/import/model.rb b/lib/locomotive/import/model.rb new file mode 100644 index 00000000..50a1234d --- /dev/null +++ b/lib/locomotive/import/model.rb @@ -0,0 +1,70 @@ +module Locomotive + module Import + class Model + + include Logger + include ActiveModel::Validations + + ## fields ## + attr_accessor :site, :source, :reset, :samples, :enabled + + ## validation ## + validates :site, :source, :presence => true + + def initialize(attributes = {}) + attributes = HashWithIndifferentAccess.new(attributes) + self.site = attributes[:site] + self.source = attributes[:source] + self.reset = attributes[:reset] || false + self.samples = attributes[:samples] || false + self.enabled = attributes[:enabled] || {} + end + + def reset=(value) + @reset = Boolean.set(value) + end + + def samples=(value) + @samples = Boolean.set(value) + end + + ## methods ## + + def to_job + new Job() + end + + def to_key + ['import'] + end + + ## class methods ## + + def self.create(attributes = {}) + puts attributes.inspect + new(attributes).tap do |job| + if job.valid? + begin + self.launch!(job) + rescue Exception => e + job.log "#{e.message}\n#{e.backtrace}" + job.errors.add(:source, e.message) + end + end + end + end + + def self.launch!(job) + Locomotive::Import::Job.run! job.source, job.site, { + :reset => job.reset, + :enabled => job.enabled + } + end + + def self.name + 'Import' + end + + end + end +end \ No newline at end of file diff --git a/lib/locomotive/import/pages.rb b/lib/locomotive/import/pages.rb index 5280d11d..fe68c99d 100644 --- a/lib/locomotive/import/pages.rb +++ b/lib/locomotive/import/pages.rb @@ -64,12 +64,13 @@ module Locomotive attributes[:position] = attributes[:position].to_i # templatized ? - if content_type_slug = attributes.delete(:content_type) - attributes.merge!({ - :templatized => true, - :content_type => site.content_types.where(:slug => content_type_slug).first - }) - end + # TODO: DEBUG PURPOSE + # if content_type_slug = attributes.delete(:content_type) + # attributes.merge!({ + # :templatized => true, + # :content_type => site.content_types.where(:slug => content_type_slug).first + # }) + # end # redirection page ? attributes[:redirect] = true if attributes[:redirect_url].present? @@ -153,7 +154,7 @@ module Locomotive template.gsub!(/\/samples\/(.*\.[a-zA-Z0-9]{3})/) do |match| name = File.basename($1) - if asset = site.assets.where(:source_filename => name).first + if asset = site.content_assets.where(:source_filename => name).first asset.source.url else match diff --git a/lib/locomotive/railties/tasks.rake b/lib/locomotive/railties/tasks.rake deleted file mode 100644 index 9cf41ce4..00000000 --- a/lib/locomotive/railties/tasks.rake +++ /dev/null @@ -1,16 +0,0 @@ -# Re-definitions are appended to existing tasks - -# Embed tasks from Delayed_job - -namespace :jobs do - desc "Clear the delayed_job queue." - task :clear => :environment do - Delayed::Job.delete_all - end - - desc "Start a delayed_job worker." - task :work => :environment do - puts "Delayed::Job.new = #{Delayed::Job.new.inspect}" - ::Delayed::Worker.new(:min_priority => ENV['MIN_PRIORITY'], :max_priority => ENV['MAX_PRIORITY']).start - end -end \ No newline at end of file diff --git a/spec/dummy/config/initializers/locomotive.rb b/spec/dummy/config/initializers/locomotive.rb index 750e89b4..b238e434 100644 --- a/spec/dummy/config/initializers/locomotive.rb +++ b/spec/dummy/config/initializers/locomotive.rb @@ -42,7 +42,7 @@ Locomotive.configure do |config| # If you do not mind about importing theme without DelayedJob, disable it. # # Warning: this option is not used if you deploy on bushi.do and we set automatically the value to true. - config.delayed_job = false + config.delayed_job = true # false # configure how many items we display in sub menu in the "Contents" section. # config.lastest_items_nb = 5