assetable 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (83) hide show
  1. checksums.yaml +15 -0
  2. data/MIT-LICENSE +20 -0
  3. data/README.rdoc +181 -0
  4. data/Rakefile +23 -0
  5. data/app/assets/images/assetable/icon-upload.png +0 -0
  6. data/app/assets/images/assetable/icons/icon-ai.png +0 -0
  7. data/app/assets/images/assetable/icons/icon-css.png +0 -0
  8. data/app/assets/images/assetable/icons/icon-desmos.png +0 -0
  9. data/app/assets/images/assetable/icons/icon-doc.png +0 -0
  10. data/app/assets/images/assetable/icons/icon-document.png +0 -0
  11. data/app/assets/images/assetable/icons/icon-docx.png +0 -0
  12. data/app/assets/images/assetable/icons/icon-eps.png +0 -0
  13. data/app/assets/images/assetable/icons/icon-flash.png +0 -0
  14. data/app/assets/images/assetable/icons/icon-html.png +0 -0
  15. data/app/assets/images/assetable/icons/icon-jpg.png +0 -0
  16. data/app/assets/images/assetable/icons/icon-js.png +0 -0
  17. data/app/assets/images/assetable/icons/icon-mov.png +0 -0
  18. data/app/assets/images/assetable/icons/icon-mp3.png +0 -0
  19. data/app/assets/images/assetable/icons/icon-mp4.png +0 -0
  20. data/app/assets/images/assetable/icons/icon-pdf.png +0 -0
  21. data/app/assets/images/assetable/icons/icon-php.png +0 -0
  22. data/app/assets/images/assetable/icons/icon-png.png +0 -0
  23. data/app/assets/images/assetable/icons/icon-ppt.png +0 -0
  24. data/app/assets/images/assetable/icons/icon-pptx.png +0 -0
  25. data/app/assets/images/assetable/icons/icon-txt.png +0 -0
  26. data/app/assets/images/assetable/icons/icon-xls.png +0 -0
  27. data/app/assets/images/assetable/icons/icon-xlsx.png +0 -0
  28. data/app/assets/images/assetable/icons/icon-xml.png +0 -0
  29. data/app/assets/javascripts/assetable/asset_gallery.js.coffee +74 -0
  30. data/app/assets/javascripts/assetable/assetable_uploader.js.coffee +204 -0
  31. data/app/assets/javascripts/assetable/gallery.js.coffee +33 -0
  32. data/app/assets/javascripts/assetable/uploader.js.coffee +10 -0
  33. data/app/assets/javascripts/vendor/bootstrap-modal.js +246 -0
  34. data/app/assets/javascripts/vendor/jquery-ui-1.10.3.custom.js +2252 -0
  35. data/app/assets/stylesheets/assetable/_assetable.css.sass +9 -0
  36. data/app/assets/stylesheets/assetable/_bootstrap.css.sass +5 -0
  37. data/app/assets/stylesheets/assetable/components/_buttons.css.sass +99 -0
  38. data/app/assets/stylesheets/assetable/components/_close.css.sass +28 -0
  39. data/app/assets/stylesheets/assetable/components/_forms.css.sass +219 -0
  40. data/app/assets/stylesheets/assetable/components/_gallery.css.sass +118 -0
  41. data/app/assets/stylesheets/assetable/components/_modals.css.sass +116 -0
  42. data/app/assets/stylesheets/assetable/components/_progress.css.sass +91 -0
  43. data/app/assets/stylesheets/assetable/components/_uploader.css.sass +175 -0
  44. data/app/assets/stylesheets/assetable/core/_mixins.css.sass +754 -0
  45. data/app/assets/stylesheets/assetable/core/_utilities.css.sass +5 -0
  46. data/app/assets/stylesheets/assetable/core/_variables.css.sass +165 -0
  47. data/app/controllers/assetable/assets_controller.rb +38 -0
  48. data/app/controllers/assetable/external_services_controller.rb +36 -0
  49. data/app/models/asset.rb +53 -0
  50. data/app/models/asset_attachment.rb +4 -0
  51. data/app/models/document.rb +5 -0
  52. data/app/models/external_service.rb +14 -0
  53. data/app/models/gallery.rb +7 -0
  54. data/app/models/image.rb +5 -0
  55. data/app/models/video.rb +5 -0
  56. data/app/uploaders/document_uploader.rb +50 -0
  57. data/app/uploaders/image_uploader.rb +67 -0
  58. data/app/uploaders/video_uploader.rb +40 -0
  59. data/app/views/assetable/assets/_asset.html.haml +20 -0
  60. data/app/views/assetable/assets/_gallery.html.haml +12 -0
  61. data/app/views/assetable/external_services/new.html.haml +31 -0
  62. data/config/initializers/carrierwave.rb +6 -0
  63. data/config/initializers/gallery_input.rb +37 -0
  64. data/config/initializers/uploader_input.rb +80 -0
  65. data/config/routes.rb +8 -0
  66. data/db/migrate/20131122232735_create_assets.rb +19 -0
  67. data/db/migrate/20131123172825_create_asset_attachments.rb +15 -0
  68. data/db/migrate/20131125200943_create_galleries.rb +14 -0
  69. data/lib/assetable.rb +18 -0
  70. data/lib/assetable/config.rb +23 -0
  71. data/lib/assetable/core.rb +41 -0
  72. data/lib/assetable/engine.rb +15 -0
  73. data/lib/assetable/version.rb +3 -0
  74. data/lib/tasks/assetable_tasks.rake +4 -0
  75. data/test/fixtures/asset_attachments.yml +11 -0
  76. data/test/fixtures/assets.yml +11 -0
  77. data/test/fixtures/images.yml +11 -0
  78. data/test/fixtures/videos.yml +11 -0
  79. data/test/models/asset_attachment_test.rb +7 -0
  80. data/test/models/asset_test.rb +7 -0
  81. data/test/models/image_test.rb +7 -0
  82. data/test/models/video_test.rb +7 -0
  83. metadata +371 -0
@@ -0,0 +1,40 @@
1
+ class VideoUploader < CarrierWave::Uploader::Base
2
+
3
+ storage Assetable.storage
4
+
5
+ # Override the directory where uploaded files will be stored.
6
+ # This is a sensible default for uploaders that are meant to be mounted:
7
+ def store_dir
8
+ if model.present?
9
+ "uploads/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}"
10
+ else
11
+ "uploads/#{mounted_as}"
12
+ end
13
+ end
14
+
15
+ # Create an MP4 version
16
+ # version :mp4 do
17
+ # process :encode_video => [:mp4, resolution: "1280x720", custom: "-preset medium"]
18
+ # end
19
+
20
+ # version :ogv, :from_version => :mp4 do
21
+ # process :encode_ogv => [resolution: :same]
22
+ # end
23
+
24
+ # # Create a thumbnail
25
+ # version :gallery_thumb do
26
+ # process thumbnail: [{format: 'jpg', quality: 10, size: "100x100", strip: true, logger: Rails.logger}]
27
+ # def full_filename for_file
28
+ # png_name for_file, version_name
29
+ # end
30
+ # end
31
+
32
+ def png_name for_file, version_name
33
+ %Q{#{version_name}_#{for_file.chomp(File.extname(for_file))}.jpg}
34
+ end
35
+
36
+ def default_url
37
+ ActionController::Base.helpers.asset_path("assetable/" + [version_name, "video.png"].compact.join('_'))
38
+ end
39
+
40
+ end
@@ -0,0 +1,20 @@
1
+ .uploader-preview
2
+
3
+ = link_to asset.filename.to_s, target: "_blank" do
4
+ - if asset.image?
5
+ = image_tag asset.filename.preview.to_s, class: "uploader-preview"
6
+ - elsif asset.document?
7
+ = image_tag "assetable/icons/icon-#{asset.extension}.png", class: "uploader-preview"
8
+ - elsif asset.video?
9
+ = image_tag "assetable/icons/icon-mp4.png", class: "uploader-preview"
10
+ - elsif asset.external_service?
11
+ = image_tag "assetable/icons/icon-document.png", class: "uploader-preview"
12
+
13
+ %span.uploader-name= asset.name
14
+ .uploader-size-and-actions
15
+ %span.uploader-size= number_to_human_size(asset.file_size)
16
+ .uploader-actions
17
+ = link_to "delete", "#", class: "btn-uploader btn-uploader-remove-asset"
18
+ = link_to "edit", "#", class: "btn-uploader btn-uploader-edit-asset"
19
+
20
+ = hidden_field_tag(fieldname, asset.id)
@@ -0,0 +1,12 @@
1
+ .assetable-gallery-header
2
+ %h3 Gallery
3
+ = link_to "&times;".html_safe, "#", class: "pull-right btn-close-assetable-gallery"
4
+
5
+ .assetable-gallery
6
+ = render partial: 'asset', collection: assets, locals: {fieldname: fieldname}
7
+
8
+ .assetable-gallery-footer
9
+ .assetable-gallery-paginate.pull-left
10
+ = paginate assets, remote: true
11
+ .pull-right
12
+ = link_to "insert asset", "#", class: "btn btn-primary btn-insert-asset"
@@ -0,0 +1,31 @@
1
+ .assetable-external-services.assetable-modal.modal.fade
2
+ .modal-dialog
3
+ .modal-content
4
+ = form_for [:assetable, @external_service], remote: true do |f|
5
+ .modal-header
6
+ %button.close{"aria-hidden" => "true", "data-dismiss" => "modal", type: "button"} ×
7
+ %h4.modal-title Third Party Service
8
+ .modal-body
9
+
10
+ = hidden_field_tag :fieldname, params[:fieldname]
11
+
12
+ .form-group
13
+ = f.label :name
14
+ = f.text_field :name, class: "form-control inpu-fluid", required: true
15
+ .form-group
16
+ = f.label :content_type
17
+ = f.select :content_type, ExternalService.possible_content_types
18
+ .form-group
19
+ = f.label :body
20
+ = f.text_area :body, class: "form-control input-fluid", required: true
21
+ .form-group.row
22
+ .col-xs-6
23
+ = f.label :width
24
+ = f.number_field :width, class: "form-control input-fluid"
25
+ .col-xs-6
26
+ = f.label :height
27
+ = f.number_field :height, class: "form-control input-fluid"
28
+
29
+ .modal-footer
30
+ = button_tag "Cancel", class: "btn btn-default", :'data-dismiss' => "modal", type: "button"
31
+ = f.submit "Add Third Party Service", class: "btn btn-primary"
@@ -0,0 +1,6 @@
1
+ if Rails.env.test? or Rails.env.cucumber?
2
+ CarrierWave.configure do |config|
3
+ config.storage = :file
4
+ config.enable_processing = false
5
+ end
6
+ end
@@ -0,0 +1,37 @@
1
+ class ActionView::Helpers::FormBuilder
2
+
3
+ include ActionView::Helpers::Tags
4
+ include ActionView::Helpers::TagHelper
5
+ include ActionView::Helpers::FormTagHelper
6
+ include ActionView::Helpers::FormOptionsHelper
7
+ include ActionView::Helpers::CaptureHelper
8
+ include ActionView::Helpers::AssetTagHelper
9
+ include ActionView::Helpers::NumberHelper
10
+
11
+ def gallery method, options = {}
12
+ # Build the association
13
+ @object.send("build_#{method}") unless @object.present? and @object.send(method).present?
14
+ # ID of the input wrapper
15
+ options[:id] = field_id(method, options[:index])
16
+ # The fieldname for the association
17
+ fieldname = @object_name + "[#{method}_attributes][asset_ids][]"
18
+
19
+ # Add the asset preview or the empty preview div
20
+ if gallery = @object.send(method)
21
+ asset_preview = ""
22
+ gallery.assets.each do |a|
23
+ asset_preview += asset_html(a, fieldname)
24
+ end
25
+ else
26
+ asset_preview = content_tag(:div, "", class: "uploader-preview")
27
+ end
28
+
29
+ # Uploader HTML with the asset previews and actions
30
+ uploader_html = content_tag(:div, (asset_preview.html_safe), class: "uploadar-data-wrapper")
31
+
32
+ # Wrap the previews and uploader in a div
33
+ uploader_wrapper = content_tag(:div, uploader_html, class: "gallery-uploader", id: options[:id], :'data-uploader-input-name' => fieldname)
34
+ return uploader_wrapper
35
+ end
36
+
37
+ end
@@ -0,0 +1,80 @@
1
+ class ActionView::Helpers::FormBuilder
2
+
3
+ include ActionView::Helpers::TagHelper
4
+ include ActionView::Helpers::FormTagHelper
5
+ include ActionView::Helpers::FormOptionsHelper
6
+ include ActionView::Helpers::CaptureHelper
7
+ include ActionView::Helpers::AssetTagHelper
8
+ include ActionView::Helpers::NumberHelper
9
+
10
+ def uploader method, options = {}
11
+ # add an ID to the options
12
+ options[:id] = field_id(method, options[:index]) unless options[:id].present?
13
+
14
+ # Set the fieldname
15
+ fieldname = @object_name + "[#{method}_association_attributes][asset_id]"
16
+
17
+ # Create the uploader
18
+ value = @object.nil? ? nil : @object.send(method)
19
+
20
+ # Add the asset preview or the empty preview div
21
+ if asset = asset_record(method)
22
+ asset_preview = asset_html(asset, fieldname)
23
+ else
24
+ asset_preview = content_tag(:div, "", class: "uploader-preview")
25
+ end
26
+
27
+ # uploaer html with preview and input
28
+ uploader_html = content_tag(:div, (asset_preview), class: "uploader-data-wrapper")
29
+
30
+ # Create and return the uploader html
31
+ uploader_wrapper = content_tag(:div, uploader_html, class: "uploader #{'uploader-has-asset' if asset} #{options[:class]}", id: options[:id], :'data-uploader-input-name' => fieldname)
32
+ return uploader_wrapper
33
+ end
34
+
35
+
36
+ # Convenience method to create the asset html
37
+ def asset_html asset, fieldname
38
+ image_tag = asset_preview_image(asset)
39
+ asset_name = content_tag(:span, asset.name.to_s, class: "uploader-name")
40
+ asset_size = content_tag(:span, number_to_human_size(asset.file_size.to_s), class: "uploader-size")
41
+ asset_size_and_actions = content_tag(:div, (asset_size + asset_actions), class: "uploader-size-and-actions")
42
+ field = hidden_field_tag(fieldname, (asset.id))
43
+ return content_tag(:div, (image_tag + asset_name + asset_size_and_actions + field), class: "uploader-preview")
44
+ end
45
+
46
+ # Asset preview image or fallback to a content type image
47
+ def asset_preview_image asset
48
+ if asset.image?
49
+ preview_image_tag = image_tag(asset.filename.preview.to_s, class: "uploader-preview")
50
+ elsif asset.document?
51
+ preview_image_tag = image_tag(ActionController::Base.helpers.asset_path("assetable/icons/icon-#{asset.extension}.png"), class: "uploader-preview")
52
+ elsif asset.video?
53
+ preview_image_tag = image_tag(ActionController::Base.helpers.asset_path("assetable/icons/icon-mp4.png"), class: "uploader-preview")
54
+ elsif asset.external_service?
55
+ preview_image_tag = image_tag(ActionController::Base.helpers.asset_path("assetable/icons/icon-document.png"), class: "uploader-preview")
56
+ end
57
+
58
+ return link_to preview_image_tag, asset.filename.to_s, target: "_blank"
59
+ end
60
+
61
+ # Asset actions, i.e.e remove and edit buttons
62
+ def asset_actions
63
+ remove_btn = link_to "delete", "#", class: "btn-uploader btn-uploader-remove-asset"
64
+ edit_btn = link_to "edit", "#", class: "btn-uploader btn-uploader-edit-asset"
65
+ content_tag(:div, (remove_btn + edit_btn), class: "uploader-actions")
66
+ end
67
+
68
+ # Get the asset record, if it's a belongs_to assocation, then we
69
+ # can grab the actual record
70
+ def asset_record method
71
+ @object.send(method) rescue nil
72
+ end
73
+
74
+ # Get the field id
75
+ def field_id label, index=nil
76
+ output = index ? "_#{index}" : ''
77
+ return @object_name + output + "_#{label}"
78
+ end
79
+
80
+ end
data/config/routes.rb ADDED
@@ -0,0 +1,8 @@
1
+ Rails.application.routes.draw do
2
+
3
+ namespace :assetable do
4
+ resources :assets
5
+ resources :external_services
6
+ end
7
+
8
+ end
@@ -0,0 +1,19 @@
1
+ class CreateAssets < ActiveRecord::Migration
2
+ def change
3
+ create_table :assets do |t|
4
+ t.string :type
5
+ t.string :name
6
+ t.text :body
7
+ t.string :filename
8
+ t.string :checksum
9
+ t.string :path
10
+ t.string :content_type
11
+ t.integer :file_size
12
+ t.integer :width
13
+ t.integer :height
14
+ t.integer :duration
15
+ t.integer :bit_rate
16
+ t.timestamps
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,15 @@
1
+ class CreateAssetAttachments < ActiveRecord::Migration
2
+ def change
3
+ create_table :asset_attachments do |t|
4
+ t.references :asset
5
+ t.references :assetable, :polymorphic => true
6
+ t.string :name
7
+ t.timestamps
8
+ end
9
+
10
+ add_index :asset_attachments, :asset_id
11
+ add_index :asset_attachments, [:assetable_type, :assetable_id]
12
+ add_index :asset_attachments, [:assetable_type, :assetable_id, :name], unique: true, name: "named_asset"
13
+ add_index :asset_attachments, :assetable_id
14
+ end
15
+ end
@@ -0,0 +1,14 @@
1
+ class CreateGalleries < ActiveRecord::Migration
2
+ def change
3
+ create_table :galleries do |t|
4
+ t.references :galleryable, :polymorphic => true
5
+ t.string :name
6
+ t.timestamps
7
+ end
8
+
9
+ add_index :galleries, [:galleryable_type, :galleryable_id]
10
+ add_index :galleries, [:galleryable_type, :galleryable_id, :name], unique: true, name: "named_gallery"
11
+
12
+ add_index :galleries, :galleryable_id
13
+ end
14
+ end
data/lib/assetable.rb ADDED
@@ -0,0 +1,18 @@
1
+ require "carrierwave"
2
+ require "fog"
3
+ require "plupload-rails"
4
+ require "kaminari"
5
+
6
+ require "haml-rails"
7
+ require "sass-rails"
8
+ require "jquery-rails"
9
+
10
+ require "assetable/core"
11
+ require "assetable/engine"
12
+ require "assetable/config"
13
+
14
+ module Assetable
15
+
16
+ extend Config
17
+
18
+ end
@@ -0,0 +1,23 @@
1
+ module Assetable
2
+ module Config
3
+
4
+ VALID_OPTION_KEYS = [
5
+ :storage,
6
+ :external_document_types
7
+ ]
8
+
9
+ attr_accessor *VALID_OPTION_KEYS
10
+
11
+ def configure
12
+ yield self
13
+ self
14
+ end
15
+
16
+ def options
17
+ options = {}
18
+ VALID_OPTION_KEYS.each{ |pname| options[pname] = send(pname) }
19
+ options
20
+ end
21
+
22
+ end
23
+ end
@@ -0,0 +1,41 @@
1
+ module Assetable
2
+ module Core
3
+ extend ActiveSupport::Concern
4
+
5
+ included do
6
+ end
7
+
8
+ module ClassMethods
9
+ def assetable *args
10
+ if args.present?
11
+ args.each do |arg|
12
+ has_one :"#{arg}_association", -> { where(name: arg) }, class_name: "AssetAttachment", as: :assetable
13
+ has_one arg, through: :"#{arg}_association", source: :asset
14
+ accepts_nested_attributes_for :"#{arg}_association", allow_destroy: true
15
+ end
16
+ end
17
+ end
18
+
19
+ # Galleries
20
+ def galleryable *args
21
+ # By default, let's include a gallery.
22
+ unless args.include? :gallery
23
+ has_one :gallery, as: :galleryable, dependent: :destroy
24
+ accepts_nested_attributes_for :gallery
25
+ end
26
+
27
+ if args.present?
28
+ args.each do |arg|
29
+ has_one arg, -> { where(name: arg) }, class_name: "Gallery", as: :galleryable
30
+ accepts_nested_attributes_for arg
31
+ end
32
+ end
33
+ end
34
+ end
35
+
36
+ module InstanceMethods
37
+ end
38
+ end
39
+ end
40
+
41
+ ActiveRecord::Base.send :include, Assetable::Core
@@ -0,0 +1,15 @@
1
+ module Assetable
2
+ class Engine < ::Rails::Engine
3
+ config.generators.integration_tool :rspec
4
+ config.generators.test_framework :rspec
5
+
6
+ # Run the engine migrations with the main app rake task
7
+ initializer :append_migrations do |app|
8
+ unless app.root.to_s.match root.to_s
9
+ config.paths["db/migrate"].expanded.each do |expanded_path|
10
+ app.config.paths["db/migrate"] << expanded_path
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,3 @@
1
+ module Assetable
2
+ VERSION = "0.1.2"
3
+ end
@@ -0,0 +1,4 @@
1
+ # desc "Explaining what the task does"
2
+ # task :assetable do
3
+ # # Task goes here
4
+ # end
@@ -0,0 +1,11 @@
1
+ # Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
2
+
3
+ # This model initially had no columns defined. If you add columns to the
4
+ # model remove the '{}' from the fixture names and add the columns immediately
5
+ # below each fixture, per the syntax in the comments below
6
+ #
7
+ one: {}
8
+ # column: value
9
+ #
10
+ two: {}
11
+ # column: value
@@ -0,0 +1,11 @@
1
+ # Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
2
+
3
+ # This model initially had no columns defined. If you add columns to the
4
+ # model remove the '{}' from the fixture names and add the columns immediately
5
+ # below each fixture, per the syntax in the comments below
6
+ #
7
+ one: {}
8
+ # column: value
9
+ #
10
+ two: {}
11
+ # column: value