0

I working on a user's public-facing profile page, where I would like to display the user's profile as well as their "published" recipes. I have the following UserSchema, but this schema displays all recipes including the one that has not been published. I want to strictly display only the published recipes. Is there a way to filter out recipes that have not been published? I looked through marshmallow documentation but could not find an answer.

class User(db.Model):
     __tablename__ = 'user'

     id = db.Column(db.Integer, primary_key=True)
     username = db.Column(db.String(80), nullable=False, unique=True)
     email = db.Column(db.String(200), nullable=False, unique=True)
     password = db.Column(db.String(200))
     recipes = db.relationship('Recipe', backref='user')

class UserSchema(Schema):
      class Meta:
           ordered = True

      id = fields.Int(dump_only=True)
      username = fields.String(required=True)
      email = fields.Email(required=True)
      password = fields.Method(required=True)
      recipes = fields.Nested("RecipeSchema", many=True, exclude=("author",))

Following is the RecipeModel and RecipeSchema,

class Recipe(db.Model):
      __tablename__ = 'recipe'

      id = db.Column(db.Integer, primary_key=True)
      name = db.Column(db.String(100), nullable=False)
      description = db.Column(db.String(200))
      is_publish = db.Column(db.Boolean(), default=False)
      user_id = db.Column(db.Integer(), db.ForeignKey("user.id"))

class RecipeSchema(Schema):
      class Meta:
            ordered = True

       id = fields.Integer(dump_only=True)
       name = fields.String(required=True, validate=[validate.Length(max=100)])
       description = fields.String(validate=[validate.Length(max=200)])           
       is_publish = fields.Boolean(dump_only=True)     
       author = fields.Nested(UserSchema, attribute='user', dump_only=True, exclude=('email', ))

Resource responsible for returning user profile data is:

from schemas.user import UserSchema
user_schema =  UserSchema()
class UserResource(Resource):
      @classmethod
      def get(cls, _id: int):
            user = User.query.filter_by(id=_id).first()    
            if not user:
                 return {"message": gettext("user_not_found")}, 404
            return user_schema.dump(user), 200

Current output is

{
    "id": "1",
    "username": "john.doe",    
    "recipes": [
        {
            "id": "1",
            "name": "cheese pizza",
            "description": "yummy",           
            "is_publish": true
        },
        {
            "id": "2",
            "name": "Potato Salad",
            "description": "tags with sepearate function",           
            "is_publish": false
        }
    ]
}

I want it to be

{
    "id": "1",
    "username": "john.doe",    
    "recipes": [
        {
            "id": "1",
            "name": "cheese pizza",
            "description": "yummy",           
            "is_publish": true
        }
    ]
}
Sam Mas
  • 1
  • 2
  • Marshmallow schemas convert data from one format to the next. It sounds like you want to modify the data that marshmallow is transforming rather than modify the actual marshaling. Can you edit your post to include the code that is responsible for retrieving the User and Recipe object that are then pumped into marshmallow? – steve Jan 21 '21 at 05:25
  • @steve just added the code that retrieves user data that is passed on to userSchema. – Sam Mas Jan 21 '21 at 17:00
  • @steve, based on your comment, I think I got the answer. Rather than trying to filter data in marshmallow schema, I filtered the published data in the resource section and then passed it to the user schema. Thank you. – Sam Mas Jan 21 '21 at 18:36
  • @SamMas how you did this bro . facing same issue :((( – Fatima Fahad Nov 26 '21 at 23:17

0 Answers0