当前位置: 首页 > news >正文

PostgreSQL的学习心得和知识总结(一百四十七)|深入理解PostgreSQL数据库之transaction chain的使用和实现


注:提前言明 本文借鉴了以下博主、书籍或网站的内容,其列表如下:

1、参考书籍:《PostgreSQL数据库内核分析》
2、参考书籍:《数据库事务处理的艺术:事务管理与并发控制》
3、PostgreSQL数据库仓库链接,点击前往
4、日本著名PostgreSQL数据库专家 铃木启修 网站主页,点击前往
5、参考书籍:《PostgreSQL中文手册》
6、参考书籍:《PostgreSQL指南:内幕探索》,点击前往
7、Using Transaction Chaining to Reduce Server Round-Trips,点击前往


1、本文内容全部来源于开源社区 GitHub和以上博主的贡献,本文也免费开源(可能会存在问题,评论区等待大佬们的指正)
2、本文目的:开源共享 抛砖引玉 一起学习
3、本文不提供任何资源 不存在任何交易 与任何组织和机构无关
4、大家可以根据需要自行 复制粘贴以及作为其他个人用途,但是不允许转载 不允许商用 (写作不易,还请见谅 💖)
5、本文内容基于PostgreSQL master源码开发而成


深入理解PostgreSQL数据库之transaction chain的使用和实现

  • 文章快速说明索引
  • 功能使用背景说明
  • 功能实现源码分析
  • 源码调试案例分析



文章快速说明索引

学习目标:

做数据库内核开发久了就会有一种 少年得志,年少轻狂 的错觉,然鹅细细一品觉得自己其实不算特别优秀 远远没有达到自己想要的。也许光鲜的表面掩盖了空洞的内在,每每想到于此,皆有夜半临渊如履薄冰之感。为了睡上几个踏实觉,即日起 暂缓其他基于PostgreSQL数据库的兼容功能开发,近段时间 将着重于学习分享Postgres的基础知识和实践内幕。


学习内容:(详见目录)

1、深入理解PostgreSQL数据库之transaction chain的使用和实现


学习时间:

2024年07月01日 20:25:11


学习产出:

1、PostgreSQL数据库基础知识回顾 1个
2、CSDN 技术博客 1篇
3、PostgreSQL数据库内核深入学习


注:下面我们所有的学习环境是Centos8+PostgreSQL master+Oracle19C+MySQL8.0

postgres=# select version();version                                                   
------------------------------------------------------------------------------------------------------------PostgreSQL 17devel on x86_64-pc-linux-gnu, compiled by gcc (GCC) 8.5.0 20210514 (Red Hat 8.5.0-21), 64-bit
(1 row)postgres=##-----------------------------------------------------------------------------#SQL> select * from v$version;          BANNER        Oracle Database 19c EE Extreme Perf Release 19.0.0.0.0 - Production	
BANNER_FULL	  Oracle Database 19c EE Extreme Perf Release 19.0.0.0.0 - Production Version 19.17.0.0.0	
BANNER_LEGACY Oracle Database 19c EE Extreme Perf Release 19.0.0.0.0 - Production	
CON_ID 0#-----------------------------------------------------------------------------#mysql> select version();
+-----------+
| version() |
+-----------+
| 8.0.27    |
+-----------+
1 row in set (0.06 sec)mysql>

功能使用背景说明

使用 PostgreSQL 或任何关系数据库实现业务应用程序通常相当于执行一系列事务。给定事务以 COMMIT 还是 ROLLBACK 结束并不重要,因为在这两种情况下,下一个事务都会在前一个事务完成后立即开始。此外,对于大多数应用程序来说,前一个事务和下一个事务具有相似的特征,例如它们的 ISOLATION LEVEL。本质上,您最终得到的样式如下所示:

START TRANSACTION;
-- workload of 1st transaction
COMMIT;
START TRANSACTION;
-- workload of 2nd transaction
ROLLBACK;
START TRANSACTION;
-- workload of 3rd transaction
COMMIT;

在上面的 SQL 脚本中,您会看到三个后续事务和总共六个语句(每个事务两个语句),但您可以想象更长的事务序列。问题是:每个语句都需要单独的服务器往返才能执行。没有办法解决这个问题,即使三个示例事务为空(不包含任何语句),也没有什么区别。


监控连接状态

为了进行此实验,我们需要与同一 PostgreSQL 服务器建立两个单独的连接(例如,两个 psql 会话)。第一个连接使用 postgres 数据库,第二个连接使用demo数据库。

好了,现在我们可以在第一个连接上使用 pg_stat_activity(属于 pg_catalog 模式的内置视图)来询问 PostgreSQL 使用演示数据库的第二个连接的状态:

postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
-------idle
(1 row)

如您所见,由于没有执行任何操作,因此该连接当前处于空闲状态。但是,如果我们在第二个连接上启动事务,我们可以看到连接的状态立即变为idle in transaction

demo=# START TRANSACTION;
START TRANSACTION
postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
---------------------idle in transaction
(1 row)

这证明 START TRANSACTION 语句导致了与服务器的往返,因为如果没有,第一个连接将无法看到第二个连接的状态变化。如果我们使用 COMMITROLLBACK 完成事务,情况也是一样的,在这种情况下,连接会立即恢复到空闲状态:

demo=*# COMMIT;
COMMIT
postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
-------idle
(1 row)

往返开销

长话短说,事务的开始和结束可能会带来巨大的开销。具体来说,如果满足以下任何条件:

  1. 往返服务器的时间很慢。通常,如果客户端和服务器之间的网络距离很远,情况就会如此。
  2. 许多事务的平均运行时间很短。这是因为对于较短的事务,开销占总运行时间的百分比较高。

那么,我们可以做些什么来减少开销并提高性能呢?


事务链

SQL 标准有一个由 PostgreSQL 实现的内置解决方案:AND CHAIN 参数。此参数可用于 COMMITROLLBACK 语句,并具有以下效果…

如果提供了 AND CHAIN 参数,则提交(或回滚)当前事务,此外,立即启动具有相同特征(例如,ISOLATION LEVEL)的后续事务。

因此,如果我们将其应用于原始示例,我们可以将服务器往返次数减少基本上 50%(从 n 减少到 n/2+1)。

START TRANSACTION;
-- workload of 1st transaction
COMMIT AND CHAIN;
-- workload of 2nd transaction
ROLLBACK AND CHAIN;
-- workload of 3rd transaction
COMMIT;

我们可以运行相同的实验来证明它按预期工作。我再次使用两个连接,一个使用 postgres 数据库,另一个使用演示数据库。最初,演示连接处于空闲状态,但是一旦我们开始新的事务,其状态就会更改为idle in transaction

demo=# START TRANSACTION;
START TRANSACTION
postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
---------------------idle in transaction
(1 row)

那么,如果demo连接执行 COMMIT AND CHAIN 语句会发生什么?正如我所说,PostgreSQL 立即启动后续事务,因此我们看不到状态变化。

demo=# COMMIT AND CHAIN;
COMMIT AND CHAIN
postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
---------------------idle in transaction
(1 row)

当我们执行 ROLLBACK AND CHAIN 时,我们得到完全相同的行为 — 没有明显的状态改变。

demo=# ROLLBACK AND CHAIN;
ROLLBACK AND CHAIN
postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
---------------------idle in transaction
(1 row)

最后,当我们发出正常的COMMITROLLBACK时,状态就会变回初始的空闲状态。

demo=# COMMIT;
COMMIT
postgres=# SELECT state FROM pg_stat_activity WHERE datname='demo';state
-------idle
(1 row)

功能实现源码分析

其语法格式如下:

// src/backend/parser/gram.y/*******************************************************************************		Transactions:**		BEGIN / COMMIT / ROLLBACK*		(also older versions END / ABORT)******************************************************************************/TransactionStmt:ABORT_P opt_transaction opt_transaction_chain{TransactionStmt *n = makeNode(TransactionStmt);n->kind = TRANS_STMT_ROLLBACK;n->options = NIL;n->chain = $3;n->location = -1;$$ = (Node *) n;}...| COMMIT opt_transaction opt_transaction_chain{TransactionStmt *n = makeNode(TransactionStmt);n->kind = TRANS_STMT_COMMIT;n->options = NIL;n->chain = $3;n->location = -1;$$ = (Node *) n;}| ROLLBACK opt_transaction opt_transaction_chain{TransactionStmt *n = makeNode(TransactionStmt);n->kind = TRANS_STMT_ROLLBACK;n->options = NIL;n->chain = $3;n->location = -1;$$ = (Node *) n;}...;TransactionStmtLegacy:...| END_P opt_transaction opt_transaction_chain{TransactionStmt *n = makeNode(TransactionStmt);n->kind = TRANS_STMT_COMMIT;n->options = NIL;n->chain = $3;n->location = -1;$$ = (Node *) n;};opt_transaction_chain:AND CHAIN		{ $$ = true; }| AND NO CHAIN	{ $$ = false; }| /* EMPTY */	{ $$ = false; };

示例一,如下:

在这里插入图片描述
在这里插入图片描述


示例二,如下:

在这里插入图片描述
在这里插入图片描述


源码调试案例分析

接下来,我们调试一下 重点看一下上面的示例二,如下:

在这里插入图片描述

如上,begin READ ONLY;是在上图将guc参数transaction_read_only设置为真 XactReadOnly = true,函数堆栈,如下:

set_config_with_handle(const char * name, config_handle * handle, const char * value, GucContext context, GucSource source, Oid srole, GucAction action, _Bool changeVal, int elevel, _Bool is_reload) (\home\postgres\postgres\src\backend\utils\misc\guc.c:3758)
set_config_option(const char * name, const char * value, GucContext context, GucSource source, GucAction action, _Bool changeVal, int elevel, _Bool is_reload) (\home\postgres\postgres\src\backend\utils\misc\guc.c:3361)
SetPGVariable(const char * name, List * args, _Bool is_local) (\home\postgres\postgres\src\backend\utils\misc\guc_funcs.c:320)
standard_ProcessUtility(PlannedStmt * pstmt, const char * queryString, _Bool readOnlyTree, ProcessUtilityContext context, ParamListInfo params, QueryEnvironment * queryEnv, DestReceiver * dest, QueryCompletion * qc) (\home\postgres\postgres\src\backend\tcop\utility.c:619)
ProcessUtility(PlannedStmt * pstmt, const char * queryString, _Bool readOnlyTree, ProcessUtilityContext context, ParamListInfo params, QueryEnvironment * queryEnv, DestReceiver * dest, QueryCompletion * qc) (\home\postgres\postgres\src\backend\tcop\utility.c:523)
PortalRunUtility(Portal portal, PlannedStmt * pstmt, _Bool isTopLevel, _Bool setHoldSnapshot, DestReceiver * dest, QueryCompletion * qc) (\home\postgres\postgres\src\backend\tcop\pquery.c:1158)
PortalRunMulti(Portal portal, _Bool isTopLevel, _Bool setHoldSnapshot, DestReceiver * dest, DestReceiver * altdest, QueryCompletion * qc) (\home\postgres\postgres\src\backend\tcop\pquery.c:1315)
PortalRun(Portal portal, long count, _Bool isTopLevel, _Bool run_once, DestReceiver * dest, DestReceiver * altdest, QueryCompletion * qc) (\home\postgres\postgres\src\backend\tcop\pquery.c:791)
exec_simple_query(const char * query_string) (\home\postgres\postgres\src\backend\tcop\postgres.c:1274)
PostgresMain(const char * dbname, const char * username) (\home\postgres\postgres\src\backend\tcop\postgres.c:4680)
BackendMain(char * startup_data, size_t startup_data_len) (\home\postgres\postgres\src\backend\tcop\backend_startup.c:105)
postmaster_child_launch(BackendType child_type, char * startup_data, size_t startup_data_len, ClientSocket * client_sock) (\home\postgres\postgres\src\backend\postmaster\launch_backend.c:265)
BackendStartup(ClientSocket * client_sock) (\home\postgres\postgres\src\backend\postmaster\postmaster.c:3593)
ServerLoop() (\home\postgres\postgres\src\backend\postmaster\postmaster.c:1674)
PostmasterMain(int argc, char ** argv) (\home\postgres\postgres\src\backend\postmaster\postmaster.c:1372)
main(int argc, char ** argv) (\home\postgres\postgres\src\backend\main\main.c:197)

接下来,这里将直接INSERT,报错如下:

在这里插入图片描述

后续处理,如下:

在这里插入图片描述

此时的函数堆栈,如下:

AtEOXact_GUC(_Bool isCommit, int nestLevel)
AbortTransaction()
AbortCurrentTransactionInternal()
AbortCurrentTransaction()
PostgresMain(const char * dbname, const char * username)
BackendMain(char * startup_data, size_t startup_data_len)
postmaster_child_launch(BackendType child_type, char * startup_data, size_t startup_data_len, ClientSocket * client_sock)
BackendStartup(ClientSocket * client_sock)
ServerLoop()
PostmasterMain(int argc, char ** argv)
main(int argc, char ** argv)

注:如上 在INSERT报错之后,该事务对应的上述GUC被重置,如下:

// src/backend/utils/misc/guc.c/** Do GUC processing at transaction or subtransaction commit or abort, or* when exiting a function that has proconfig settings, or when undoing a* transient assignment to some GUC variables.  (The name is thus a bit of* a misnomer; perhaps it should be ExitGUCNestLevel or some such.)* During abort, we discard all GUC settings that were applied at nesting* levels >= nestLevel.  nestLevel == 1 corresponds to the main transaction.*  * 在事务或子事务提交或中止时,或在退出具有 proconfig 设置的函数时,或在撤消对某些 GUC 变量的临时分配时,执行 GUC 处理* (因此,这个名字有点用词不当;也许应该是 ExitGUCNestLevel 或类似的名字)* 在中止期间,我们会丢弃在嵌套级别 >= nestLevel 处应用的所有 GUC 设置* nestLevel == 1 对应于主事务*/
void
AtEOXact_GUC(bool isCommit, int nestLevel);

于是在接下来的commit and chain;中,XactReadOnly仍是假,如下:

在这里插入图片描述

此时函数堆栈,如下:

EndTransactionBlock(_Bool chain)
standard_ProcessUtility(PlannedStmt * pstmt, const char * queryString, _Bool readOnlyTree, ProcessUtilityContext context, ParamListInfo params, QueryEnvironment * queryEnv, DestReceiver * dest, QueryCompletion * qc)
ProcessUtility(PlannedStmt * pstmt, const char * queryString, _Bool readOnlyTree, ProcessUtilityContext context, ParamListInfo params, QueryEnvironment * queryEnv, DestReceiver * dest, QueryCompletion * qc)
PortalRunUtility(Portal portal, PlannedStmt * pstmt, _Bool isTopLevel, _Bool setHoldSnapshot, DestReceiver * dest, QueryCompletion * qc) 
PortalRunMulti(Portal portal, _Bool isTopLevel, _Bool setHoldSnapshot, DestReceiver * dest, DestReceiver * altdest, QueryCompletion * qc)
PortalRun(Portal portal, long count, _Bool isTopLevel, _Bool run_once, DestReceiver * dest, DestReceiver * altdest, QueryCompletion * qc)
exec_simple_query(const char * query_string)
...

接下来,我们调试一下上面的示例二的另一种情况,因为当前会话已经设置该GUC参数为真(将要被rollback或者commit的事务),接下来的rollback and chain的处理 如下:

在这里插入图片描述

UserAbortTransactionBlock(_Bool chain) (\home\postgres\postgres\src\backend\access\transam\xact.c:4262)
standard_ProcessUtility(PlannedStmt * pstmt, const char * queryString, _Bool readOnlyTree, ProcessUtilityContext context, ParamListInfo params, QueryEnvironment * queryEnv, DestReceiver * dest, QueryCompletion * qc)
ProcessUtility(PlannedStmt * pstmt, const char * queryString, _Bool readOnlyTree, ProcessUtilityContext context, ParamListInfo params, QueryEnvironment * queryEnv, DestReceiver * dest, QueryCompletion * qc)
PortalRunUtility(Portal portal, PlannedStmt * pstmt, _Bool isTopLevel, _Bool setHoldSnapshot, DestReceiver * dest, QueryCompletion * qc)
PortalRunMulti(Portal portal, _Bool isTopLevel, _Bool setHoldSnapshot, DestReceiver * dest, DestReceiver * altdest, QueryCompletion * qc)
PortalRun(Portal portal, long count, _Bool isTopLevel, _Bool run_once, DestReceiver * dest, DestReceiver * altdest, QueryCompletion * qc)
exec_simple_query(const char * query_string)
...

在UserAbortTransactionBlock函数中的处理,如下:

s->blockState: TBLOCK_INPROGRESS -> TBLOCK_ABORT_PENDING
s->chain: false -> true

然后进入如下的处理逻辑:

CommitTransactionCommandInternal()
CommitTransactionCommand()
finish_xact_command()
exec_simple_query(const char * query_string)
...
			/** Here we were in a perfectly good transaction block but the user* told us to ROLLBACK anyway.  We have to abort the transaction* and then clean up.*/case TBLOCK_ABORT_PENDING:AbortTransaction();CleanupTransaction();s->blockState = TBLOCK_DEFAULT;if (s->chain){StartTransaction();s->blockState = TBLOCK_INPROGRESS;s->chain = false;RestoreTransactionCharacteristics(&savetc);}break;

首先进入AbortTransaction函数,因为在这种情况下guc_stack_list != NIL,在如下的堆栈处理中 该参数XactReadOnly被置为假:

AtEOXact_GUC(_Bool isCommit, int nestLevel)
AbortTransaction()
CommitTransactionCommandInternal()
CommitTransactionCommand()
finish_xact_command()
exec_simple_query(const char * query_string)
...

在这里插入图片描述


接着进入CleanupTransaction函数进行清理!


接下来进入今天的重点,如下:

			if (s->chain){StartTransaction();s->blockState = TBLOCK_INPROGRESS;s->chain = false;RestoreTransactionCharacteristics(&savetc);}

因为chain为真,这里还是再重启一个事务。不过这种类似于XactReadOnly的guc参数在StartTransaction过程中仍被赋值默认值!该参数的重新修改如下:

在这里插入图片描述

至此,rollback and chain 操作回滚了上一个事务,并开启新的事务 且XactReadOnly = true,得以保留!


同上面rollback and chain操作一样,其他几种 如下:

// src/backend/access/transam/xact.c/**	CommitTransactionCommandInternal - a function doing an iteration of work*		regarding handling the commit transaction command.  In the case of*		subtransactions more than one iterations could be required.  Returns*		true when no more iterations required, false otherwise.*/
static bool
CommitTransactionCommandInternal(void)
{.../** We are completing a "COMMIT" command.  Do it and return to the* idle state.*/case TBLOCK_END:CommitTransaction();s->blockState = TBLOCK_DEFAULT;if (s->chain)				// here{StartTransaction();s->blockState = TBLOCK_INPROGRESS;s->chain = false;RestoreTransactionCharacteristics(&savetc);}break;.../** Here we were in an aborted transaction block and we just got* the ROLLBACK command from the user, so clean up the* already-aborted transaction and return to the idle state.*/case TBLOCK_ABORT_END:CleanupTransaction();s->blockState = TBLOCK_DEFAULT;if (s->chain)				// here{StartTransaction();s->blockState = TBLOCK_INPROGRESS;s->chain = false;RestoreTransactionCharacteristics(&savetc);}break;.../** Here we were in a perfectly good transaction block but the user* told us to ROLLBACK anyway.  We have to abort the transaction* and then clean up.*/case TBLOCK_ABORT_PENDING:AbortTransaction();CleanupTransaction();s->blockState = TBLOCK_DEFAULT;if (s->chain)				// here{StartTransaction();s->blockState = TBLOCK_INPROGRESS;s->chain = false;RestoreTransactionCharacteristics(&savetc);}break;.../** The user issued a COMMIT, so we end the current subtransaction* hierarchy and perform final commit. We do this by rolling up* any subtransactions into their parent, which leads to O(N^2)* operations with respect to resource owners - this isn't that* bad until we approach a thousands of savepoints but is* necessary for correctness should after triggers create new* resource owners.*/case TBLOCK_SUBCOMMIT:do{CommitSubTransaction();s = CurrentTransactionState;	/* changed by pop */} while (s->blockState == TBLOCK_SUBCOMMIT);/* If we had a COMMIT command, finish off the main xact too */if (s->blockState == TBLOCK_END){Assert(s->parent == NULL);CommitTransaction();s->blockState = TBLOCK_DEFAULT;if (s->chain)				// here{StartTransaction();s->blockState = TBLOCK_INPROGRESS;s->chain = false;RestoreTransactionCharacteristics(&savetc);}}else if (s->blockState == TBLOCK_PREPARE){Assert(s->parent == NULL);PrepareTransaction();s->blockState = TBLOCK_DEFAULT;}elseelog(ERROR, "CommitTransactionCommand: unexpected state %s",BlockStateAsString(s->blockState));break;...
}

对应非特殊的guc参数,能否可以继承呢?如下:

[postgres@localhost:~/test/bin]$ ./psql 
psql (17beta2)
Type "help" for help.postgres=# show timezone;TimeZone       
---------------------America/Los_Angeles
(1 row)postgres=# begin;
BEGIN
postgres=*# set timezone = 'PRC';
SET
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*# commit and chain; ## commit 提交 && 继承
COMMIT
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*# rollback and chain; ## 无东西可以回滚
ROLLBACK
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*#
[postgres@localhost:~/test/bin]$ ./psql 
psql (17beta2)
Type "help" for help.postgres=# show timezone;TimeZone       
---------------------America/Los_Angeles
(1 row)postgres=# begin;
BEGIN
postgres=*# desc a error;
2024-07-01 06:19:56.969 PDT [34810] ERROR:  syntax error at or near "desc" at character 1
2024-07-01 06:19:56.969 PDT [34810] STATEMENT:  desc a error;
ERROR:  syntax error at or near "desc"
LINE 1: desc a error;^
postgres=!# show timezone;
2024-07-01 06:20:00.721 PDT [34810] ERROR:  current transaction is aborted, commands ignored until end of transaction block
2024-07-01 06:20:00.721 PDT [34810] STATEMENT:  show timezone;
ERROR:  current transaction is aborted, commands ignored until end of transaction block
postgres=!# 
postgres=!# commit and chain; ## commit 这里相当于先回滚 && 继承
ROLLBACK
postgres=*# show timezone;TimeZone       
---------------------America/Los_Angeles
(1 row)postgres=*# set timezone = 'PRC';
SET
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*# commit and chain; ## commit 提交 && 继承
COMMIT
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*# rollback and chain; ## 无东西可以回滚
ROLLBACK
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*# reset timezone;
RESET
postgres=*# show timezone;TimeZone       
---------------------America/Los_Angeles
(1 row)postgres=*# rollback and chain; ## rollback 这里相当于先回滚 && 继承
ROLLBACK
postgres=*# show timezone;TimeZone 
----------PRC
(1 row)postgres=*#

相关文章:

PostgreSQL的学习心得和知识总结(一百四十七)|深入理解PostgreSQL数据库之transaction chain的使用和实现

目录结构 注:提前言明 本文借鉴了以下博主、书籍或网站的内容,其列表如下: 1、参考书籍:《PostgreSQL数据库内核分析》 2、参考书籍:《数据库事务处理的艺术:事务管理与并发控制》 3、PostgreSQL数据库仓库…...

宝塔linux网站迁移步骤

网站迁移到新服务器步骤 1.宝塔网站迁移,有个一键迁移工具,参考官网 宝塔一键迁移API版本 3.0版本教程 - Linux面板 - 宝塔面板论坛 (bt.cn)2 2.修改域名解析为新ip 3.如果网站没有域名,而是用ip访问的,则新宝塔数据库的wp_o…...

电路笔记(三极管器件): MOSFETIGBT

MOSFET vs IGBT MOSFET主要用于低电压和功率系统,而IGBT更适合高电压和功率系统。 1. MOSFET(金属氧化物半导体场效应晶体管) 优势: 高开关速度和响应速度,适合高频应用。(IGBT不适合高频应用&#xff0c…...

Docker 镜像导出和导入

docker 镜像导出 # 导出 docker 镜像到本地文件 docker save -o [输出文件名.tar] [镜像名称[:标签]] # 示例 docker save -o minio.tar minio/minio:latest-o 或 --output:指定导出文件的路径和名称[镜像名称[:标签]]:导出镜像名称以及可选的标签 dock…...

QueryClientProvider is not defined

QueryClientProvider is not defined 运行一个svelte的项目,报错如上,前后查找解决不了,然后没办法, 本来是用yarn 安装的依赖,改用npm install,再次运行就成功了...

HTTPS是什么?原理是什么?用公钥加密为什么不能用公钥解密?

HTTPS(HyperText Transfer Protocol Secure)是HTTP的安全版本,它通过在HTTP协议之上加入SSL/TLS协议来实现数据加密传输,确保数据在客户端和服务器之间的传输过程中不会被窃取或篡改。 HTTPS 的工作原理 客户端发起HTTPS请求&…...

系统中非功能性需求的思考

概要 设计系统时不仅要考虑功能性需求,还要考虑一些非功能性需求,比如: 扩展性可靠性和冗余安全和隐私服务依赖SLA要求 下面对这5项需要考虑的事项做个简单的说明 1. 可扩展性 数据量增长如何扩展? 流量增长如何扩展&#xf…...

力扣第215题“数组中的第K个最大元素”

在本篇文章中,我们将详细解读力扣第215题“数组中的第K个最大元素”。通过学习本篇文章,读者将掌握如何使用快速选择算法和堆排序来解决这一问题,并了解相关的复杂度分析和模拟面试问答。每种方法都将配以详细的解释,以便于理解。…...

java.util.function实现原理和Java使用场景【Function、Predicate集合转换过滤,BiConsumer事件处理】

简介 java.util.function 是 Java 8 引入的一个功能包,它包含了多种函数式接口的定义,使得在 Java 中进行函数式编程变得更为方便。下面我将分别介绍 java.util.function 的作用、实现原理、常用 Java 使用场景以及代码示例。 作用 java.util.function 的主要作用是为 Jav…...

《每天5分钟用Flask搭建一个管理系统》 第6章:数据库集成

第6章:数据库集成 6.1 数据库的选择和配置 在Flask中集成数据库,首先需要选择一个数据库系统。常见的选择包括SQLite、MySQL、PostgreSQL等。选择后,需要配置数据库连接字符串。 示例代码:配置数据库 from flask import Flask…...

pandas读取和处理Excel文件的基础应用1

Pandas如何读取Excel文件并处理数据 引言: Pandas是一种常用的数据处理和分析工具,它提供了丰富的函数和方法,方便用户对数据进行清洗、转换和分析。在实际工作中,我们经常需要处理Excel格式的数据文件,本文将介绍如何…...

electron vite react 创建一个项目

要使用 Electron、Vite 和 React 创建一个项目,你可以按照以下步骤操作: 1. 安装 Node.js 和 npm 首先,确保你的计算机上安装了 Node.js 和 npm(Node Package Manager)。你可以从 Node.js 官网 下载并安装。 2. 初始化一个新的项目 在你的工作目录下,创建一个新的文件…...

鸿蒙使用 @Builder扩展出来的布局数据更新没法更新UI

由于业务的复杂,所以我们把相关UI抽离出来。但是数据变化了,没法更新UI Builder MyGridLayout() { } 通过日志打印发现数据的确是更新了,但是UI就没没办法,如何解决呢 Entry Component struct Page35 {// State sArray: bool…...

湖南省教育网络协会莅临麒麟信安调研教育网络数字化建设及教育信创发展情况

6月28日下午,湖南省教育网络协会理事长张智勇、秘书长刘志勇、副理事长黄旭、胡洪波、周中伟等协会相关负责人一行莅临麒麟信安,就湖南省教育网络数字化建设、教育信创工作等主题进行深入调研。麒麟信安副总裁王攀热情接待。 协会成员一行来到麒麟信安展…...

论文阅读_优化RAG系统的检索

英文名称: The Power of Noise: Redefining Retrieval for RAG Systems 中文名称: 噪声的力量:重新定义RAG系统的检索 链接: https://arxiv.org/pdf/2401.14887.pdf 作者: Florin Cuconasu, Giovanni Trappolini, Federico Siciliano, Simone Filice, Cesare Campag…...

STC8/32 软硬件I2C通讯方式扫描I2C设备地址

STC8/32 软硬件I2C通讯方式扫描I2C设备地址 📄主要用于检测挂载在I2C总线上的设备。在驱动I2C设备之前,如果能扫描到该设备,说明通讯设备可以连接的上,在提前未知I2C地址的情况下,可以方便后面的驱动代码的完善。 🔬扫描测试效果:(测试mpu6050以及ssd1306 i2c oled )…...

Linux——数据流和重定向,制作镜像

1. 数据流 标准输入( standard input ,简称 stdin ):默认情况下,标准输入指从键盘获取的输入 标准输出( standard output ,简称 stdout ):默认情况下,命令…...

Windows 11的市场份额越来越大了,推荐你升级!

7月1日,系统之家发布最新数据,显示Windows 11操作系统的市场份额正在稳步上升。自2021年10月Windows 11发布以来,Windows 10一直占据着市场主导地位,当时其市场份额高达81.44%。然而,随着时间的推移,Window…...

微服务架构中的调试难题与分布式事务解决方案

微服务架构作为现代软件开发的一种主要趋势,因其灵活性、高可维护性和易于扩展的特点,得到了广泛的应用。然而,在享受微服务架构带来的诸多优点的同时,开发者也面临着一些新的挑战。调试的复杂性和分布式事务的处理是其中两个较为…...

银行家算法-操作系统中避免死锁的最著名算法

背景 有很多文章都会介绍银行家算法。在百度和CSDN上搜一搜能搜出很多来。很多同学会觉得这个算法很深奥,有些文章写的又很复杂,其实真的很简单。这里简单记录一下基本原理,然后大家再配合其他文章看,就能加深理解。 算法原理 …...

gopool 源码分析

gopool gopool是字节跳动开源节流的gopkg包中协程池的一个实现。 关键结构 协程池: type pool struct {// The name of the poolname string// capacity of the pool, the maximum number of goroutines that are actually working// 协程池的最大容量cap int32…...

ROS2,工作空间中新建了一个python脚本,需要之后作为节点运行。告诉我步骤?

提问 ROS2,工作空间中新建了一个python脚本,需要之后运行。告诉我步骤? 大概要包括而不限于:chmod给可执行权限、setup.py中entry point的配置,如果在launch文件中要使用,还涉及到launch.py文件的配置。最…...

ubuntu显示器未知

在Ubuntu系统中,当外接显示器被识别为“未知设备”时,可通过以下日志文件进行问题诊断,结合Xorg日志和内核日志综合分析: 🔍 一、查看Xorg显示服务日志(核心) Xorg日志记录了图形界面的详细事…...

元器件基础学习笔记——结型场效应晶体管 (JFET)

场效应晶体管(Field Effect Transistor,FET)简称场效应管,是一种三端子半导体器件,它根据施加到其其中一个端子的电场来控制电流的流动。与双极结型晶体管 (BJT) 不同,场效应晶体管 …...

libiec61850 mms协议异步模式

之前项目中使用到libiec61850库,都是服务端开发。这次新的需求要接收服务端的遥测数据,这就涉及到客户端开发了。 客户端开发没搞过啊,挑战不少,但是人不就是通过战胜困难才成长的嘛。通过查看libiec61850的客户端API发现&#xf…...

Qt/C++学习系列之Excel使用记录

Qt/C学习系列之Excel使用记录 前言The process was ended forcefully.解决方式断点查语句问题 总结 前言 在项目中解析条目达50多条,并且都需要将对应的结果进行显示。为了将结果显示的更加清晰,考虑采用QTableWidget进行表格设置,而在使用过…...

【storage】

文章目录 1、RAM and ROM2、DRAM and SRAM2、Flash Memory(闪存)4、DDR and SPI NOR Flash5、eMMC6、SPI NOR vs SPI NAND vs eMMC vs SD附录——prototype and demo board附录——U盘、SD卡、TF卡、SSD参考 1、RAM and ROM RAM(Random Acce…...

IDEA 打开文件乱码

问题:文件乱码 底部编码无法切换 解决方案: 第一步 使用Nodepad 查询文件编码 本项目设置为 转为 UTF-8 无 BOM 第二步:在 IntelliJ IDEA 中:右键点击文件 → File Encoding → 选择目标编码(如 UTF-8) 最…...

STM32——CAN总线

STM32——CAN总线 1. CAN总线基础概念 1.1 CAN总线简介 控制器局域网(Controller Area Network, CAN)是由Bosch公司开发的串行通信协议,专为汽车电子和工业控制设计,具有以下核心特性: 多主控制架构:所有…...

2025年渗透测试面试题总结-ali 春招内推电话1面(题目+回答)

安全领域各种资源,学习文档,以及工具分享、前沿信息分享、POC、EXP分享。不定期分享各种好玩的项目及好用的工具,欢迎关注。 目录 ali 春招内推电话1面 一、Web安全核心理解 二、熟悉漏洞及防御方案 三、UDF提权原理与防御 四、XSS Fuzz…...