python - 从 sqlalchemy 数据库查询数据

标签 python python-2.7 sqlalchemy

engine = create_engine('sqlite:///nwtopology.db', echo=False)
Base = declarative_base()

class SourcetoPort(Base):
    """"""
    __tablename__ = 'source_to_port'
    id = Column(Integer, primary_key=True)
    port_no        = Column(Integer)
    src_address    = Column(String)

    #----------------------------------------------------------------------
    def __init__(self, src_address,port_no):
        """"""
        self.src_address = src_address
        self.port_no     = port_no




Session = sessionmaker(bind=engine)
session = Session()
self.mac_to_port[packet.src]=packet_in.in_port
if(self.matrix.get((packet.src,packet.dst))==None):
       self.matrix[(packet.src,packet.dst)]=0
       print "found a new flow"
       #create an databse entry with address and port
       entry = SourcetoPort(src_address=str(packet.src) , port_no=packet_in.in_port)
       #add the record to the session object
       session.add(entry)
       #add the record to the session object
       session.commit()
self.matrix[(packet.src,packet.dst)]+=1
print "incrementing flow count"
#if self.mac_to_port.get(packet.dst)!=None:
if session.query(SourcetoPort).filter_by(src_address=str(packet.dst)).count():
#do stuff if the flow information is already in the databaase.

我对 python 和 sql alchemy 等东西非常陌生。上面的代码是网络 Controller 的相关部分。每当有新数据包进入时,上面的代码就会被调用。我的问题是

if session.query(SourcetoPort).filter_by(src_address=str(packet.dst)).count():

这是了解 src_address 是否已在数据库中的正确/最有效的方法吗?有人可以建议一些更好的方法吗?依赖正数似乎不太严格。

最佳答案

一些建议

1) 确保您的表在 src_address 字段上创建了索引。如果您使用 SQLAlchemy 创建架构索引,则可以通过对表定义的简单更改来添加。 (更多信息请参见Describing Databases with MetaData: Indexes part of SQLAlchemy manual)

class SourcetoPort(Base):
    """"""
    __tablename__ = 'source_to_port'
    id = Column(Integer, primary_key=True)
    port_no        = Column(Integer)
    src_address    = Column(String, index=True)

2) 要检查是否有 src_address=str(packet.dst) 的记录,还有另一种方法,即使用 EXISTS。因此,它不必扫描具有此类 src_address 的所有记录,而是在找到第一条具有此类字段值的记录时立即返回结果。

if session.query(SourcetoPort).filter_by(src_address=str(packet.dst)).count():
#do stuff if the flow information is already in the databaase.

用存在查询替换计数查询

from sqlalchemy.sql.expression import exists
if session.query(exists().where(SourcetoPort.src_address == '123')).scalar() is not None:
    #do stuff if the flow information is already in the database.

3)我不确定您通过编写此脚本来解决什么任务。我只是希望你不会在每次新的网络数据包到达网络接口(interface)时启动新的 python 脚本。启动新的 python 解释器进程需要几秒钟的时间,并且每秒可能有数千个数据包到达。 在后一种情况下,我会考虑将此类网络 Controller 程序作为守护进程运行,并将所有信息缓存在内存中。此外,我还将实现数据库操作以在单独的线程甚至线程池中异步运行,因此它们不会阻止控制网络流的主线程。

关于python - 从 sqlalchemy 数据库查询数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16329790/

相关文章:

python - 函数不打印预期结果

python subprocess 命令中包含 json ('u' 前缀错误)

python - 完全卸载 Django

python - 多处理池和队列

sqlalchemy - IronPython db-api 2.0

python - 如何标记 pandas DataFrame 中的最后一个重复元素

python - 将矩阵乘法从 Python 转换为 C++

python - 在嵌套的 json/dict 中搜索与指定键匹配的多个键值

python - 两个 SQLAlchemy 声明模型必须共享同一个 declarative_base() 吗?

sqlalchemy - SQLAlchemy 连接的模拟异步上下文管理器