2014-10-14 3 views
3

Этот код предназначен для UserList (пользователь может создать список пользователей). Этот конкретный ресурс не содержит элементы списка, а просто заголовок списка и тип списка.В Rails, почему я получаю ответ «204 - Нет содержимого» для моего обновления/PATCH/PUT, используя Active Serializers модели?

class Api::V1::UserListsController < ApplicationController 
    respond_to :json 
    skip_before_filter :verify_authenticity_token 

    def index 
     if authenticate_user 
      user_lists = @current_user.user_lists 
      if user_lists 
       respond_with user_lists, each_serializer: Api::V1::UserListSerializer 
      else 
       render json: { error: "Could not find user's lists."}, status: :not_found 
      end 
     else 
      render json: { error: "User is not signed in." }, status: :unauthorized 
     end  
    end   

    def show 
     if authenticate_user 
      user_lists = @current_user.user_lists 
      user_list = user_lists.find_by_id(params[:id]) 
      if user_list 
       respond_with user_list, serializer: Api::V1::UserListSerializer 
      else 
       render json: { error: "Could not find user's list."}, status: :not_found 
      end 
     else 
      render json: { error: "User is not signed in." }, status: :unauthorized 
     end  
    end  

    def create 
     if authenticate_user 
      user_list = @current_user.user_lists.new(user_list_params) 
      if (user_list.save!) 
       respond_with :api, :v1, @current_user, user_list, serializer: Api::V1::UserListSerializer 
      else 
       render json: { error: "Could not create new User List."}, status: :unprocessable_entity 
      end   
     else 
      render json: { error: "User is not signed in." }, status: :unauthorized 
     end 
    end 

    def update 
     if authenticate_user 
      user_list = @current_user.user_lists.find_by_id(params[:id]) 

      if (user_list.update_attributes(user_list_update_params)) 
       respond_with :api, :v1, @current_user, user_list, serializer: Api::V1::UserListSerializer         
            #respond_with user_list, serializer: Api::V1::UserListSerializer 
      else 
       render json: { error: "Could not update User List." }, status: :unprocessable_entity 
      end 
     end 
    end 

    private 

     def user_list_params 
      params.require(:user_list).permit(:user_id, :type_id, :title) 
     end 

     def user_list_update_params 
      params.require(:user_list).permit(:type_id, :title) 
     end 
end 

Теперь обновление работает, когда я PUT/PATCH ... но я получаю

Completed 204 No Content in 24ms (ActiveRecord: 4.3ms) 

Это было около 4 + месяцев, так как я делал никаких рельсов, и тогда я был только только начинающий его изучать.

1) Кто-нибудь знает, почему я ничего не получаю? Я знаю, что это как-то связано с моей версией кода response_with, но я точно не знаю.

2) Может кто-то уточнить мне разницу между SHOW reply_with и CREATE reply_with. Я помню, что у меня была проблема с этим, и, очевидно, сейчас.

ШОУ

respond_with user_list, serializer: Api::V1::UserListSerializer 

СОЗДАТЬ

respond_with :api, :v1, @current_user, user_list, serializer: Api::V1::UserListSerializer 

а) Почему создание требует: апи и: v1 первый, но шоу не делает?

b) Почему для создания требуется @current_user, но показывать нет?

Приложение: Вот мой Serializer для справки

class Api::V1::UserListSerializer < ActiveModel::Serializer 
    attributes :id, :user_id, :type_id, :title 
    has_many :items, embed: :ids 
end 
+1

Этот вопрос может помочь вам: http://stackoverflow.com/questions/9953887/simple-respond-with-in-rails-that-avoids- 204-from-put – Passalini

ответ

0

Вы не должны получить что-либо назад, кроме 204. Любой разумный клиент не нужно получить обратно данные, которые он просто послал вас - он нуждается только в подтверждении того, что данные были сохранены.

+6

А как насчет тупых клиентов? Мы не должны различать интеллект :) –

2

Я знаю, что это уже 2 года, но после некоторого рытья я нашел пустой ответ с 204 намеренно (как упоминалось выше). Если вы используете respond_with, это всегда будет так. Обходной будет использовать render вместо (пример ниже):

class Api::V1::ItemsController < ApplicationController 
    respond_to :json 
    ... 

    def update 
    @item = Item.find(params[:id] 
    if @item 
     @item.update_attribute(item_params) 
     render json: @item 
    end 
    end 
    ... 
end 
-1
def update 
    @item = Item.find(params[:id]) 
    respond_with(:api, :v1, @item) do |format| 
    if @item.update(item_params) 
     format.json { render json: @item} 
    else 
     format.json { render json: {error: @item.errors.full_messages}} 
    end 
    end 
end 
+0

Благодарим вас за этот фрагмент кода, который может предоставить некоторую ограниченную немедленную помощь. A [надлежащее объяснение] (https://meta.stackexchange.com/q/114762/349538) значительно улучшит его долгосрочную ценность, показывая, почему это является хорошим решением проблемы и сделает более полезным будущим читателям с другими, подобными вопросами. Пожалуйста, отредактируйте свой ответ , чтобы добавить некоторое объяснение, включая сделанные вами предположения. –

0

Не перепутать передать свой класс Api::V1::UserListSerializer как ключ/значение пары (форма Hash). Вы получите сообщение об ошибке класс или модуль. Он должен выглядеть следующим образом:

serialize :some_array, Api::V1::UserListSerializer 

Или, возможно, понятнее будет:

serialize(:some_array, Api::V1::UserListSerializer) 

Вы пропустите один из параметров, и вы рендеринг класса объектов без содержания: 204 - No Content Это может показаться очевидным, но обычно принято привыкать передавать вещи в виде пары ключ/значение.

Один улучшения:

before_action :authenticate_user, only: [:create, :show, :update, ...] 

https://apidock.com/rails/ActiveRecord/Base/serialize/class