Rails не вставляет записи в базу данных - PullRequest
0 голосов
/ 20 октября 2019

Я новичок в Rails, и у меня возникают проблемы с вставкой новых записей в базу данных с использованием моей модели автомобиля.

Приложение выглядит следующим образом: я создал базовое учебное приложение статей, как определено вна официальном сайте Rails, до раздела 5.9

Я добавил аутентификацию пользователей, используя devise, и я хотел добавить модель -cars, которая имеет связь с пользователем. пользователь has_many cars, и машина принадлежит_ пользователю. Это файл модели user.rb:

class User < ApplicationRecord
 # Include default devise modules. Others available are:
 # :confirmable, :lockable, :timeoutable, :trackable and :omniauthable
 devise :database_authenticatable, :registerable,
     :recoverable, :rememberable, :validatable
 has_many :cars
end

Файл cars.rb:

class Car < ApplicationRecord
belongs_to :user
end

Таблица машин имеет следующую структуру:

class CreateCars < ActiveRecord::Migration[6.0]
  def change
    create_table :cars do |t|
      t.string :title
      t.text :description
      t.string :img

      t.timestamps
    end
  end
end

Я добавил ассоциацию пользователей с:

class AddUserIdToCars < ActiveRecord::Migration[6.0]
  def change
    add_column :cars, :user_id, :integer
  end
end

Теперь, когда я использую консоль rails, я вижу, что таблица cars и таблица user созданы, и создание пользователей работает нормально.

Alse, когдаЯ пытаюсь создать новую машину, меня перенаправляют обратно в мой список машин, и ничего не загружается, и когда я проверяю консоль, я вижу, что таблица машин пуста.

контроллер машины:

class CarsController < ApplicationController
    def index
        @cars = Car.all
    end
    def new
    end
    def show
        @car = Car.find(params[:id])
    end
    def create
        # render plain: params[:car].inspect
        @car = Car.new(car_params)
        @car.save
        redirect_to @car
    end
    private
    def car_params
        params.require(:car).permit(:title, :description, :img)
    end
end

автомобили / новый вид:

<h1>Add new car</h1>

<%= form_with scope: :car,
url: cars_path,
local: true do |form| %>
  <p>
    <%= form.label :title %><br>
    <%= form.text_field :title %>
  </p>

  <p>
    <%= form.label :description %><br>
    <%= form.text_area :description %>
  </p>

    <p>
    <%= form.label :img %><br>
    <%= form.text_area :img %>
  </p>

  <p>
    <%= form.submit %>
  </p>
<% end %>
<%= link_to 'Back', cars_path %>

, а индекс автомобилей -:

<h1>Listing cars</h1>

<table>
  <tr>
    <th>Title</th>
    <th>description</th>
    <th>Img</th>
  </tr>

  <% @cars.each do |car| %>
    <tr>
      <td><%= car.title %></td>
      <td><%= car.description %></td>
      <td><%= car.img %></td>

      <td>
      <%= link_to 'Show', car_path(car) %>
      </td>
    </tr>
  <% end %>
</table>

<%= link_to 'New Car', new_car_path %>

, когда я публикую новую машину или иду в индексна странице, ошибки нет, и та же самая структура в разделе статьи (которую я создал с помощью официального руководства по rails) работает нормально.

При переходе к пути / автомобилям или при отправке нового автомобиля яувидеть пустую таблицу. Когда я пытаюсь использовать show при переходе к cars /: id, возникает ошибка, что ни один автомобиль с таким идентификатором не существует - еще одно свидетельство того, что записи не вставлены.

Я очень новичок в Rails, поэтомуИзвините, если не хватает информации / Я поделился большим количеством информации. Если вам нужна дополнительная информация, пожалуйста, скажите мне.

Я видел большинство вопросов с похожими темами и не нашел там никакого подходящего ответа. Я видел это, среди прочего:

Вставить в базу данных Rails

Rails 4 не вставляет значения в базу данных

Ruby on Rails не добавляет запись в базу данных

Rails 5: ActiveRecord не создает запись

Это журнал рельсов для создания автомобилей

Started POST "/cars" for ::1 at 2019-10-20 16:46:15 +0300 Processing by CarsController#create as HTML Parameters: {"authenticity_token"=>"MZYIt+YOELCPSFbZZmammwr7LrdMWQfzlge3k/h8UftwBjqgzHHH9VqHBFHAiwXi2Ej2Y4jM2xhC/V7sil773Q==", "car"=>{"title"=>"car3", "description"=>"123123", "img"=>"123"}, "commit"=>"Save Car"} Redirected to localhost:3000/cars Completed 302 Found in 5ms (ActiveRecord: 0.0ms | Allocations: 1322

Почему ни одна машина не вставляется в то время, как статья вставляется, даже если функции и файлы erb практически одинаковы?

1 Ответ

0 голосов
/ 20 октября 2019

Похоже, вы на рельсах 6. Итак, по умолчанию, когда Car belongs_to :user, то user_id на @car требуется. Но в вашем create действии вы никогда не устанавливаете user_id на @car, поэтому @car не сохраняется.

Если вы думаете, что сохранение должно работать, а это не так, вы всегда можете сделать save! вместо save. Ударная версия метода вызовет ошибку, если сохранение будет неудачным.

В любом случае, я думаю, что действие create в вашем CarsController должно выглядеть примерно так:

class CarsController < ApplicationController

  def index
    @cars = Car.all
  end

  def new
    @car = Car.new
  end

  def show
    @car = Car.find(params[:id])
  end

  def create
    @car = current_user.cars.new(car_params)
    if @car.save
      redirect_to @car
    else
      # do something else
    end
  end

  private

  def car_params
    params.require(:car).permit(:title, :description, :img)
  end

end

Делая current_user.cars.new, user_id автоматически устанавливается на новый Car, и вы сможете сохранять.

В ответ на ваши вопросы в комментариях:

Почему current_user.cars.new (car_params), а не: current_user.Car.new (car_params)? Почему не нужен был заглавный автомобиль, как в Car.find?

Car - это класс. Car.new вызывает метод new класса Car. Car.find вызывает метод find класса Car. Car - это , а не - метод для current_user. Следовательно, current_user.Car не имеет смысла и должно выдавать ошибку.

cars (при использовании как current_user.cars) - это метод для current_user экземпляра User. Метод .cars создается, когда вы делаете User has_many :cars. Вы можете увидеть список всех методов, созданных с помощью has_many, в разделе Methods, добавленном has_many руководства Ассоциации активных записей .

current_user.cars возвращает ActiveRecord_Relation. Когда вы делаете current_user.cars.new, вы вызываете метод new для ActiveRecord_Relation, возвращаемого current_user.cars. Этот метод new возвращает экземпляр Car, для которого уже имеет user_id, установленный , что является смыслом всего этого. Итак:

  1. Car.new возвращает новый Car без user_id набора,
  2. current_user.cars.new возвращает новый Car с набором user_id.

Почему автомобили? как я понимаю, автомобили - это привязка к таблице, а не сама модель автомобиля.

Нет. Как указано выше, и в этом контексте cars - это метод для current_user, который создается при выполнении User has_many :cars и возвращает ActiveRecord_Relation, представляющий все Car экземпляры, которые имеют user_id, которыйспички current_user.id.

...