sqlalchemy отношения многие ко многим (значение дублирующего ключа нарушает уникальное ограничение) роль flask_user - PullRequest
0 голосов
/ 09 января 2019

Вы можете мне помочь,

когда я запускаю этот скрипт, он хорошо работает

class User(db.Model, UserMixin):
    __tablename__ = 'users'
    id = db.Column(db.Integer, primary_key=True)
    active = db.Column('is_active', db.Boolean(), nullable=False, server_default='1')

    # User authentication information. The collation='NOCASE' is required
    # to search case insensitively when USER_IFIND_MODE is 'nocase_collation'.
    email = db.Column(db.String(255, collation='NOCASE'), nullable=False, unique=True)
    email_confirmed_at = db.Column(db.DateTime())
    password = db.Column(db.String(255), nullable=False, server_default='')

    # User information
    first_name = db.Column(db.String(100, collation='NOCASE'), nullable=False, server_default='')
    last_name = db.Column(db.String(100, collation='NOCASE'), nullable=False, server_default='')

    # Define the relationship to Role via UserRoles
    roles = db.relationship('Role', secondary='user_roles')

# Define the Role data-model
class Role(db.Model):
    __tablename__ = 'roles'
    id = db.Column(db.Integer(), primary_key=True)
    name = db.Column(db.String(50), unique=True)

# Define the UserRoles association table
class UserRoles(db.Model):
    __tablename__ = 'user_roles'
    id = db.Column(db.Integer(), primary_key=True)
    user_id = db.Column(db.Integer(), db.ForeignKey('users.id', ondelete='CASCADE'))
    role_id = db.Column(db.Integer(), db.ForeignKey('roles.id', ondelete='CASCADE'))

# Setup Flask-User and specify the User data-model
user_manager = UserManager(app, db, User)

# Create all database tables
db.create_all()

# Create 'member@example.com' user with no roles
if not User.query.filter(User.email == 'member@example.com').first():
    user = User(
        email='member@example.com',
        email_confirmed_at=datetime.datetime.utcnow(),
        password=user_manager.hash_password('Password1'),
    )
    db.session.add(user)
    db.session.commit()

# Create 'admin@example.com' user with 'Admin' and 'Agent' roles
if not User.query.filter(User.email == 'admin@example.com').first():
    user = User(
        email='admin@example.com',
        email_confirmed_at=datetime.datetime.utcnow(),
        password=user_manager.hash_password('Password1'),
    )
    user.roles.append(Role(name='Admin'))
    user.roles.append(Role(name='Agent'))
    db.session.add(user)
    db.session.commit()

на этом этапе код работает без проблем, но проблема возникает только после того, как я добавляю другого пользователя с уже существующей ролью в этом случае роль администратора или роль агента например, если я добавлю код ниже, появится сообщение об ошибке

    if not User.query.filter(User.email == 'admin2@example.com').first():
    user = User(
        email='admin2@example.com',
        email_confirmed_at=datetime.datetime.utcnow(),
        password=user_manager.hash_password('Password1'),
    )
    user.roles.append(Role(name='Admin'))
    user.roles.append(Role(name='Agent'))
    db.session.add(user)
    db.session.commit()

sqlalchemy.exc.IntegrityError: (psycopg2.IntegrityError) ERREUR: замечательная копия, полная копия, противоречащая уникальной «роли_имя_ключа» ДЕТАЛИ: La clé «(name) = (Admin)» existe déjà. [SQL: 'INSERT INTO role (name) VALUES (% (name) s) RETURNING role.id'] [parameters: {'name': 'Admin'}] (фон этой ошибки: http://sqlalche. я / е / gkpj)

Я пробовал другой драйвер БД (pg8000, pygresql, py-postgresql) и все еще ту же проблему,

как сообщение об ошибке показывает проблему из-за уникального значения имени

name = db.Column (db.String (50), unique = True)

Можете ли вы объяснить мне, какую ошибку я допустил и какова роль этой части кода

# Define the relationship to Role via UserRoles

roles = db.relationship ('Role', secondary = 'user_roles')

Я использую колбу с flask_user

...