ruby-on-rails - 无法更新 Rails。错误消息“找不到带有 'id'=:id 的电影”
问题描述
我想运行更新操作,但我无法获取 ID。我认为这将是一个简单的问题,但我找不到解决问题的方法。
我认为从编辑发送的值将被发送到更新操作,更新操作会更新值,但我无法获取 ID。我一直在看其他文章,看起来它也在以同样的方式更新。
代码
编辑
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<%= form_with model: @movie, url: '/admin/movies/:id', method: :put do |form| %>
<%= form.text_field :name %>
<p>Year</p>
<%= form.text_field :year %>
<p>Image URL</p>
<%= form.text_field :image_url %>
<p>Description</p>
<%= form.text_area :description %>
<p>Show</p>
<%= form.text_field :is_showing %>
<%= form.submit"Edit Save"%>
<% end %>
</body>
</html>
控制器
class MoviesController < ApplicationController
def index
@movie = Movie.all
end
def new
@movie = Movie.new
end
def create
@movie = Movie.new(post_params)
@movie.save!
end
def edit
@movie = Movie.find(params[:id])
@movie.save
end
def update
@movie = Movie.find(params[:id])
if @movie.update(post_params)
redirect_to :idnex
else
render :edit
end
end
private
def post_params
params.require(:movie).permit(:id,:name, :year, :image_url, :description, :is_showing )
end
end
模型
FactoryBot.define do
factory :movie do
sequence(:name) { |n| "TEST_MOVIE#{n}"}
sequence(:year) { 2021 }
sequence(:description) { "test"}
sequence(:image_url) {"" }
sequence(:is_showing) { 1 }
end
end
路线
Rails.application.routes.draw do
# get 'movies', to: 'movies#index'
get '/admin/movies', to: 'movies#index'
get '/admin/movies/new', to: 'movies#new'
post '/admin/movies/new', to: 'movies#create'
get '/admin/movies/:id/edit', to: 'movies#edit'
put '/admin/movies/:id', to: 'movies#update'
get '/admin/movies/:id', to: 'movies#edit'
end
更改 form_with 方法后出错
解决方案
您真的只需要在这里利用 Rails 约定,而不是手动完成所有操作。
Rails.application.routes.draw do
scope :admin do
resources :movies
end
end
而不是手动输入每条路线使用resources
宏。此外,Rails 使用 PATCH HTTP 方法而不是 PUT 进行更新已经有一段时间了。由于遗留原因,Rails 也会输出 PUT 路由,但将来可能会改变。
现在的表格:
<%= form_with model: [:admin, @movie] do |form| %>
<div class="field">
<%= form.label :name %>
<%= form.text_field :name %>
</div>
<div class="field">
<%= form.label :year %>
<%= form.text_field :year %>
</div>
<div class="field">
<%= form.label :image_url, "Image URL" %>
<%= form.text_field :image_url %>
</div>
<div class="field">
<%= form.label :description %>
<%= form.text_area :description %>
</div>
<div class="field">
<%= form.label :is_showing, "Show" %>
<%= form.text_field :is_showing %>
</div>
<div class="actions">
<%= form.submit %>
</div>
<% end %>
您无需指定 URL 或方法。Rails 可以根据模型计算出所有这些。使用[:admin, @movie]
告诉 rails 去寻找admin_movie_path
.
使用标签而不是<p>
标签来标记您的输入,以便屏幕阅读器等辅助技术可以访问它。将输入和标签组合在一个元素中可以让您使用 CSS 对其进行样式设置。
您的控制器中有许多错别字和错误:
class MoviesController < ApplicationController
# GET /admin/movies
def index
# use the plural name for the instance variable since its many movies
@movies = Movie.all
end
# GET /admin/movies/new
def new
@movie = Movie.new
end
# POST /admin/movies/
def create
@movie = Movie.new(post_params)
# check if the movie is saved and respond accordingly
# save! generally should not be used in controllers
if @movie.save
redirect_to :index, notice: 'Movie created'
else
render :new
end
end
# GET /admin/movies/1/edit
def edit
@movie = Movie.find(params[:id])
end
# PATCH|PUT /admin/movies/1
def update
@movie = Movie.find(params[:id])
if @movie.update(post_params)
# this was a typo
redirect_to :index, notice: 'Movie updated'
else
render :edit
end
end
private
def post_params
params.require(:movie)
.permit(
:id, :name, :year,
:image_url, :description, :is_showing
)
end
end
推荐阅读
- r - 根据同一数据框中另一列的值计算或求和 2 列的值
- solr - 通过将索引目录复制到新的空集合来将独立的 Solr 迁移到 Solr Cloud
- php - 使用 exec 创建文件夹后压缩文件夹会导致没有文件夹创建和压缩失败
- java - 无法在 Wowza GoCoder 的 PlayerActivity 中播放视频
- terraform - MODULE 中的 Terraform 条件源
- javascript - 如何在网页上显示数据库中的内容并允许用户选择以获取更多信息
- gitlab - gitlab:我如何以编程方式下载 CI 管道末端发布的工件
- c# - 在 Excel 工作表/单元格中嵌入文件
- docker - Visual Studio Docker 工具 - 图像在哪里以及容器在哪里运行
- node.js - 在自己的服务器上部署 Angular 7、mongo、express、node 应用程序