From dd50144bcd4dbd605995123ab5afc99e40e9a630 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Fri, 30 Jun 2017 19:12:58 +0200 Subject: First sketching --- README.md | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) create mode 100644 README.md (limited to 'README.md') diff --git a/README.md b/README.md new file mode 100644 index 0000000000..fccaa2d2bb --- /dev/null +++ b/README.md @@ -0,0 +1,45 @@ +# Active File + +... + +## Example + +class Person < ApplicationRecord + has_one :avatar +end + +class Avatar < ApplicationRecord + belongs_to :person + belongs_to :image, class_name: 'ActiveFile::Blob' + + has_file :image +end + +avatar.image.url(expires_in: 5.minutes) + + +class ActiveFile::DownloadsController < ActionController::Base + def show + head :ok, ActiveFile::Blob.locate(params[:id]).download_headers + end +end + + +class AvatarsController < ApplicationController + def create + # @avatar = Avatar.create \ + # image: ActiveFile::Blob.save!(file_name: params.require(:name), content_type: request.content_type, data: request.body) + @avatar = Avatar.create! image: Avatar.image.extract_from(request) + end +end + + +class ProfilesController < ApplicationController + def update + @person.update! avatar: @person.avatar.update!(image: ) + end +end + +## License + +Google Sign-In for Rails is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From 8ec90d0b934d30c2e39626e0436fba13ad96f695 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sat, 1 Jul 2017 12:11:04 +0200 Subject: Update README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index fccaa2d2bb..737e47041f 100644 --- a/README.md +++ b/README.md @@ -4,6 +4,7 @@ ## Example +```ruby class Person < ApplicationRecord has_one :avatar end @@ -39,6 +40,7 @@ class ProfilesController < ApplicationController @person.update! avatar: @person.avatar.update!(image: ) end end +``` ## License -- cgit v1.2.3 From ceae303c49523193216bef1a5ceb82940fb083c2 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Mon, 3 Jul 2017 16:04:14 +0200 Subject: Fix reference --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 737e47041f..7a59bcd18d 100644 --- a/README.md +++ b/README.md @@ -44,4 +44,4 @@ end ## License -Google Sign-In for Rails is released under the [MIT License](https://opensource.org/licenses/MIT). +Active File is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From 571509ad12bf3bcb3190efd7494a38c4796302b8 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 13:06:29 +0200 Subject: Rename from ActiveFile to ActiveVault since activefile gem name was taken --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 7a59bcd18d..7b4c7f2aaa 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,7 @@ end class Avatar < ApplicationRecord belongs_to :person - belongs_to :image, class_name: 'ActiveFile::Blob' + belongs_to :image, class_name: 'ActiveVault::Blob' has_file :image end @@ -19,9 +19,9 @@ end avatar.image.url(expires_in: 5.minutes) -class ActiveFile::DownloadsController < ActionController::Base +class ActiveVault::DownloadsController < ActionController::Base def show - head :ok, ActiveFile::Blob.locate(params[:id]).download_headers + head :ok, ActiveVault::Blob.locate(params[:id]).download_headers end end @@ -29,7 +29,7 @@ end class AvatarsController < ApplicationController def create # @avatar = Avatar.create \ - # image: ActiveFile::Blob.save!(file_name: params.require(:name), content_type: request.content_type, data: request.body) + # image: ActiveVault::Blob.save!(file_name: params.require(:name), content_type: request.content_type, data: request.body) @avatar = Avatar.create! image: Avatar.image.extract_from(request) end end -- cgit v1.2.3 From f008fe3947e8f0ecd326efa18d14dd0363db93a1 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 13:09:01 +0200 Subject: Last name update --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 7b4c7f2aaa..5160acda56 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -# Active File +# Active Vault ... @@ -44,4 +44,4 @@ end ## License -Active File is released under the [MIT License](https://opensource.org/licenses/MIT). +Active Vault is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From aaf841518866b34d769d9a951a389d1eef70d6e7 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 15:18:50 +0200 Subject: Add attachments --- README.md | 17 +---------------- 1 file changed, 1 insertion(+), 16 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 5160acda56..a72c79948f 100644 --- a/README.md +++ b/README.md @@ -6,26 +6,11 @@ ```ruby class Person < ApplicationRecord - has_one :avatar -end - -class Avatar < ApplicationRecord - belongs_to :person - belongs_to :image, class_name: 'ActiveVault::Blob' - - has_file :image + has_file :avatar end avatar.image.url(expires_in: 5.minutes) - -class ActiveVault::DownloadsController < ActionController::Base - def show - head :ok, ActiveVault::Blob.locate(params[:id]).download_headers - end -end - - class AvatarsController < ApplicationController def create # @avatar = Avatar.create \ -- cgit v1.2.3 From c2dd4418f6c72358a54da48d7c30263180c69c71 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 16:28:45 +0200 Subject: Slim down examples --- README.md | 22 ++++++++++------------ 1 file changed, 10 insertions(+), 12 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index a72c79948f..7fc1e43e07 100644 --- a/README.md +++ b/README.md @@ -5,24 +5,22 @@ ## Example ```ruby -class Person < ApplicationRecord - has_file :avatar +class User < ApplicationRecord + has_one_attached :avatar end -avatar.image.url(expires_in: 5.minutes) +user.avatar.attach io: File.open("~/face.jpg"), filename: "avatar.jpg", content_type: "image/jpg" +user.avatar.exist? # => true -class AvatarsController < ApplicationController - def create - # @avatar = Avatar.create \ - # image: ActiveVault::Blob.save!(file_name: params.require(:name), content_type: request.content_type, data: request.body) - @avatar = Avatar.create! image: Avatar.image.extract_from(request) - end -end +user.avatar.purge +user.avatar.exist? # => false +user.image.url(expires_in: 5.minutes) # => /rails/blobs/ -class ProfilesController < ApplicationController +class AvatarsController < ApplicationController def update - @person.update! avatar: @person.avatar.update!(image: ) + Current.user.avatar.attach(params.require(:avatar)) + redirect_to Current.user end end ``` -- cgit v1.2.3 From 5492be52103d2237a8782a86f0f6f89d2fb5a06e Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 18:30:15 +0200 Subject: Bit further on the README --- README.md | 38 +++++++++++++++++++++++++++++++++++++- 1 file changed, 37 insertions(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 7fc1e43e07..4a554ac18f 100644 --- a/README.md +++ b/README.md @@ -1,9 +1,13 @@ # Active Vault -... +Active Vault makes it simple to upload and reference files in cloud sites, like Amazon S3 or Google Cloud Storage, +and attach those files to Active Records. It also provides a disk site for testing or local deployments, but the +focus is on cloud storage. ## Example +One attachment: + ```ruby class User < ApplicationRecord has_one_attached :avatar @@ -25,6 +29,38 @@ class AvatarsController < ApplicationController end ``` +Many attachments: + +```ruby +class Message < ApplicationRecord + has_many_attached :images +end + +<%= form_with model: @message do |form| %> + <%= form.text_field :title, placeholder: "Title" %>
+ <%= form.text_area :content %>

+ + <%= form.file_field :images, multiple: true %>
+ <%= form.submit %> +<% end %> + +class MessagesController < ApplicationController + def create + message = Message.create! params.require(:message).permit(:title, :content) + message.images.attach(params[:message][:images]) + redirect_to message + end +end +``` + +## Configuration + +Add `require "active_vault"` to config/application.rb and create a `config/initializers/active_vault_sites.rb` with the following: + +```ruby + +``` + ## License Active Vault is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From 54886cb7b0754fb4c09febf1b70dd6eae48995cf Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 18:44:58 +0200 Subject: Record outstanding todos --- README.md | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index 4a554ac18f..bb6e9c1e34 100644 --- a/README.md +++ b/README.md @@ -61,6 +61,17 @@ Add `require "active_vault"` to config/application.rb and create a `config/initi ``` +## Todos + +- Strip Download of its resposibilities and delete class +- Proper logging +- MirrorSite +- Read metadata via Marcel? +- Copy over migration to app via rake task +- Add Migrator to copy/move between sites +- Explore direct uploads to cloud +- Extract VerifiedKeyWithExpiration into Rails as a feature of MessageVerifier + ## License Active Vault is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From abda6d784eb0940b352cd28c28a3f3e87757a489 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Wed, 5 Jul 2017 18:57:45 +0200 Subject: Basic MirrorSite Still need to convert it to threading --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index bb6e9c1e34..97101c6099 100644 --- a/README.md +++ b/README.md @@ -65,7 +65,7 @@ Add `require "active_vault"` to config/application.rb and create a `config/initi - Strip Download of its resposibilities and delete class - Proper logging -- MirrorSite +- Convert MirrorSite to use threading - Read metadata via Marcel? - Copy over migration to app via rake task - Add Migrator to copy/move between sites -- cgit v1.2.3 From c624df326a4ef36919a5195a3c5509fab97dcba3 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 11:33:29 +0200 Subject: ActiveVault -> ActiveStorage MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Yaroslav agreed to hand over the gem name ❤️ --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 97101c6099..8803cd9f3b 100644 --- a/README.md +++ b/README.md @@ -19,7 +19,7 @@ user.avatar.exist? # => true user.avatar.purge user.avatar.exist? # => false -user.image.url(expires_in: 5.minutes) # => /rails/blobs/ +user.avatar.url(expires_in: 5.minutes) # => /rails/blobs/ class AvatarsController < ApplicationController def update @@ -55,7 +55,7 @@ end ## Configuration -Add `require "active_vault"` to config/application.rb and create a `config/initializers/active_vault_sites.rb` with the following: +Add `require "active_storage"` to config/application.rb and create a `config/initializers/active_storage_sites.rb` with the following: ```ruby -- cgit v1.2.3 From b3a9f3556dedb80cfa6336e6241d933baeb4f906 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 11:34:21 +0200 Subject: Update README with new name --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 8803cd9f3b..73602db219 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ -# Active Vault +# Active Storage -Active Vault makes it simple to upload and reference files in cloud sites, like Amazon S3 or Google Cloud Storage, +Active Storage makes it simple to upload and reference files in cloud sites, like Amazon S3 or Google Cloud Storage, and attach those files to Active Records. It also provides a disk site for testing or local deployments, but the focus is on cloud storage. @@ -74,4 +74,4 @@ Add `require "active_storage"` to config/application.rb and create a `config/ini ## License -Active Vault is released under the [MIT License](https://opensource.org/licenses/MIT). +Active Storage is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From 35d5bddabcd8f0eccc7de3ddf60431ea196508a1 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 12:22:44 +0200 Subject: Rename from Site to Service now that we're called Active Storage --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 73602db219..b768520756 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Active Storage -Active Storage makes it simple to upload and reference files in cloud sites, like Amazon S3 or Google Cloud Storage, -and attach those files to Active Records. It also provides a disk site for testing or local deployments, but the +Active Storage makes it simple to upload and reference files in cloud services, like Amazon S3 or Google Cloud Storage, +and attach those files to Active Records. It also provides a disk service for testing or local deployments, but the focus is on cloud storage. ## Example @@ -55,7 +55,7 @@ end ## Configuration -Add `require "active_storage"` to config/application.rb and create a `config/initializers/active_storage_sites.rb` with the following: +Add `require "active_storage"` to config/application.rb and create a `config/initializers/active_storage_services.rb` with the following: ```ruby @@ -65,10 +65,10 @@ Add `require "active_storage"` to config/application.rb and create a `config/ini - Strip Download of its resposibilities and delete class - Proper logging -- Convert MirrorSite to use threading +- Convert MirrorService to use threading - Read metadata via Marcel? - Copy over migration to app via rake task -- Add Migrator to copy/move between sites +- Add Migrator to copy/move between services - Explore direct uploads to cloud - Extract VerifiedKeyWithExpiration into Rails as a feature of MessageVerifier -- cgit v1.2.3 From 6129a63764a0ac3c81d7876db5d9a55d1c5c963c Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 13:58:43 +0200 Subject: Add task to install the migration needed --- README.md | 1 - 1 file changed, 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index b768520756..1f0f30098d 100644 --- a/README.md +++ b/README.md @@ -67,7 +67,6 @@ Add `require "active_storage"` to config/application.rb and create a `config/ini - Proper logging - Convert MirrorService to use threading - Read metadata via Marcel? -- Copy over migration to app via rake task - Add Migrator to copy/move between services - Explore direct uploads to cloud - Extract VerifiedKeyWithExpiration into Rails as a feature of MessageVerifier -- cgit v1.2.3 From 87ad273659ef261f51dafee4ca1cc097b9ffd1bd Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 15:02:09 +0200 Subject: Extract configuration into config/storage_configuration.yml --- README.md | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 1f0f30098d..b771629cd0 100644 --- a/README.md +++ b/README.md @@ -53,13 +53,12 @@ class MessagesController < ApplicationController end ``` -## Configuration +## Installation -Add `require "active_storage"` to config/application.rb and create a `config/initializers/active_storage_services.rb` with the following: - -```ruby - -``` +1. Add `require "active_storage"` to config/application.rb. +2. Run rails activestorage:install to create needed directories, migrations, and configuration. +3. Configure the storage service in config/environments/* with `config.active_storage.service = :local` + that references the services configured in config/storage_services.yml. ## Todos -- cgit v1.2.3 From 343a4b73084d563d21c86a4b03348e562ea6fe9d Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 15:39:10 +0200 Subject: There are two --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index b771629cd0..e4feab3984 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,7 @@ Active Storage makes it simple to upload and reference files in cloud services, and attach those files to Active Records. It also provides a disk service for testing or local deployments, but the focus is on cloud storage. -## Example +## Examples One attachment: -- cgit v1.2.3 From ef07687262716984db51c173a0378d1eb0664289 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 15:43:14 +0200 Subject: Escape commands and paths --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index e4feab3984..a3ae62f377 100644 --- a/README.md +++ b/README.md @@ -56,9 +56,9 @@ end ## Installation 1. Add `require "active_storage"` to config/application.rb. -2. Run rails activestorage:install to create needed directories, migrations, and configuration. -3. Configure the storage service in config/environments/* with `config.active_storage.service = :local` - that references the services configured in config/storage_services.yml. +2. Run `rails activestorage:install` to create needed directories, migrations, and configuration. +3. Configure the storage service in `config/environments/*` with `config.active_storage.service = :local` + that references the services configured in `config/storage_services.yml`. ## Todos -- cgit v1.2.3 From 37f7cf8daf0faaf90e6b5548244e6038097097b3 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 16:04:08 +0200 Subject: Documentation, yo! --- README.md | 1 + 1 file changed, 1 insertion(+) (limited to 'README.md') diff --git a/README.md b/README.md index a3ae62f377..bb14d9df0f 100644 --- a/README.md +++ b/README.md @@ -62,6 +62,7 @@ end ## Todos +- Document all the classes - Strip Download of its resposibilities and delete class - Proper logging - Convert MirrorService to use threading -- cgit v1.2.3 From 7bd2b3aaa2ec1133025473c78437482ff94c6ea9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Adrian=20Paca=C5=82a?= Date: Thu, 6 Jul 2017 15:23:00 +0100 Subject: Use correct syntax in erb block --- README.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index bb14d9df0f..ab01df471e 100644 --- a/README.md +++ b/README.md @@ -35,15 +35,19 @@ Many attachments: class Message < ApplicationRecord has_many_attached :images end +``` +```erb <%= form_with model: @message do |form| %> <%= form.text_field :title, placeholder: "Title" %>
<%= form.text_area :content %>

- + <%= form.file_field :images, multiple: true %>
<%= form.submit %> <% end %> +``` +```ruby class MessagesController < ApplicationController def create message = Message.create! params.require(:message).permit(:title, :content) -- cgit v1.2.3 From 8fb2e96724f8b4dc2da15312f5769578cb0f3372 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 17:25:40 +0200 Subject: Describe some of the design differences in AS --- README.md | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index ab01df471e..ecfc2ed170 100644 --- a/README.md +++ b/README.md @@ -4,6 +4,12 @@ Active Storage makes it simple to upload and reference files in cloud services, and attach those files to Active Records. It also provides a disk service for testing or local deployments, but the focus is on cloud storage. +## Compared to other storage solutions + +A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in `Blob` and `Attachment` models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses GlobalID to provide polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. + +These `Blob` models are intended to be immutable in spirit. One file, one blob. You can associate the same blob with multiple application models as well. And if you want to do transformations of a given `Blob`, the idea is that you'll simply create a new one, rather than attempt to mutate the existing (though of course you can delete that later if you don't need it). + ## Examples One attachment: -- cgit v1.2.3 From fbeec41e56e3767baf0810f7a0bed46e050a8044 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Thu, 6 Jul 2017 17:26:53 +0200 Subject: Link up main models --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index ecfc2ed170..7dde8b6926 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ focus is on cloud storage. ## Compared to other storage solutions -A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in `Blob` and `Attachment` models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses GlobalID to provide polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. +A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in [Blob](https://github.com/rails/activestorage/blob/master/lib/active_storage/blob.rb) and [Attachment](https://github.com/rails/activestorage/blob/master/lib/active_storage/attachment.rb) models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses GlobalID to provide polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. These `Blob` models are intended to be immutable in spirit. One file, one blob. You can associate the same blob with multiple application models as well. And if you want to do transformations of a given `Blob`, the idea is that you'll simply create a new one, rather than attempt to mutate the existing (though of course you can delete that later if you don't need it). -- cgit v1.2.3 From d3527bbdafbc2769320f30568011dd926a5eb1f5 Mon Sep 17 00:00:00 2001 From: Bradly Feeley Date: Thu, 6 Jul 2017 17:18:46 -0700 Subject: Fixing typo in Readme --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 7dde8b6926..06af5a5417 100644 --- a/README.md +++ b/README.md @@ -73,7 +73,7 @@ end ## Todos - Document all the classes -- Strip Download of its resposibilities and delete class +- Strip Download of its responsibilities and delete class - Proper logging - Convert MirrorService to use threading - Read metadata via Marcel? -- cgit v1.2.3 From 0e54b8be0546a4b575f4fe585f4da053cecf3c3d Mon Sep 17 00:00:00 2001 From: Marat Galiev Date: Fri, 7 Jul 2017 14:45:50 +0300 Subject: Update README.md For the first look It's obvious, but makes sense I think, and raises undefined method `active_storage' on migration run for example. --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 06af5a5417..08bd0844c2 100644 --- a/README.md +++ b/README.md @@ -65,7 +65,7 @@ end ## Installation -1. Add `require "active_storage"` to config/application.rb. +1. Add `require "active_storage"` to config/application.rb, after `require "rails/all"` line. 2. Run `rails activestorage:install` to create needed directories, migrations, and configuration. 3. Configure the storage service in `config/environments/*` with `config.active_storage.service = :local` that references the services configured in `config/storage_services.yml`. -- cgit v1.2.3 From 800e957abdd68fcfc7ee424711dc3f32e81c77b8 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sat, 8 Jul 2017 18:51:55 +0200 Subject: Add a brief roadmap section --- README.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 08bd0844c2..74a9581e6b 100644 --- a/README.md +++ b/README.md @@ -78,9 +78,13 @@ end - Convert MirrorService to use threading - Read metadata via Marcel? - Add Migrator to copy/move between services -- Explore direct uploads to cloud +- [Explore direct uploads to cloud](https://github.com/rails/activestorage/pull/19) - Extract VerifiedKeyWithExpiration into Rails as a feature of MessageVerifier +## Roadmap + +This separate repository is a staging ground for eventual inclusion in rails/rails prior to the Rails 5.2 release. It is not intended to be a long-term stand-alone repository. Compatibility with prior versions of Rails is not a development priority either. + ## License Active Storage is released under the [MIT License](https://opensource.org/licenses/MIT). -- cgit v1.2.3 From 7593b7704c60de37dfdea3fafd5def1db7a9258c Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sun, 9 Jul 2017 17:04:59 +0200 Subject: Proper logging is now in place --- README.md | 1 - 1 file changed, 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 74a9581e6b..625b960624 100644 --- a/README.md +++ b/README.md @@ -74,7 +74,6 @@ end - Document all the classes - Strip Download of its responsibilities and delete class -- Proper logging - Convert MirrorService to use threading - Read metadata via Marcel? - Add Migrator to copy/move between services -- cgit v1.2.3 From 986a71d26868d296f4c619df85909d1073b6c91f Mon Sep 17 00:00:00 2001 From: Dino Maric Date: Fri, 21 Jul 2017 15:14:07 +0200 Subject: Add instruction to install the gem from the master (#65) --- README.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 625b960624..27678a8fe1 100644 --- a/README.md +++ b/README.md @@ -65,9 +65,10 @@ end ## Installation -1. Add `require "active_storage"` to config/application.rb, after `require "rails/all"` line. -2. Run `rails activestorage:install` to create needed directories, migrations, and configuration. -3. Configure the storage service in `config/environments/*` with `config.active_storage.service = :local` +1. Add `gem "activestorage", git: "https://github.com/rails/activestorage.git"` to your Gemfile. +2. Add `require "active_storage"` to config/application.rb, after `require "rails/all"` line. +3. Run `rails activestorage:install` to create needed directories, migrations, and configuration. +4. Configure the storage service in `config/environments/*` with `config.active_storage.service = :local` that references the services configured in `config/storage_services.yml`. ## Todos -- cgit v1.2.3 From 2e9ff80e50fee0df6ea47d4d43a27c4505985b29 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Fri, 21 Jul 2017 16:49:00 -0500 Subject: Quick example of variants --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index 625b960624..48a33f8b3d 100644 --- a/README.md +++ b/README.md @@ -63,6 +63,13 @@ class MessagesController < ApplicationController end ``` +Variation of image attachment: + +```erb +<%# Hitting the variant URL will lazy transform the original blob and then redirect to its new service location %> +<%= image_tag url_for(user.avatar.variant(resize: "100x100")) %> +``` + ## Installation 1. Add `require "active_storage"` to config/application.rb, after `require "rails/all"` line. -- cgit v1.2.3 From 6ac4fec964e67cf3d7dfbf7726bff9b05aca522c Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Fri, 21 Jul 2017 16:50:23 -0500 Subject: Mention need for mini_magick with variants --- README.md | 1 + 1 file changed, 1 insertion(+) (limited to 'README.md') diff --git a/README.md b/README.md index 69166664f6..b56999cae7 100644 --- a/README.md +++ b/README.md @@ -77,6 +77,7 @@ Variation of image attachment: 3. Run `rails activestorage:install` to create needed directories, migrations, and configuration. 4. Configure the storage service in `config/environments/*` with `config.active_storage.service = :local` that references the services configured in `config/storage_services.yml`. +5. Optional: Add `gem "mini_magick"` to your Gemfile if you want to use variants. ## Todos -- cgit v1.2.3 From 347dc166324c108b4a9c25c5ab03222a2f42b1d0 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sun, 23 Jul 2017 13:19:32 -0500 Subject: VerifiedKeyWithExpiration no longer needed Thanks to rails/rails#29854! This does mean that we now depend on rails/rails master. --- README.md | 1 - 1 file changed, 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index b56999cae7..901d8f4f23 100644 --- a/README.md +++ b/README.md @@ -87,7 +87,6 @@ Variation of image attachment: - Read metadata via Marcel? - Add Migrator to copy/move between services - [Explore direct uploads to cloud](https://github.com/rails/activestorage/pull/19) -- Extract VerifiedKeyWithExpiration into Rails as a feature of MessageVerifier ## Roadmap -- cgit v1.2.3 From 5889560427e56cb40861c0d57582857386f7e8fd Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sun, 23 Jul 2017 13:26:52 -0500 Subject: Update the README with more explicit expectation setting --- README.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 901d8f4f23..9e4749b1c6 100644 --- a/README.md +++ b/README.md @@ -4,6 +4,12 @@ Active Storage makes it simple to upload and reference files in cloud services, and attach those files to Active Records. It also provides a disk service for testing or local deployments, but the focus is on cloud storage. +## Compatibility & Expectations + +Active Storage only works with the development version of Rails 5.2+ (as of July 19, 2017). This separate repository is a staging ground for the upcoming inclusion in rails/rails prior to the Rails 5.2 release. It is not intended to be a long-term stand-alone repository. + +Furthermore, this repository is likely to be in heavy flux prior to the merge to rails/rails. You're heartedly encouraged to follow along and even use Active Storage in this phase, but don't be surprised if the API suffers frequent breaking changes prior to the merge. + ## Compared to other storage solutions A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in [Blob](https://github.com/rails/activestorage/blob/master/lib/active_storage/blob.rb) and [Attachment](https://github.com/rails/activestorage/blob/master/lib/active_storage/attachment.rb) models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses GlobalID to provide polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. @@ -82,15 +88,9 @@ Variation of image attachment: ## Todos - Document all the classes -- Strip Download of its responsibilities and delete class - Convert MirrorService to use threading - Read metadata via Marcel? - Add Migrator to copy/move between services -- [Explore direct uploads to cloud](https://github.com/rails/activestorage/pull/19) - -## Roadmap - -This separate repository is a staging ground for eventual inclusion in rails/rails prior to the Rails 5.2 release. It is not intended to be a long-term stand-alone repository. Compatibility with prior versions of Rails is not a development priority either. ## License -- cgit v1.2.3 From e16d0c9ceacd771c99048385dc886c6026c7bc45 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sun, 23 Jul 2017 16:57:26 -0500 Subject: No more GlobalID --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 9e4749b1c6..c1bfe12b77 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ Furthermore, this repository is likely to be in heavy flux prior to the merge to ## Compared to other storage solutions -A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in [Blob](https://github.com/rails/activestorage/blob/master/lib/active_storage/blob.rb) and [Attachment](https://github.com/rails/activestorage/blob/master/lib/active_storage/attachment.rb) models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses GlobalID to provide polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. +A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in [Blob](https://github.com/rails/activestorage/blob/master/lib/active_storage/blob.rb) and [Attachment](https://github.com/rails/activestorage/blob/master/lib/active_storage/attachment.rb) models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. These `Blob` models are intended to be immutable in spirit. One file, one blob. You can associate the same blob with multiple application models as well. And if you want to do transformations of a given `Blob`, the idea is that you'll simply create a new one, rather than attempt to mutate the existing (though of course you can delete that later if you don't need it). -- cgit v1.2.3 From 2bbfaf0c9f6ad23cb2c64a917848ca180917ebe2 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Sun, 23 Jul 2017 16:58:09 -0500 Subject: Demonstrate preloading in example --- README.md | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index c1bfe12b77..8f340d7013 100644 --- a/README.md +++ b/README.md @@ -66,6 +66,11 @@ class MessagesController < ApplicationController message.images.attach(params[:message][:images]) redirect_to message end + + def show + # Use the built-in with_attached_images scope to avoid N+1 + @message = Message.find(params[:id]).with_attached_images + end end ``` -- cgit v1.2.3 From d0e90b4a9dc1accd4f1044fde0dd9a347cd0afcf Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Mon, 24 Jul 2017 11:14:29 -0500 Subject: Blob/Variant#url -> #service_url to emphasize this URL isn't to be public --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 8f340d7013..0022ba9c2b 100644 --- a/README.md +++ b/README.md @@ -31,7 +31,7 @@ user.avatar.exist? # => true user.avatar.purge user.avatar.exist? # => false -user.avatar.url(expires_in: 5.minutes) # => /rails/blobs/ +user.avatar.service_url(expires_in: 5.minutes) # => /rails/blobs/ class AvatarsController < ApplicationController def update -- cgit v1.2.3 From 3a5372d80cfc40d89b07e9c253401fd1b8d47956 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Mon, 24 Jul 2017 15:51:25 -0500 Subject: Flesh out the README a bit more --- README.md | 32 ++++++++++++++++++++++---------- 1 file changed, 22 insertions(+), 10 deletions(-) (limited to 'README.md') diff --git a/README.md b/README.md index 0022ba9c2b..72d03f46b5 100644 --- a/README.md +++ b/README.md @@ -4,11 +4,10 @@ Active Storage makes it simple to upload and reference files in cloud services, and attach those files to Active Records. It also provides a disk service for testing or local deployments, but the focus is on cloud storage. -## Compatibility & Expectations - -Active Storage only works with the development version of Rails 5.2+ (as of July 19, 2017). This separate repository is a staging ground for the upcoming inclusion in rails/rails prior to the Rails 5.2 release. It is not intended to be a long-term stand-alone repository. +Files can uploaded from the server to the cloud or directly from the client to the cloud. -Furthermore, this repository is likely to be in heavy flux prior to the merge to rails/rails. You're heartedly encouraged to follow along and even use Active Storage in this phase, but don't be surprised if the API suffers frequent breaking changes prior to the merge. +Image files can further more be transformed using on-demand variants for quality, aspect ratio, size, or any other +MiniMagick supported transformation. ## Compared to other storage solutions @@ -26,15 +25,16 @@ class User < ApplicationRecord end user.avatar.attach io: File.open("~/face.jpg"), filename: "avatar.jpg", content_type: "image/jpg" -user.avatar.exist? # => true +user.avatar.attached? # => true user.avatar.purge -user.avatar.exist? # => false +user.avatar.attached? # => false -user.avatar.service_url(expires_in: 5.minutes) # => /rails/blobs/ +url_for(user.avatar) # Generate a permanent URL for the blob, which upon access will redirect to a temporary service URL. class AvatarsController < ApplicationController def update + # params[:avatar] contains a ActionDispatch::Http::UploadedFile object Current.user.avatar.attach(params.require(:avatar)) redirect_to Current.user end @@ -61,6 +61,11 @@ end ```ruby class MessagesController < ApplicationController + def index + # Use the built-in with_attached_images scope to avoid N+1 + @messages = Message.all.with_attached_images + end + def create message = Message.create! params.require(:message).permit(:title, :content) message.images.attach(params[:message][:images]) @@ -68,8 +73,7 @@ class MessagesController < ApplicationController end def show - # Use the built-in with_attached_images scope to avoid N+1 - @message = Message.find(params[:id]).with_attached_images + @message = Message.find(params[:id]) end end ``` @@ -88,7 +92,15 @@ Variation of image attachment: 3. Run `rails activestorage:install` to create needed directories, migrations, and configuration. 4. Configure the storage service in `config/environments/*` with `config.active_storage.service = :local` that references the services configured in `config/storage_services.yml`. -5. Optional: Add `gem "mini_magick"` to your Gemfile if you want to use variants. +5. Optional: Add `gem "aws-sdk", "~> 2"` to your Gemfile if you want to use AWS S3. +6. Optional: Add `gem "google-cloud-storage", "~> 1.3"` to your Gemfile if you want to use Google Cloud Storage. +7. Optional: Add `gem "mini_magick"` to your Gemfile if you want to use variants. + +## Compatibility & Expectations + +Active Storage only works with the development version of Rails 5.2+ (as of July 19, 2017). This separate repository is a staging ground for the upcoming inclusion in rails/rails prior to the Rails 5.2 release. It is not intended to be a long-term stand-alone repository. + +Furthermore, this repository is likely to be in heavy flux prior to the merge to rails/rails. You're heartedly encouraged to follow along and even use Active Storage in this phase, but don't be surprised if the API suffers frequent breaking changes prior to the merge. ## Todos -- cgit v1.2.3 From 6dd82b84de08635d3178fa3916e153d78f03c6e1 Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Mon, 24 Jul 2017 16:00:24 -0500 Subject: Did that --- README.md | 1 - 1 file changed, 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 72d03f46b5..705659b9aa 100644 --- a/README.md +++ b/README.md @@ -104,7 +104,6 @@ Furthermore, this repository is likely to be in heavy flux prior to the merge to ## Todos -- Document all the classes - Convert MirrorService to use threading - Read metadata via Marcel? - Add Migrator to copy/move between services -- cgit v1.2.3 From 293db49b7f5969d11d5599f97bd968dbe64c7f8b Mon Sep 17 00:00:00 2001 From: Rolandas Barysas Date: Thu, 27 Jul 2017 18:47:26 +0300 Subject: Fix broken links in README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index 705659b9aa..328bf01672 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,7 @@ MiniMagick supported transformation. ## Compared to other storage solutions -A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in [Blob](https://github.com/rails/activestorage/blob/master/lib/active_storage/blob.rb) and [Attachment](https://github.com/rails/activestorage/blob/master/lib/active_storage/attachment.rb) models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. +A key difference to how Active Storage works compared to other attachment solutions in Rails is through the use of built-in [Blob](https://github.com/rails/activestorage/blob/master/app/models/active_storage/blob.rb) and [Attachment](https://github.com/rails/activestorage/blob/master/app/models/active_storage/attachment.rb) models (backed by Active Record). This means existing application models do not need to be modified with additional columns to associate with files. Active Storage uses polymorphic associations via the join model of `Attachment`, which then connects to the actual `Blob`. These `Blob` models are intended to be immutable in spirit. One file, one blob. You can associate the same blob with multiple application models as well. And if you want to do transformations of a given `Blob`, the idea is that you'll simply create a new one, rather than attempt to mutate the existing (though of course you can delete that later if you don't need it). -- cgit v1.2.3 From 6262891b5669716db7c46dcdcec685d2f55903b5 Mon Sep 17 00:00:00 2001 From: Javan Makhmali Date: Thu, 27 Jul 2017 19:47:03 -0400 Subject: Add JavaScript direct upload support (#81) --- README.md | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index 328bf01672..b127f87c5c 100644 --- a/README.md +++ b/README.md @@ -96,6 +96,44 @@ Variation of image attachment: 6. Optional: Add `gem "google-cloud-storage", "~> 1.3"` to your Gemfile if you want to use Google Cloud Storage. 7. Optional: Add `gem "mini_magick"` to your Gemfile if you want to use variants. +## Direct uploads + +Active Storage, with its included JavaScript library, supports uploading directly from the client to the cloud. + +### Direct upload installation + +1. Include `activestorage.js` in your application's JavaScript bundle. + + Using the asset pipeline: + ```js + //= require activestorage + ``` + Using the npm package: + ```js + import * as ActiveStorage from "activestorage" + ActiveStorage.start() + ``` +2. Annotate file inputs with the direct upload URL. + + ```ruby + <%= form.file_field :attachments, multiple: true, data: { direct_upload_url: rails_direct_uploads_url } %> + ``` +3. That's it! Uploads begin upon form submission. + +### Direct upload JavaScript events + +| Event name | Event target | Event data (`event.detail`) | Description | +| --- | --- | --- | --- | +| `direct-uploads:start` | `
` | None | A form containing files for direct upload fields was submit. | +| `direct-upload:initialize` | `` | `{id, file}` | Dispatched for every file after form submission. | +| `direct-upload:start` | `` | `{id, file}` | A direct upload is starting. | +| `direct-upload:before-blob-request` | `` | `{id, file, xhr}` | Before making a request to your application for direct upload metadata. | +| `direct-upload:before-storage-request` | `` | `{id, file, xhr}` | Before making a request to store a file. | +| `direct-upload:progress` | `` | `{id, file, progress}` | As requests to store files progress. | +| `direct-upload:error` | `` | `{id, file, error}` | An error occurred. An `alert` will display unless this event is canceled. | +| `direct-upload:end` | `` | `{id, file}` | A direct upload has ended. | +| `direct-uploads:end` | `` | None | All direct uploads have ended. | + ## Compatibility & Expectations Active Storage only works with the development version of Rails 5.2+ (as of July 19, 2017). This separate repository is a staging ground for the upcoming inclusion in rails/rails prior to the Rails 5.2 release. It is not intended to be a long-term stand-alone repository. -- cgit v1.2.3 From 696b8c6f43214ed4b9b79f36a9f68de0db19f1ee Mon Sep 17 00:00:00 2001 From: David Heinemeier Hansson Date: Fri, 28 Jul 2017 15:13:22 -0500 Subject: Add a direct_upload: true option to file_field_tag and Form#file_field Then users don't have to bother with manually referring to internal routes. --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'README.md') diff --git a/README.md b/README.md index b127f87c5c..4a5f03233d 100644 --- a/README.md +++ b/README.md @@ -116,7 +116,7 @@ Active Storage, with its included JavaScript library, supports uploading directl 2. Annotate file inputs with the direct upload URL. ```ruby - <%= form.file_field :attachments, multiple: true, data: { direct_upload_url: rails_direct_uploads_url } %> + <%= form.file_field :attachments, multiple: true, direct_upload: true %> ``` 3. That's it! Uploads begin upon form submission. -- cgit v1.2.3 From 12d944f7651f79541d9f55fc6900d7fe4e3c62bc Mon Sep 17 00:00:00 2001 From: Claudio B Date: Fri, 4 Aug 2017 15:55:24 -0700 Subject: Add Active Storage to README and release (#30065) Before we forget... --- README.md | 2 ++ 1 file changed, 2 insertions(+) (limited to 'README.md') diff --git a/README.md b/README.md index 8bd066cb27..ee0ee2019d 100644 --- a/README.md +++ b/README.md @@ -40,6 +40,8 @@ to generate and send emails; Active Job ([README](activejob/README.md)), a framework for declaring jobs and making them run on a variety of queueing backends; Action Cable ([README](actioncable/README.md)), a framework to integrate WebSockets with a Rails application; +Active Storage ([README](activestorage/README.md)), a library to attach cloud +and local files to Rails applications; and Active Support ([README](activesupport/README.rdoc)), a collection of utility classes and standard library extensions that are useful for Rails, and may also be used independently outside Rails. -- cgit v1.2.3