sqlalchemy:TypeError:不可互换的类型创建实例,sqlalchemy [英] sqlalchemy: TypeError: unhashable type creating instance, sqlalchemy
问题描述
我在尝试更新以下代码时遇到错误:
https:// github。 com / thrisp / flask-security 从python 2.7到3.3
给出以下最基本的实例
test.py:
from flask import Flask
from flask.ext.sqlalchemy import SQLAlchemy
from flask.ext.security import Security,UserMixin,RoleMixin,\
SQLAlchemyUserDatastore
$ b app = Flask(__ name__)
app.config ['SQLALCHEMY_DATABASE_URI'] ='sqlite: //'
db = SQLAlchemy(app)
db.drop_all()
roles_users = db.Table('roles_users',
db。列('user_id',db.Integer(),db.ForeignKey('user.id')),
db.Column('role_id',db.Integer(),db.ForeignKey('role.id ')))
类角色(db.Model,RoleMixin):
id = db.Column(db.Integer(),primary_key = True)
name = db。列(db.Str (db.Model,UserMixin):
id =$
$ db.Column(db.Integer,primary_key = True)
email = db.Column(db.String(255),unique = True)
password = db.Column(db.String(255))
last_login_at = db.Column(db.DateTime())
current_login_at = db.Column(db.DateTime())
last_login_ip = db.Column(db.String(100))
current_login_ip = db.Column(db.String(100))
login_count = db.Column(db.Integer)
active = db.Column(db.Boolean())
confirm_at = db.Column(db.DateTime())
roles = db.relationship('Role',secondary = roles_users,
backref = db.backref('users',lazy ='dynamic') )
db.create_all()
app.security =安全性(app,datastore = SQLAlchemyUserDatastore(db,User,Role))
ds = app.extensions (''security']。datastore
def create_roles():
for('ad ()
ds.create_role(name = role)
ds.commit()
create_roles()
def create_users(count = None):
users = [('matt@lp.com','password',['admin'],True),
('joe@lp.com ','password',['editor'],True),
('dave@lp.com','password',['admin','editor'],True),
'jill@lp.com','password',['author'],True),
('tiya@lp.com','password',[],False)]
count = count或len(用户)
用户中的u [:count]:
pw = u [1]
ds.create_user(email = u [0],password =
$ Traceback (最近的最后一次调用):
在< module>文件中的第62行,输入test.py
create_users(1)
在create_users
roles = u [2],active = u [3])
文件test.py,第59行, /lxch/686e26f8-c6d4-4448-8fe4-c19802726dcb/projects/current/public/flask-security/flask_security/datastore.py,第164行,在create_user
user = self.user_model(** self._prepare_create_user_args (** kwargs))
文件< string>,第4行,在__init__
文件中/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy /orm/state.py,第200行,在_initialize_instance
return manager.original_init(* mixed [1:],** kwargs)
文件/home/lxch/.virtualenvs/p3/lib /python3.3/site-packages/sqlalchemy/ext/declarative/base.py,第425行,在_declarative_constructor
setattr(self,k,kwargs [k])
文件/ home / lxch /.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/attributes.py,第303行,在__set__
instance_dict(instance),value,None)
文件/ home / lxch / .virtualenvs / p3 / lib / python3.3 / site-packages / sqlalchemy / orm / attributes.py,第1001行,在s et
lambda适配器,i:adapter.adapt_like_to_iterable(i))
文件/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/attributes.py ,第1036行,在_set_iterable
collections.bulk_replace(new_values,old_collection,new_collection)
文件/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm /collections.py,第803行,在bulk_replace
常量= existing_idset.intersection(值或())
文件/home/lxch/.virtualenvs/p3/lib/python3.3/site- (self._working_set(members).intersection(other))
TypeError:不可用类型:'Role'包含/ packages / sqlalchemy / util / _collections.py,第558行,在交叉点
result._members.update
我正在努力理解为什么,究竟是什么:
TypeError:不可取消类型:'角色'
>解决方案
类似的问题在这里讨论:修改SqlAlchemy模型时不可更改的类型错误
A解决方案(或至少是解决方法)是在你的Role类中定义一个 hash 函数,如下所示:
def __hash __(self):
return hash(self.name)
I am getting an error while trying to update code for: https://github.com/thrisp/flask-security from python 2.7 to 3.3
given the following most basic instance
test.py:
from flask import Flask
from flask.ext.sqlalchemy import SQLAlchemy
from flask.ext.security import Security, UserMixin, RoleMixin, \
SQLAlchemyUserDatastore
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite://'
db = SQLAlchemy(app)
db.drop_all()
roles_users = db.Table('roles_users',
db.Column('user_id', db.Integer(), db.ForeignKey('user.id')),
db.Column('role_id', db.Integer(), db.ForeignKey('role.id')))
class Role(db.Model, RoleMixin):
id = db.Column(db.Integer(), primary_key=True)
name = db.Column(db.String(80), unique=True)
description = db.Column(db.String(255))
class User(db.Model, UserMixin):
id = db.Column(db.Integer, primary_key=True)
email = db.Column(db.String(255), unique=True)
password = db.Column(db.String(255))
last_login_at = db.Column(db.DateTime())
current_login_at = db.Column(db.DateTime())
last_login_ip = db.Column(db.String(100))
current_login_ip = db.Column(db.String(100))
login_count = db.Column(db.Integer)
active = db.Column(db.Boolean())
confirmed_at = db.Column(db.DateTime())
roles = db.relationship('Role', secondary=roles_users,
backref=db.backref('users', lazy='dynamic'))
db.create_all()
app.security = Security(app, datastore=SQLAlchemyUserDatastore(db, User, Role))
ds = app.extensions['security'].datastore
def create_roles():
for role in ('admin', 'editor', 'author'):
ds.create_role(name=role)
ds.commit()
create_roles()
def create_users(count=None):
users = [('matt@lp.com', 'password', ['admin'], True),
('joe@lp.com', 'password', ['editor'], True),
('dave@lp.com', 'password', ['admin', 'editor'], True),
('jill@lp.com', 'password', ['author'], True),
('tiya@lp.com', 'password', [], False)]
count = count or len(users)
for u in users[:count]:
pw = u[1]
ds.create_user(email=u[0], password=pw,
roles=u[2], active=u[3])
ds.commit()
create_users(1)
results in the error:
Traceback (most recent call last):
File "test.py", line 62, in <module>
create_users(1)
File "test.py", line 59, in create_users
roles=u[2], active=u[3])
File "/media/lxch/686e26f8-c6d4-4448-8fe4-c19802726dcb/projects/current/public/flask-security/flask_security/datastore.py", line 164, in create_user
user = self.user_model(**self._prepare_create_user_args(**kwargs))
File "<string>", line 4, in __init__
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/state.py", line 200, in _initialize_instance
return manager.original_init(*mixed[1:], **kwargs)
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/ext/declarative/base.py", line 425, in _declarative_constructor
setattr(self, k, kwargs[k])
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/attributes.py", line 303, in __set__
instance_dict(instance), value, None)
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/attributes.py", line 1001, in set
lambda adapter, i: adapter.adapt_like_to_iterable(i))
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/attributes.py", line 1036, in _set_iterable
collections.bulk_replace(new_values, old_collection, new_collection)
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/orm/collections.py", line 803, in bulk_replace
constants = existing_idset.intersection(values or ())
File "/home/lxch/.virtualenvs/p3/lib/python3.3/site-packages/sqlalchemy/util/_collections.py", line 558, in intersection
result._members.update(self._working_set(members).intersection(other))
TypeError: unhashable type: 'Role'
I'm working on trying to understand why and what exactly is:
TypeError: unhashable type: 'Role'
Any insight appreciated.
A similar issue is discussed here: Unhashable Type error when modifying SqlAlchemy Models
A solution (or at least workaround) is to define a hash function in your Role class, something like this:
def __hash__(self):
return hash(self.name)
这篇关于sqlalchemy:TypeError:不可互换的类型创建实例,sqlalchemy的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!