DEV Community

Chris Siku
Chris Siku

Posted on

Upload multiple images To Rails 7 API - Active_storage : Part 1

Image description

Uploading multiple images is a common task when building web applications.

With the release of Rails 5.2, we were introduced to Active Storage, a framework for managing file uploads to a cloud storage service or the local disk. In this blog post, we will walk through how to upload multiple images to a Rails 7 API using Active Storage.

In this blog post, we will go through the steps to upload multiple images to a Ruby on Rails 7 API using Active Storage, a framework for managing file uploads to a cloud storage service or the local disk.

This blog post is divided into 2 parts

Part 1 : Backend API whit Rails 7

Part 2 : Frontend with React.js

Part 1 : Backend API

  • First, we need to create a new Rails API application using the following command in your terminal:
rails new multiple-image-uploads --api -d postgresql 
Enter fullscreen mode Exit fullscreen mode
  • Then, navigate to the new application directory using the command
cd multiple-image-uploads
Enter fullscreen mode Exit fullscreen mode
  • Next, generate a Post model using scaffold. This model will be used to represent the posts that will contain the uploaded images:
rails g scaffold post
Enter fullscreen mode Exit fullscreen mode
  • After generating the Post model, we need to install Active Storage using the following command:
rails active_storage:install
Enter fullscreen mode Exit fullscreen mode

This command will create the necessary database tables and migration files to enable Active Storage.

  • Next, we need to update the Gemfile file to include two necessary gems: image_processing and rack-cors. Uncomment these gems and run bundle install to update all your gems.
# [...]
gem "image_processing"
gem "rack-cors"
Enter fullscreen mode Exit fullscreen mode
  • To allow all origins to access the API, update the cors.rb file under config/initializers:
Rails.application.config.middleware.insert_before 0, Rack::Cors do
  allow do
    origins "*"

    resource "*",
      headers: :any,
      methods: [:get, :post, :put, :patch, :delete, :options, :head]
  end
end
Enter fullscreen mode Exit fullscreen mode
  • Now that Active Storage is installed, we can set up the Active Storage association in the Post model. In the post.rb file under app/models/, add the following code:
class Post < ApplicationRecord
  has_many_attached :images
end
Enter fullscreen mode Exit fullscreen mode
  • With the association set up, we need to update the posts_controller.rb file to handle image uploads. Replace the contents of this file with the following code:
class PostsController < ApplicationController
  before_action :set_post, only: %i[show update destroy]

  # GET /posts
  def index
    @posts = Post.all

    render json: @posts
  end

  # GET /posts/1
  def show
    render json: @post.as_json(include: :images).merge(
      images: @post.images.map do |image|
        url_for(image)
      end,
    )
  end

  def create
    # The `Post` model should be defined or required in this file.
    @post = Post.new(post_params.except(:images))

    # The `save` method should be called after images have been attached.
    if @post.save
      images = params[:post][:images]

      if images
        images.each do |image|
          @post.images.attach(image)
        end
      end

      render json: @post, status: :created, location: @post
    else
      render json: @post.errors, status: :unprocessable_entity
    end
  end

  # PATCH/PUT /posts/1
  def update
    if @post.update(post_params)
      render json: @post
    else
      render json: @post.errors, status: :unprocessable_entity
    end
  end

  # DELETE /posts/1
  def destroy
    @post.destroy
  end

  private

  # Use callbacks to share common setup or constraints between actions.
  def set_post
    @post = Post.find(params[:id])
  end

  # Only allow a list of trusted parameters through.
  def post_params
    params.require(:post).permit(images: [])
  end
end

Enter fullscreen mode Exit fullscreen mode

The show action will return a JSON response of a specific post and its images. The as_json method is used to include the associated images with the post, and the merge method is used to add a new key-value pair images in the response JSON that contains an array of image URLs.

The create action creates a new post and attaches any images that were passed in the request parameters. The except method is used to remove the images parameter from the post_params hash, as it is handled separately in the images variable. The permit method is used to allow an array of image attachments to be passed in the request parameters.

The update action updates an existing post with the new parameters passed in the request. The save method is used to update the post with the new parameters, and the post_params method is passed in as an argument.

The destroy action deletes a specific post.

The set_post method is a private method that finds the post with the specified ID and assigns it to the instance variable @post.

The before_action method is used to call this method before the show, update, and destroy actions are executed.

  • Now we Confugure the database and make sure that the database.yml file under config/ directory looks like the following
default: &default
  adapter: postgresql
  encoding: unicode
  username: postgres
  password: 123456
  pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>

development:
  <<: *default
  database: multiple_image_uploads_development

  <<: *default
  database: multiple_image_uploads_test

production:
  <<: *default
  database: multiple_image_uploads_production
  username: multiple_image_uploads
  password: <%= ENV["MULTIPLE_IMAGE_UPLOADS_DATABASE_PASSWORD"] %>
Enter fullscreen mode Exit fullscreen mode

You can replace the username and password by you postgres host configuration

  • Create the database and run migrations
rails db:create db:migrate
Enter fullscreen mode Exit fullscreen mode
  • Now run the rails server
rails server
Enter fullscreen mode Exit fullscreen mode

The database.yml file under the config/ directory sets the default adapter to PostgreSQL, specifies the database encoding as Unicode, and sets the default pool size to 5 threads. The development and test environments use the same database configuration as the default, while the production environment uses a different database name and a custom username and password.

The rails db:create command creates the databases specified in the database.yml file, and the rails db:migrate command runs any pending migrations to update the database schema.

Finally, the rails server command starts the Rails server, which listens for incoming requests on localhost:3000 by default. With the database configured and the server running, the Rails application is ready to receive and respond to requests.

Overall, this code sets up a RESTful API for posts with image attachments, allowing clients to create, read, update, and delete posts with images.

⏮⏮ intro ________________________ part 2⏭⏭

Top comments (0)