2017-02-15 20 views
-1

У меня возникают проблемы с сохранением данных json в моей базе данных postgres с помощью команды POST в RESTful API. Данные принимаются, но ключевые значения взаимозаменяются друг с другом. Я прикрепил и команду PUT, и результирующую базу данных. Какая ошибка в моем коде вызывает такую ​​специфическую проблему?Неверные значения, хранящиеся в базе данных при передаче через POST в RESTapi

Ниже приведен питон файлы, используемые для управления нашей веб-страницы (с unncessary частями для пространства опущены) инициализации .py

from flask import Flask, render_template, flash, request, url_for, redirect,session 
from models import db, Users 
from forms import SignupForm 
from secrets import whole_string 
import config 
import logging 
from logging.handlers import RotatingFileHandler 
from flask_bcrypt import Bcrypt 
from flask_restful import Resource, Api 
from views import table_master 

app = Flask(__name__) 

db.init_app(app) 
api = Api(app) 
api.add_resource(table_master, '/api/master_animal/<cownumber>') 
api.add_resource(table_master, '/api/master_animal/', endpoint = "cownumber") 

if __name__ == '__main__': 
    handler = RotatingFileHandler('barnyard.log', maxBytes=10000, backupCount=1) 
    handler.setLevel(logging.INFO) 
    app.logger.addHandler(handler) 
    #app.run(debug = True) 

просмотры .py

from flask import Blueprint, request, jsonify, make_response 
from models import UsersSchema, db, Master_animal, Master_animal_Schema 
from flask_restful import Api, Resource 
from sqlalchemy.exc import SQLAlchemyError 
from marshmallow import ValidationError 
import sys 

master_animal= Blueprint('master_animal', __name__) # Seems to only change the format of returned json data 
schemaMaster = Master_animal_Schema() 

# master_animal table 
class table_master(Resource): 

    def get(self, cownumber): 
     master_animal_query = Master_animal.query.get_or_404(cownumber) 
     #Serialize the query results in the JSON API format 
     result = schemaMaster.dump(master_animal_query).data 
     return result 

    def post(self): 
     raw_dict = request.get_json(force=True) 
     master_dict = raw_dict['data']['attributes'] 
     print >> sys.stderr, "data {}".format(raw_dict) 
     try: 
       #Validate the data or raise a Validation error if 
       schemaMaster.validate(master_dict) 
       #Create a master object with the API data recieved 
       master = Master_animal(master_dict['cownumber'], master_dict['weight'], master_dict['height']) 
       master.add(master) 
       query = Master_animal.query.all() 
       results = schemaMaster.dump(query, many = True).data 
       return results, 201 


     except ValidationError as err: 
       resp = jsonify({"error": err.messages}) 
       resp.status_code = 403 
       return resp    

     except SQLAlchemyError as e: 
       db.session.rollback() 
       resp = jsonify({"error": str(e)}) 
       resp.status_code = 403 
       return resp 

модель .py

import sys 

from flask import Flask 
from flask_bcrypt import Bcrypt 
from secrets import whole_string 
from marshmallow_jsonapi import Schema, fields 
from marshmallow import validate 
from flask_sqlalchemy import SQLAlchemy 
from sqlalchemy.exc import SQLAlchemyError 


app = Flask(__name__) 
bcrypt = Bcrypt(app) 
app.config['SQLALCHEMY_DATABASE_URI'] = whole_string 
db = SQLAlchemy() 


#Class to add, update and delete data via SQLALchemy sessions 
class CRUD(): 

    def add(self, resource): 
     db.session.add(resource) 
     return db.session.commit() 

    def update(self): 
     return db.session.commit() 

    def delete(self, resource): 
     db.session.delete(resource) 
     return db.session.commit() 

class Master_animal(db.Model, CRUD): 
    __tablename__ = 'master_animal' 
    cownumber = db.Column(db.Text, primary_key = True) 
    height = db.Column(db.Float) 
    weight = db.Column(db.Float) 

    def __init__(self, cownumber, height, weight): 
     self.cownumber = cownumber 
     self.height = height 
     self.weight = weight 

class Master_animal_Schema(Schema): 
    not_blank = validate.Length(min=1, error ='Field cannot be blank') 
    id = fields.Integer(dump_only=True) #WHY DOES THIS HAVE TO BE HERE??? 
    cownumber = fields.String(validate = not_blank) 
    height = fields.Float(validate = not_blank) 
    weight = fields.Float(validate = not_blank) 

    # self links 
    def get_top_level_links(self, data, many): 
     print >> sys.stderr, "data {}".format(data) # print data to verify get request 
     if many: 
      self_link = "/master_animal/" 
     else: 
      self_link = "/master_animal/{}".format(data['attributes']['cownumber']) 
     return {"self":self_link} 
    class Meta: 
     type_ = 'master_animal' 

Использование PUT в почтальона

example.com/api/master_animal/

тела:

{ 
    "data": { 
    "attributes": { 
     "cownumber": "1344", 
     "height": 56, 
     "weight": 230 
    }}} 

В нашей базе данных PostGreSQL значения высоты и веса перепутаны

barnyard=# Select * from master_animal; 
cownumber | height | weight 
-----------+--------+-------- 
1235  | 189 |  32 
1253  | 156 |  23 
1254  | 183 |  54 
1344  | 230 |  56 

Каждая команда PUT дает этот формат.

Я понятия не имею, почему он делает это или как решить проблему

ответ

1

Я подозреваю, что проблема в том, где вы экземпляр объекта Master_animal. Вы почти наверняка должны использовать аргументы ключевых слов.

master = Master_animal(cownumer=master_dict['cownumber'], weight=master_dict['weight'], height=master_dict['height']) 
+0

THAT FIXED IT !! БОЛЬШОЕ СПАСИБО. Не понимаю, почему ... –