Добавить "пространство имен" в сериализатор - PullRequest
1 голос
/ 27 января 2020

У меня есть модель User, существующая в моей базе данных, однако я хотел бы вернуть json ответ с active_model_serializers гемом, в котором атрибуты user инкапсулированы / вложены в пространство имен player, которого нет в базе данных (скажем, это виртуальный, и это произвольный ожидаемый ответ).

Вместо:

{
    "email": "some@mail.com",
    "first_name": "Hey",
    "last_name": "Hoo",
    "birthdate": "1540-05-05",
    "phone_number": "856539571"
}

Я хотел бы иметь:

{
    "player":
    {
        "email": "some@mail.com",
        "first_name": "Hey",
        "last_name": "Hoo",
        "birthdate": "1540-05-05",
        "phone_number": "856539571"
    }
}

Ответы [ 3 ]

1 голос
/ 27 января 2020

Когда ответ Nwocha будет правильным, я добавлю к нему более подробную информацию.

Что касается документации , в которой говорится:

Переопределение ресурса root применяется только при использовании JSON адаптер.

Обычно ресурс root является производным от имени класса сериализуемого ресурса. например, UserPostSerializer.new(UserPost.new) будет сериализовано с root user_post или user_posts в соответствии с правилами множественного набора адаптеров.

При использовании адаптера JSON в инициализаторе (ActiveModelSerializers.config.adapter = :json) или передаче в адаптере при вызове рендеринга вы можете указать root, передав его в качестве аргумента для рендеринга. Например:

  render json: @user_post, root: "admin_post", adapter: :json

Будет отображаться как:


  {
    "admin_post": {
      "title": "how to do open source"
    }
  }

Примечание : Адаптер атрибутов (по умолчанию) не включает ресурс root. Вы также не сможете создать один root верхнего уровня, если используете адаптер: json_api .

1 голос
/ 27 января 2020

В классе UserSerializer определите атрибут root. Например:

class UserSerializer < ActiveModel::Serializer
  root :player

  ...
end

0 голосов
/ 27 января 2020

Ответ предоставляется и до работы, но в итоге я использовал немного другой подход. Оказалось, что помимо player должен быть еще один json, скажем, team, который делает окончательный ответ похожим на это:

{
    "player": 
    {
        "email": "some@mail.com",
        ...
    },
    "team":
    {
        "name": "Fancy Team",
        ...
    }
}

Что я на самом деле сделал, так это определил точное json, которое Я хотел использовать, как это:

class UserSerializer < ActiveRecord::Serializer
    attributes :player
    attributes :team

    def player
        {
            email: object.email,
            ...
        }
    end

    def team
        { 
            name: object.name,
            ...
        }
    end
end

Если бы я использовал опцию root в render json:, весь сериализатор был бы инкапсулирован в это имя. Извините, что не очистил его в начале.

...