[Ting's笔记Day6]活用套件carrierwave gem:(1)在Rails实现图片上传功能

carrierwave是一款经典的图片上传套件,本篇的目标是先在本地端(development)的rails项目试成功gem。html

(预计中集的进度会练习怎么利用Amazone S3架设图片上传Host,git

并再下集远端(production)实做上传,敬请期待!)github

 

https://ithelp.ithome.com.tw/upload/images/20180904/20111177jA3W9YiK5l.pngweb

 

在阅读任何Github上的README.md,有一点很重要的是知道由于环境设定的不一样,必须渐渐了解哪些步骤能够跳过、哪些变数须要修改为符合本身项目性质的名称,这点身为新手的我,将会靠练习活用各式各样的gem来进步。:)数据库

 

此次咱们会更动的档案/文件夹以下:安全

 

Rails的构架说明ruby

Gemfile设定Rails应用程序使用了哪些Gems套件服务器

app放Controllers、Models和Views档案app

接下来就按造步骤来实做吧(leafor)!ide

 

A.在gemfile加入套件,重启rails server:

首先咱们按照carrierwave在githhub上说明档的指示,前往/项目名称/gemfile,新增代码:

gem 'carrierwave','~> 1.0'

README.md告诉咱们CarrierWave的版本需求:Rails 4.0 or higher and Ruby 2.0,个人ruby 2.4.2 Rails 5.1.6,因此没有问题~

 

每次新增任何新的Gem到Gemfile,就要在Terminal输入bundle install处理相依性,而后rails s重启服务器。

tingdeMacBook-Air:yelpdemo tingtinghsu$ bundle install

tingdeMacBook-Air:yelpdemo tingtinghsu$ bundle info carrierwave

* carrierwave(1.2.3)

Summary: Ruby file upload library

Homepage: https://github.com/carrierwaveuploader/carrierwave

Path: /Users/tingtinghsu/.rvm/gems/ruby-2.4.2/gems/carrierwave-1.2.3

B.用rails g指令,新增Image uploader功能

接下来就能够看到carrierwave的厉害之处了,在此我须要将本身的餐厅(restaurants)数据库创建新的图片(image)字段,因此把carrier的指令客制化成本身的项目。

指令rails g uploader Image帮助咱们在此路径:app/uploaders/image_uploader.rb新增了档案。

打开image_uploader.rb看看里面的类别写法:

 

class ImageUploader < CarrierWave::Uploader::Base

storage:file

#storage:fog

# Override the directory where uploaded files will be stored.

# def store_dir

“uploads/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}”

end

这个部分指的是:

若是我把储存档案的地方放在本地端(localhost),就要把storage:file前的#注释拿掉

相对的,想要把储存档案的地方放在远端(Heroku),把storage:fog前的#注释拿掉

 

在本篇里,CarrierWave会把我上传的图片将会放在/public/uploads/restaurant/image。

 

C.创建数据库上传Image所需字段

创建迁移档(migration,修改数据库结构)

rails g migration add_image_to_restaurants image:string

并在数据库增长上传图片的字段:

rake db:migrate

而后重启服务器:rails s

顺利的在db/migrate跑出了add_image_to_restaurants.rb档案。打开来瞧瞧:

 

class AddImageToRestaurants < ActiveRecord::Migration[5.1]

def change

add_column:restaurants,:image,:string

end

end

D.修改Models,让数据库准备好存取图片的功能

接下来咱们修改跟ActiveRecord有关的Models。mount Model里面,这个名为uploader上传功能小帮手,将来它会帮咱们翻译数据库语言(SQL)跟数据库要数据(餐厅图片)。:

 

Models: app/models/restaurant.rb

 

class User < ActiveRecord::Base

mount_uploader:image,ImageUploader

end

在rails官网提到:

 

Active Record是MVC的M(Model)表现商业逻辑与数据的层级,负责新增与操做须要持久存在数据库里的数据。Active Record自己是ORM(Object Relational Mapping,物件关联映像)系统的描述。

 

E.修改Views

数据库的上传功能已经准备好了,接下来到Views跟表单沟通,请让表单可以接受上传的图片。

到app/views/restaurants/_form.html.erb,修改为能够上传照片的form type(表单型态)。

<%= form_with(model: restaurant,local: true,:html => { multipart: true })do |form| %>

咱们来增长:「上传图片」字段,让使用者能在视觉上看得见新字段,并修改上传图片的档案(file)类型为form.file_field,不一样于其余纯文字(text)字段如地址、电话的form.text_field。

 

<div class=“form-group”>

<%= form.label:name %>

<%= form.text_field:name,id::restaurant_name,class:“form-control”%>

</div>

<div class=“form-group”>

<%= form.label:image %>

<%= form.file_field:image,id::restaurant_image,class:“form-control”%>

</div>

告诉rails什么时候取得image。咱们来到app/views/restaurants/show.html.erb,在餐厅数据前面加上代码:

<p id=“notice”><%= notice %></p>

<%= image_tag @restaurant.image_url if @restaurant.image_url.present?%>

<p>

<p>

<strong>Name:</strong>

<%= @restaurant.name %>

</p>

image_tag:Rails内置的Helper静态辅助方法,可让咱们建构HTML更为容易。参考这里

@restaurant.image_url:显示目前这笔餐厅数据的图片位置。

 

[新手常见Bug!]检查图片为nil写法:if @restaurant.image_url.present?。能够防止当某位使用者新增一笔餐厅数据、但没有附上图片的时候,show.html.erb这页网页直接当掉给你看…

 

F.修改Controllers

最后,咱们在Controllers: app/controllers/restaurants.controller.rb加上容许上传至字段的参数,告诉rails,新的image字段是安全的(gdgfpy)。

 

def restaurant_params

params.require(:restaurant).permit(:name,:address,:phone,:website,:image)

end

**大功告成**

相关文章
相关标签/搜索