2017-01-16 9 views
1

내가 파이썬 SQLAlchemy의를 생성하려면, 이것이이 개 테이블,SQLAlchemy의 내 데이터베이스에이 테이블

table name : student 

- id (integer) 

- student_name (varchar(20)) 

- edu_level_id (integer) 

포함 기록에 가입

id | student_name | edu_level_id 

1 | John | 2 

2 | George | 1 

테이블 : master_edu_level

* id (integer) 
* name_level (varchar(50)) 

기록 :

id | name_level | 

1 | high school 

2 | Bachelor 

3 | Master 

같은 기록을 표시하는 방법 :이 같은 SQL을 설명하면

id | student_name | education 


1 | John  | Bachelor 

2 | George | high school 

을 :

from app import db 
from app import session 
from sqlalchemy import Table, DateTime,Date, Text, text, Column, Integer, String, MetaData, ForeignKey, select, func 
from sqlalchemy.ext.declarative import declarative_base 
from marshmallow_jsonapi import Schema, fields 
from marshmallow import validate 
from marshmallow import ValidationError 
from sqlalchemy.exc import SQLAlchemyError 
from sqlalchemy.orm import relationship 

class Student(db.Model): 
     __tablename__ = 'student' 

     id = db.Column(Integer, primary_key=True, index=True) 
     student_name = db.Column(String(20), nullable=False, index=True) 
     edu_level_id = db.Column(Integer) 

class StudentSchema(Schema): 
    not_blank = validate.Length(min=1, error='Field cannot be blank') 
    id = fields.Integer(dump_only=True) 
    student_name  = fields.String() 
    edu_level_id  = fields.String() 

    class Meta: 
     type_ = 'student' 

student_schema = StudentSchema() 


class MasterEduLevel(db.Model): 
    __tablename__ = 'master_edu_level' 
    __table_args__ = {'extend_existing': True} 

    id = db.Column(Integer, primary_key=True, index=True) 
    name_level = db.Column(String(20), nullable=False, index=True) 


class MasterEdulevelSchema(Schema): 
    not_blank = validate.Length(min=1, error='Field cannot be blank') 
    id = fields.Integer(dump_only=True) 
    name_level  = fields.String() 

    class Meta: 
     type_ = 'master_edu_level' 

schema = MasterEdulevelSchema() 

방법 테이블 ORM 가입 만드는 :

select student.id, student.name,master_edu_level.name AS educatio FROM student 
left join master_edu_Level ON master_edu_level.id = student.edu_level_id 

이미 코드를 작성 파이썬 SQLAlchemy에? 첫 번째 단계 변화 스키마와 같은 길에

감사

+0

-against-multiple-tables), 실제로는 [Student]에 [relationship] (http://docs.sqlalchemy.org/en/latest/orm/relationships.html)을 추가한다는 의미 였기 때문에 예를 들어'student.edu_level.name_level'과 같이 접근하거나'query (Student.student_name, MasterEduLevel.name_level) .join (MasterEduLevel) ... '과 같은 질의를하는 방법? –

+0

@ helo1987 내 코드를 사용해 보셨습니까? 나는 당신의 질문에 대답 했습니까? – theodor

답변

0

는 :

import marshmallow as mm 
from marshmallow_sqlalchemy import ModelSchema 

class StudentSchema(ModelSchema): 
    id = mm.fields.Integer(dump_only=True) 
    student_name = mm.fields.String() 
    education = mm.fields.Nested('MasterEdulevelSchema') 

    class Meta: 
     type_ = 'student' 

    @mm.post_dump 
    def format_dump(self, data): 
     education = data.pop('education') 
     data['education'] = education['name_level'] 
     return data 


class MasterEdulevelSchema(ModelSchema): 
    name_level = mm.fields.String() 

    class Meta: 
     type_ = 'master_edu_level' 

그것은 당신의 데이터를 올바른 방법으로 포맷합니다.

student_schema = StudentSchema() 
student = db.session.query(Student).join(MasterEduLevel, Student.edu_level_id == MasterEduLevel.id).first() 
student_result = student_schema.dump(student) 

이 작동합니다,하지만 난 그것을 테스트하지 않았습니다 :

다음 단계 덤프 데이터베이스 개체에

.

그런데이 문제를 해결하는 방법에는 여러 가지가 있습니다. SQLAlchemy과 마찬가지로, Marshmallow의 측면에 있습니다.

+0

안녕 sory의 iogane, 내가 늦게 내가 당신의 명령에 따라 응답하지만, 점점 오류입니다 '@marshmallow.post_dump 나가서 설명하자면 NameError : 당신은 상단에 마시 멜로를 가져와야합니다 helo1987 @ – helo1987

+0

을 defined'되지 않은 이름 '마시마로' sqlalchemy.ext.declarative 수입에서 상단 에 당신이'수입 marshmallow' 파일 ... – theodor

+0

yes..i 이미 넣어 가져 오기 SQLAlchemy의에서 마시 멜로 수입 ValidationError 에서 을 확인 마시 멜로 가져 오기에서 필드 , marshmallow_jsonapi 가져 오기 스키마에서 을 declarative_base. exc import SQLAlchemyError sqlalchemy.orm에서 가져 오기 관계 ' 상단의 예와 동일합니다. – helo1987

0

그래서, 나는이

params = {"id":1} 
s = text("SELECT student.*, master_edu_level.name_level FROM student left join master_edu_level ON master_edu_level.id = student.edu_level_id WHERE student.id= :id") 
users_query= session.execute(s, params).fetchall() 
results = schema.dump(users_query, many=True).data 

같은 텍스트 쿼리 SQLAlchemy의 을 사용하여 결정하고 스키마 학생이

class StudentSchema(Schema): 
    not_blank = validate.Length(min=1, error='Field cannot be blank') 
    id = fields.Integer(dump_only=True) 
    student_name  = fields.String() 
    edu_level_id  = fields.String() 
    name_level = fields.String() 

당신을 감사처럼 필드를 name_level

를 추가합니다.

0

이 시도 : 당신은 참 (http://docs.sqlalchemy.org/en/latest/orm/nonstandard_mappings.html#mapping-a-class [조인 위에 맵핑을 작성] 수

from app import db 
from app import session 
from sqlalchemy import Table, DateTime,Date, Text, text, Column, Integer, String, MetaData, ForeignKey, select, func 
from sqlalchemy.ext.declarative import declarative_base 
from marshmallow_jsonapi import Schema, fields 
from marshmallow import validate 
from marshmallow import ValidationError 
from sqlalchemy.exc import SQLAlchemyError 
from sqlalchemy.orm import relationship 


class MasterEduLevel(db.Model): 
    __tablename__ = 'master_edu_level' 
    __table_args__ = {'extend_existing': True} 

    id = db.Column(Integer, primary_key=True, index=True) 
    name_level = db.Column(String(20), nullable=False, index=True) 


class MasterEdulevelSchema(Schema): 
    not_blank = validate.Length(min=1, error='Field cannot be blank') 
    id = fields.Integer(dump_only=True) 
    name_level  = fields.String() 

    class Meta: 
     type_ = 'master_edu_level' 

class Student(db.Model): 
    __tablename__ = 'student' 

    id = db.Column(Integer, primary_key=True, index=True) 
    student_name = db.Column(String(20), nullable=False, index=True) 
    edu_level_id = db.Column(Integer, db.ForeignKey(MasterEduLevel.id)) 
    edu_level = db.relationship("MasterEduLevel") 

class StudentSchema(Schema): 
    not_blank = validate.Length(min=1, error='Field cannot be blank') 
    id = fields.Integer(dump_only=True) 
    student_name  = fields.String() 
    edu_level_id  = fields.String() 

    edu_level   = fields.Function(lambda x: x.edu_level) 

    # You can use Nested for get the entire object of the MaterEduLevel (comment above edu_level) 
    #edu_level   = fields.Nested("MasterEdulevelSchema") 

    # You can also specify a field of the Nested object using the 'only' attribute (comment above edu_level) 
    #edu_level   = fields.Nested("MasterEdulevelSchema", only=('name_level',)) 

    class Meta: 
     type_ = 'student' 

student_schema = StudentSchema() 
# You can also use the ONLY attribute here 
#student_schema = StudentSchema(only=('student_name', 'edu_level')) 

# Many results 
users_query = session.query(Student).all() 
results = student_schema.dump(users_query, many=True).data 

# Many results with filter 
users_query = session.query(Student).filter(Student.name.like('jo%')).all() 
results = student_schema.dump(users_query, many=True).data 

# Many results with filter in child property 
users_query = session.query(Student).join(Student.edu_level).filter(MasterEduLevel.name == 'Bachelor').all() 
results = student_schema.dump(users_query, many=True).data 

# Just one row by PK 
user = session.query(Student).get(1) #Student.id == 1 
result = student_schema.dump(user).data 
+0

안녕하세요 Jair Perrut, 의견을 보내 주셔서 감사합니다. – helo1987

+0

안녕하세요 @ helo1987이 문서는 [SQLALchemy Relationship] (https : // docs .sqlalchemy.org/ko/rel_1_1/orm/basic_relationships.html) 및 [Marshmallow] (https://marshmallow.readthedocs.io/en/latest/) –