import cx_Oracle # 连接Oracle数据库 dsn = cx_Oracle.makedsn(host='localhost', port=1521, sid='orcl') connection = cx_Oracle.connect(user='yourusername', password='yourpassword', dsn=dsn) # 插入数据并校验 cursor = connection.cursor() try: for batch in batches: cursor.execute("BEGIN") for row in batch: cursor.execute("INSERT INTO yourtable (col1, col2, col3) VALUES (:1, :2, :3)", row) cursor.execute("COMMIT") # 数据校验 cursor.execute("SELECT count(*) FROM yourtable") count = cursor.fetchone()[0] if count != len(results): raise Exception("数据校验失败") except Exception as e: print(e) connection.rollback() finally: cursor.close() connection.close(),如果在后面循环中发生异常也会回滚前面循环已经提交的事务吗,为什么请解释下
时间: 2024-04-01 07:35:54 浏览: 16
在以上代码中,如果在后面的循环中发生异常,会回滚整个事务,包括前面已经提交的批次。这是因为整个操作是在一个事务中进行的,如果发生异常,则会回滚整个事务,而不是只回滚当前批次的操作。
在每个批次之后,都有一个 `COMMIT` 操作,这会将当前批次的操作提交到数据库中并结束当前事务。如果在后面的批次中发生异常,由于整个操作是在同一个事务中进行的,因此整个事务都会被回滚,包括之前已经提交的批次。
如果需要在每个批次中启动一个独立的事务,可以将 `BEGIN` 和 `COMMIT` 操作移动到循环内部,这样每个批次都会在自己的事务中执行,如果发生异常,只会影响当前批次的操作。
相关问题
import cx_Oracle # 连接Oracle数据库 dsn = cx_Oracle.makedsn(host='localhost', port=1521, sid='orcl') connection = cx_Oracle.connect(user='yourusername', password='yourpassword', dsn=dsn) # 插入数据并校验 cursor = connection.cursor() try: for batch in batches: cursor.execute("BEGIN") for row in batch: cursor.execute("INSERT INTO yourtable (col1, col2, col3) VALUES (:1, :2, :3)", row) cursor.execute("COMMIT") # 数据校验 cursor.execute("SELECT count(*) FROM yourtable") count = cursor.fetchone()[0] if count != len(results): raise Exception("数据校验失败") except Exception as e: print(e) connection.rollback() finally: cursor.close() connection.close(),以上代码 BEGIN 和 COMMIT 操作在循环内部,如果其他批次出现异常,会将其他已经提交的事务也回滚吗,帮我再输出一份有注释的代码,使用sqlalchemy实现
以下是使用 `sqlalchemy` 实现的代码,其中每个批次都在自己的事务中执行,如果一个批次出现异常,只会回滚当前批次的操作,而不会影响到其他批次已经提交的操作:
```
import cx_Oracle
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
# 连接Oracle数据库
dsn = cx_Oracle.makedsn(host='localhost', port=1521, sid='orcl')
engine = create_engine(f"oracle+cx_oracle://yourusername:yourpassword@{dsn}")
# 创建Session
Session = sessionmaker(bind=engine)
# 插入数据并校验
try:
session = Session()
for batch in batches:
tx = session.begin() # 启动事务
try:
for row in batch:
session.execute("INSERT INTO yourtable (col1, col2, col3) VALUES (:1, :2, :3)", row)
session.commit() # 提交事务
except Exception as e:
session.rollback() # 回滚事务
raise e
finally:
tx.close()
# 数据校验
count = session.query(func.count('*')).select_from(YourTable).scalar()
if count != len(results):
raise Exception("数据校验失败")
except Exception as e:
print(e)
finally:
session.close()
engine.dispose()
```
在上面的代码中,每个批次都在自己的事务中执行。在每个批次的循环中,使用 `session.begin()` 启动一个新的事务,并使用 `session.commit()` 提交事务。如果在批次中发生异常,将会执行 `session.rollback()` 回滚当前事务,并抛出异常。在每个批次结束后,使用 `tx.close()` 关闭当前事务。
在循环结束后,使用 `session.query(func.count('*')).select_from(YourTable).scalar()` 查询表中的记录数,并与 `len(results)` 进行比较,以校验插入数据的结果。
最后,使用 `session.close()` 关闭 `Session`,并使用 `engine.dispose()` 释放数据库连接。
dsn = cx_Oracle.makedsn('your_host', 'your_port', service_name='your_service_name') service_name,这个不知道是什么,只有一个sid
在Oracle中,`service_name` 和 `SID` 都可以用来标识一个数据库实例,但是 `service_name` 是 Oracle 推荐使用的标识方式。在使用 `cx_Oracle` 连接 Oracle 数据库时,如果要使用 `service_name`,需要在 Oracle 数据库中启用相应的监听器服务(listener service),并且在 `tnsnames.ora` 或 `ldap.ora` 文件中配置相应的服务名称。如果没有启用监听器服务或者没有配置相应的服务名称,则只能使用 `SID` 进行连接。
如果你只有一个 `SID`,可以尝试使用以下方式进行连接:
```python
dsn = cx_Oracle.makedsn('your_host', 'your_port', sid='your_sid')
conn = cx_Oracle.connect(username, password, dsn)
```
其中,`your_sid` 是你要连接的 Oracle 数据库实例的 SID。注意,如果使用 `SID` 进行连接,需要在本地安装 Oracle 客户端或者使用 Instant Client,并配置好 `ORACLE_HOME` 和 `LD_LIBRARY_PATH` 环境变量。
相关推荐
![pdf](https://img-home.csdnimg.cn/images/20210720083512.png)
![pdf](https://img-home.csdnimg.cn/images/20210720083512.png)
![rar](https://img-home.csdnimg.cn/images/20210720083606.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)