mysql8 从C++源码角度看 Statement cancelled due to timeout or client request异常

##Statement cancelled due to timeout or client request 异常

Caused by: com.mysql.jdbc.exceptions.MySQLTimeoutException: Statement cancelled due to timeout or client requestat com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1932)at com.mysql.jdbc.PreparedStatement.execute(PreparedStatement.java:1251)at com.alibaba.druid.filter.FilterChainImpl.preparedStatement_execute(FilterChainImpl.java:3461)at com.alibaba.druid.filter.FilterEventAdapter.preparedStatement_execute(FilterEventAdapter.java:440)at com.alibaba.druid.filter.FilterChainImpl.preparedStatement_execute(FilterChainImpl.java:3459)at com.alibaba.druid.filter.FilterAdapter.preparedStatement_execute(FilterAdapter.java:1081)at com.alibaba.druid.filter.FilterChainImpl.preparedStatement_execute(FilterChainImpl.java:3459)at com.alibaba.druid.filter.FilterEventAdapter.preparedStatement_execute(FilterEventAdapter.java:440)at com.alibaba.druid.filter.FilterChainImpl.preparedStatement_execute(FilterChainImpl.java:3459)at com.alibaba.druid.proxy.jdbc.PreparedStatementProxyImpl.execute(PreparedStatementProxyImpl.java:167)at com.alibaba.druid.pool.DruidPooledPreparedStatement.execute(DruidPooledPreparedStatement.java:497)at sun.reflect.GeneratedMethodAccessor101.invoke(Unknown Source)at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)at java.lang.reflect.Method.invoke(Method.java:498)at org.apache.ibatis.logging.jdbc.PreparedStatementLogger.invoke(PreparedStatementLogger.java:59)at com.sun.proxy.$Proxy60.execute(Unknown Source)at org.apache.ibatis.executor.statement.PreparedStatementHandler.query(PreparedStatementHandler.java:63)at org.apache.ibatis.executor.statement.RoutingStatementHandler.query(RoutingStatementHandler.java:79)at org.apache.ibatis.executor.ReuseExecutor.doQuery(ReuseExecutor.java:60)at org.apache.ibatis.executor.BaseExecutor.queryFromDatabase(BaseExecutor.java:324)at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:156)at org.apache.ibatis.executor.BaseExecutor.query(BaseExecutor.java:136)at sun.reflect.GeneratedMethodAccessor56.invoke(Unknown Source)at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)at java.lang.reflect.Method.invoke(Method.java:498)at org.apache.ibatis.plugin.Plugin.invoke(Plugin.java:63)at com.sun.proxy.$Proxy58.query(Unknown Source)at sun.reflect.GeneratedMethodAccessor56.invoke(Unknown Source)at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)at java.lang.reflect.Method.invoke(Method.java:498)at org.apache.ibatis.plugin.Plugin.invoke(Plugin.java:63)at com.sun.proxy.$Proxy58.query(Unknown Source)at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:148)at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:141)at org.apache.ibatis.session.defaults.DefaultSqlSession.selectList(DefaultSqlSession.java:136)at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)at java.lang.reflect.Method.invoke(Method.java:498)at org.mybatis.spring.SqlSessionTemplate$SqlSessionInterceptor.invoke(SqlSessionTemplate.java:433)

##5.1.48mysql驱动包 sql 语句超时设置

/*** Sets the queryTimeout limit* * @param seconds*            -*            the new query timeout limit in seconds* * @exception SQLException*                if a database access error occurs*/public void setQueryTimeout(int seconds) throws SQLException {synchronized (checkClosed().getConnectionMutex()) {if (seconds < 0) {throw SQLError.createSQLException(Messages.getString("Statement.21"), SQLError.SQL_STATE_ILLEGAL_ARGUMENT, getExceptionInterceptor());}this.timeoutInMillis = seconds * 1000;}}

自定义的 CancelTask 类,它继承自 TimerTask 类,用于在 Java 应用程序中取消 MySQL 数据库中的查询任务。这个类是 JDBC 驱动程序的一部分,用于处理查询超时的情况。以下是代码的主要功能和流程:

  1. 构造函数 (CancelTask(StatementImpl cancellee)):

    • 接收一个 StatementImpl 对象作为参数,这个对象代表需要被取消的 SQL 语句。
    • 复制连接的属性到 origConnProps 属性集合中。
    • 保存原始连接的 URL 和 ID。
  2. run 方法

    • 这个方法是 TimerTask 的核心,当定时器触发时会调用此方法。
    • 创建一个新的线程 cancelThread 来执行取消操作,以避免阻塞定时器线程。
  3. cancelThread 线程

    • 在这个线程中,尝试获取物理连接 physicalConn
    • 如果连接支持超时后关闭(getQueryTimeoutKillsConnection() 返回 true),则标记 SQL 语句为已取消,并关闭连接。
    • 如果连接不支持,尝试使用原始连接的属性和 URL 重新建立连接,并执行 KILL QUERY 命令来取消查询。
    • 如果在尝试重新连接时捕获到 NullPointerException,则忽略,因为这意味着连接已经关闭,查询已经超时。
  4. 异常处理

    • 捕获 SQLException 和 NullPointerException,并在 caughtWhileCancelling 变量中保存 SQLException
    • 在 finally 块中,关闭 cancelStmt 和 cancelConn,并清理 CancelTask 对象的引用。

这个类的主要目的是在查询超时时提供一个机制来取消正在执行的 SQL 查询。这是 JDBC 驱动程序中的一个高级特性,允许应用程序在查询执行时间过长时中断查询,以避免资源长时间占用。这种机制对于需要处理大量数据或执行复杂查询的应用程序尤其重要,因为它可以帮助提高应用程序的响应性和资源利用率。

##执行查询语句,设置超时任务timeoutTask = new CancelTask(this);

timeoutInMillis毫秒后,调度任务
  locallyScopedConn.getCancelTimer().schedule(timeoutTask, this.timeoutInMillis);

private boolean executeInternal(String sql, boolean returnGeneratedKeys) throws SQLException {MySQLConnection locallyScopedConn = checkClosed();synchronized (locallyScopedConn.getConnectionMutex()) {checkClosed();checkNullOrEmptyQuery(sql);resetCancelledState();implicitlyCloseAllOpenResults();if (sql.charAt(0) == '/') {if (sql.startsWith(PING_MARKER)) {doPingInstead();return true;}}char firstNonWsChar = StringUtils.firstAlphaCharUc(sql, findStartOfStatement(sql));boolean maybeSelect = firstNonWsChar == 'S';this.retrieveGeneratedKeys = returnGeneratedKeys;this.lastQueryIsOnDupKeyUpdate = returnGeneratedKeys && firstNonWsChar == 'I' && containsOnDuplicateKeyInString(sql);if (!maybeSelect && locallyScopedConn.isReadOnly()) {throw SQLError.createSQLException(Messages.getString("Statement.27") + Messages.getString("Statement.28"), SQLError.SQL_STATE_ILLEGAL_ARGUMENT,getExceptionInterceptor());}boolean readInfoMsgState = locallyScopedConn.isReadInfoMsgEnabled();if (returnGeneratedKeys && firstNonWsChar == 'R') {// If this is a 'REPLACE' query, we need to be able to parse the 'info' message returned from the server to determine the actual number of keys// generated.locallyScopedConn.setReadInfoMsgEnabled(true);}try {setupStreamingTimeout(locallyScopedConn);if (this.doEscapeProcessing) {Object escapedSqlResult = EscapeProcessor.escapeSQL(sql, locallyScopedConn.serverSupportsConvertFn(), locallyScopedConn);if (escapedSqlResult instanceof String) {sql = (String) escapedSqlResult;} else {sql = ((EscapeProcessorResult) escapedSqlResult).escapedSql;}}CachedResultSetMetaData cachedMetaData = null;ResultSetInternalMethods rs = null;this.batchedGeneratedKeys = null;if (useServerFetch()) {rs = createResultSetUsingServerFetch(sql);} else {CancelTask timeoutTask = null;String oldCatalog = null;try {if (locallyScopedConn.getEnableQueryTimeouts() && this.timeoutInMillis != 0 && locallyScopedConn.versionMeetsMinimum(5, 0, 0)) {timeoutTask = new CancelTask(this);locallyScopedConn.getCancelTimer().schedule(timeoutTask, this.timeoutInMillis);}if (!locallyScopedConn.getCatalog().equals(this.currentCatalog)) {oldCatalog = locallyScopedConn.getCatalog();locallyScopedConn.setCatalog(this.currentCatalog);}//// Check if we have cached metadata for this query...//Field[] cachedFields = null;if (locallyScopedConn.getCacheResultSetMetadata()) {cachedMetaData = locallyScopedConn.getCachedMetaData(sql);if (cachedMetaData != null) {cachedFields = cachedMetaData.fields;}}//// Only apply max_rows to selects//locallyScopedConn.setSessionMaxRows(maybeSelect ? this.maxRows : -1);statementBegins();rs = locallyScopedConn.execSQL(this, sql, this.maxRows, null, this.resultSetType, this.resultSetConcurrency, createStreamingResultSet(),this.currentCatalog, cachedFields);if (timeoutTask != null) {if (timeoutTask.caughtWhileCancelling != null) {throw timeoutTask.caughtWhileCancelling;}timeoutTask.cancel();timeoutTask = null;}synchronized (this.cancelTimeoutMutex) {if (this.wasCancelled) {SQLException cause = null;if (this.wasCancelledByTimeout) {cause = new MySQLTimeoutException();} else {cause = new MySQLStatementCancelledException();}resetCancelledState();throw cause;}}} finally {if (timeoutTask != null) {timeoutTask.cancel();locallyScopedConn.getCancelTimer().purge();}if (oldCatalog != null) {locallyScopedConn.setCatalog(oldCatalog);}}}if (rs != null) {this.lastInsertId = rs.getUpdateID();this.results = rs;rs.setFirstCharOfQuery(firstNonWsChar);if (rs.reallyResult()) {if (cachedMetaData != null) {locallyScopedConn.initializeResultsMetadataFromCache(sql, cachedMetaData, this.results);} else {if (this.connection.getCacheResultSetMetadata()) {locallyScopedConn.initializeResultsMetadataFromCache(sql, null /* will be created */, this.results);}}}}return ((rs != null) && rs.reallyResult());} finally {locallyScopedConn.setReadInfoMsgEnabled(readInfoMsgState);this.statementExecuting.set(false);}}}

##发送 cancelStmt.execute("KILL QUERY " + physicalConn.getId());  给mysql服务端

class CancelTask extends TimerTask {SQLException caughtWhileCancelling = null;StatementImpl toCancel;Properties origConnProps = null;String origConnURL = "";long origConnId = 0;CancelTask(StatementImpl cancellee) throws SQLException {this.toCancel = cancellee;this.origConnProps = new Properties();Properties props = StatementImpl.this.connection.getProperties();Enumeration<?> keys = props.propertyNames();while (keys.hasMoreElements()) {String key = keys.nextElement().toString();this.origConnProps.setProperty(key, props.getProperty(key));}this.origConnURL = StatementImpl.this.connection.getURL();this.origConnId = StatementImpl.this.connection.getId();}@Overridepublic void run() {Thread cancelThread = new Thread() {@Overridepublic void run() {Connection cancelConn = null;java.sql.Statement cancelStmt = null;try {MySQLConnection physicalConn = StatementImpl.this.physicalConnection.get();if (physicalConn != null) {if (physicalConn.getQueryTimeoutKillsConnection()) {CancelTask.this.toCancel.wasCancelled = true;CancelTask.this.toCancel.wasCancelledByTimeout = true;physicalConn.realClose(false, false, true,new MySQLStatementCancelledException(Messages.getString("Statement.ConnectionKilledDueToTimeout")));} else {synchronized (StatementImpl.this.cancelTimeoutMutex) {if (CancelTask.this.origConnURL.equals(physicalConn.getURL())) {// All's finecancelConn = physicalConn.duplicate();cancelStmt = cancelConn.createStatement();cancelStmt.execute("KILL QUERY " + physicalConn.getId());} else {try {cancelConn = (Connection) DriverManager.getConnection(CancelTask.this.origConnURL, CancelTask.this.origConnProps);cancelStmt = cancelConn.createStatement();cancelStmt.execute("KILL QUERY " + CancelTask.this.origConnId);} catch (NullPointerException npe) {// Log this? "Failed to connect to " + origConnURL + " and KILL query"}}CancelTask.this.toCancel.wasCancelled = true;CancelTask.this.toCancel.wasCancelledByTimeout = true;}}}} catch (SQLException sqlEx) {CancelTask.this.caughtWhileCancelling = sqlEx;} catch (NullPointerException npe) {// Case when connection closed while starting to cancel.// We can't easily synchronize this, because then one thread can't cancel() a running query.// Ignore, we shouldn't re-throw this, because the connection's already closed, so the statement has been timed out.} finally {if (cancelStmt != null) {try {cancelStmt.close();} catch (SQLException sqlEx) {throw new RuntimeException(sqlEx.toString());}}if (cancelConn != null) {try {cancelConn.close();} catch (SQLException sqlEx) {throw new RuntimeException(sqlEx.toString());}}CancelTask.this.toCancel = null;CancelTask.this.origConnProps = null;CancelTask.this.origConnURL = null;}}};cancelThread.start();}}

##mysql8处理KILL QUERY C++源码

THD 类的 awake 方法,并向其传递了一个参数,这个参数决定了是只杀死查询(THD::KILL_QUERY)还是关闭整个连接(THD::KILL_CONNECTION)。awake 方法的作用是发送一个信号给目标线程,使其停止当前正在执行的操作。

  • 如果 only_kill_query 参数为 true,则传递 THD::KILL_QUERY,这会导致目标线程停止当前的查询操作。
  • 如果 only_kill_query 参数为 false,则传递 THD::KILL_CONNECTION,这会导致目标线程关闭整个连接,包括所有查询。

这个方法是线程间通信的一种方式,用于安全地中断另一个线程的执行。在 MySQL 服务器中,这是处理 KILL 命令的核心部分,允许管理员或有权限的用户终止长时间运行的查询或释放资源。

/**kill on thread.@param thd			Thread class@param id			Thread id@param only_kill_query        Should it kill the query or the connection@noteThis is written such that we have a short lock on LOCK_thd_list
*/static uint kill_one_thread(THD *thd, my_thread_id id, bool only_kill_query) {uint error = ER_NO_SUCH_THREAD;Find_thd_with_id find_thd_with_id(id);DBUG_TRACE;DBUG_PRINT("enter", ("id=%u only_kill=%d", id, only_kill_query));DEBUG_SYNC(thd, "kill_thd_begin");THD_ptr tmp = Global_THD_manager::get_instance()->find_thd(&find_thd_with_id);Security_context *sctx = thd->security_context();if (tmp) {/*If we're SUPER, we can KILL anything, including system-threads.No further checks.KILLer: thd->m_security_ctx->user could in theory be NULL whilewe're still in "unauthenticated" state. This is a theoreticalcase (the code suggests this could happen, so we play it safe).KILLee: tmp->m_security_ctx->user will be NULL for system threads.We need to check so Jane Random User doesn't crash the serverwhen trying to kill a) system threads or b) unauthenticated users'threads (Bug#43748).If user of both killer and killee are non-NULL, proceed withslayage if both are string-equal.*/if (sctx->check_access(SUPER_ACL) ||sctx->has_global_grant(STRING_WITH_LEN("CONNECTION_ADMIN")).first ||sctx->user_matches(tmp->security_context())) {/*Process the kill:if thread is not already undergoing any kill connection.Killer must have SYSTEM_USER privilege iff killee has the same privilegeprivilege*/if (tmp->killed != THD::KILL_CONNECTION) {if (tmp->is_system_user() && !thd->is_system_user()) {error = ER_KILL_DENIED_ERROR;} else {tmp->awake(only_kill_query ? THD::KILL_QUERY : THD::KILL_CONNECTION);error = 0;}} elseerror = 0;} elseerror = ER_KILL_DENIED_ERROR;}DEBUG_SYNC(thd, "kill_thd_end");DBUG_PRINT("exit", ("%d", error));return error;
}/*kills a thread and sends responseSYNOPSISsql_kill()thd			Thread classid			Thread idonly_kill_query     Should it kill the query or the connection
*/static void sql_kill(THD *thd, my_thread_id id, bool only_kill_query) {uint error;if (!(error = kill_one_thread(thd, id, only_kill_query))) {if (!thd->killed) my_ok(thd);} elsemy_error(error, MYF(0), id);
}

##gdb调用栈

(gdb) b sql_kill
#0  kill_one_thread (thd=0x73e42003e450, id=444, only_kill_query=true) at /home/yym/mysql8/mysql-8.1.0/sql/sql_parse.cc:6518
#1  0x00006040ed8ae76a in sql_kill (thd=0x73e42003e450, id=444, only_kill_query=true) at /home/yym/mysql8/mysql-8.1.0/sql/sql_parse.cc:6582
#2  0x00006040ed8a71e1 in mysql_execute_command (thd=0x73e42003e450, first_level=true) at /home/yym/mysql8/mysql-8.1.0/sql/sql_parse.cc:4306
#3  0x00006040ed8aacb3 in dispatch_sql_command (thd=0x73e42003e450, parser_state=0x73e5594f79f0) at /home/yym/mysql8/mysql-8.1.0/sql/sql_parse.cc:5447
#4  0x00006040ed8a00d7 in dispatch_command (thd=0x73e42003e450, com_data=0x73e5594f8340, command=COM_QUERY) at /home/yym/mysql8/mysql-8.1.0/sql/sql_parse.cc:2112
#5  0x00006040ed89df77 in do_command (thd=0x73e42003e450) at /home/yym/mysql8/mysql-8.1.0/sql/sql_parse.cc:1459
#6  0x00006040edaf5835 in handle_connection (arg=0x6040f65a0060) at /home/yym/mysql8/mysql-8.1.0/sql/conn_handler/connection_handler_per_thread.cc:303
#7  0x00006040efa34bdc in pfs_spawn_thread (arg=0x6040f66eb480) at /home/yym/mysql8/mysql-8.1.0/storage/perfschema/pfs.cc:3043
#8  0x000073e569094ac3 in start_thread (arg=<optimized out>) at ./nptl/pthread_create.c:442
#9  0x000073e569126850 in clone3 () at ../sysdeps/unix/sysv/linux/x86_64/clone3.S:81

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/64652.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

SAP HCM 标准报表与前台操作的增强差异逻辑分析(rhgrenz4)

导读 增强差异:SAP的HCM模块组织和人事增强都有标准的增强点&#xff0c;不管你调用标准的函数还是前台操作都会触发对应的增强。所以很多业务不需要考虑那么多分散点&#xff0c;只要找到一个合适的增强点&#xff0c;就能解决很多和外围系统集成的业务逻辑&#xff0c;今天遇…

EZ-USB™ FX3 USB 5 Gbps 外设控制器

EZ-USB™ FX3 USB 5 Gbps 外设控制器 EZ-USB™ FX3 提供 USB 5Gbps 至 32 位数据总线&#xff0c;并配备 ARM9&#xff0c;可为任何系统添加 USB 3.0 连接 英飞凌的 EZ-USB™ FX3 是业界用途最广泛的 USB 外围设备控制器&#xff0c;可以为几乎任何系统添加 USB 5Gbps 连接。 …

【数据仓库】spark大数据处理框架

文章目录 概述架构spark 架构角色下载安装启动pyspark启动spark-sehll启动spark-sqlspark-submit经验 概述 Spark是一个性能优异的集群计算框架&#xff0c;广泛应用于大数据领域。类似Hadoop&#xff0c;但对Hadoop做了优化&#xff0c;计算任务的中间结果可以存储在内存中&a…

数据库容灾备份的意义+分类+执行工具!

数据库容灾解决方案的背景 数据库容灾&#xff08;Disaster Recovery&#xff0c;DR&#xff09;解决方案的背景主要源于企业对数据安全性、业务连续性和系统高可用性的需求。随着数字化转型的加速&#xff0c;企业的数据量迅猛增长&#xff0c;数据库已成为支撑核心业务的关键…

PDF怎么压缩得又小又清晰?5种PDF压缩方法

PDF 文件在日常办公与学习中使用极为频繁&#xff0c;可想要把它压缩得又小又清晰却困难重重。一方面&#xff0c;PDF 格式本身具有高度兼容性&#xff0c;集成了文字、图像、矢量图等多样元素&#xff0c;压缩时难以兼顾不同元素特性&#xff0c;稍不注意&#xff0c;文字就会…

GoldenDB组件及对应的用户和进程

1. GoldenDB组件及对应的用户和进程 GoldenDB数据库由管理节点、全局事务节点GTM、计算节点CN、数据节点DN等组成。 1.1. 管理节点 管理节点分为集群管理、Insight运维管理平台&#xff08;InsightServer、RDB、ZK&#xff09;。 1.1.1. 集群管理 1. 集群管理包括Metadatas…

OpenStack系列第四篇:云平台基础功能与操作(Dashboard)

文章目录 1. 镜像&#xff08;Image&#xff09;添加镜像查看镜像删除镜像 2. 卷&#xff08;Volume&#xff09;创建卷查看卷删除卷 3. 网络&#xff08;虚拟网络&#xff09;创建网络查看网络删除网络 4. 实例类型创建实例类型查看实例类型删除实例类型 4. 密钥对&#xff08…

CSDN编辑器

这里写自定义目录标题 欢迎使用Markdown编辑器新的改变功能快捷键合理的创建标题&#xff0c;有助于目录的生成如何改变文本的样式插入链接与图片如何插入一段漂亮的代码片生成一个适合你的列表创建一个表格设定内容居中、居左、居右SmartyPants 创建一个自定义列表如何创建一个…

四大自平衡树对比:AVL树、红黑树、B树与B+树

AVL树、红黑树、B树和B树的对比与应用场景 树系列相关文章&#xff08;置顶&#xff09; 1、从链表到平衡树&#xff1a;二叉查找树的退化与优化 2、自平衡二叉查找树&#xff1a;如何让二叉查找树始终保持高效 3、AVL树入门&#xff1a;理解自平衡二叉查找树的基础 4、红黑树全…

Linux下读取Windows下保存的文件,报错信息中出现“^M“时如何解决?【由于Windows和Linux的换行方式不同造成的-提供两种转换方式】

Windows 和 Linux 的文本文件使用的换行符不同&#xff1a; Windows 使用 \r\n &#xff08;回车 换行&#xff09;。Linux 使用 \n &#xff08;换行&#xff09;。 因此&#xff0c;当在 Linux 系统上运行带有 Windows 换行符的脚本或读取相关文件时&#xff0c;可能会出现…

npm ERR! ECONNRESET 解决方法

问题&#xff1a;npm 命令遇到的错误是 ECONNRESET&#xff0c;这通常与网络连接问题相关。设置代理解决问题。 一、查看当前代理设置 npm config get proxy npm config get https-proxy二、设置代理 npm config set proxy http://your-proxy-address:port npm config set h…

【UE5】UnrealEngine源码构建2:windows构建unreal engine 5.3.2

参考大神知乎的文章:UE5 小白也能看懂的源码编译指南 据说会耗费400G的空间。 代码本身并不大,可能是依赖特别多,毕竟看起来UE啥都能干,核心还是c++的, 【UE5】UnrealEngine源码构建1:tag为5.3.2源码clone 本着好奇+ 学习的态度,想着也许有机会能更为深入的熟悉UE的机制…

在Linux上获取MS(如Media Server)中的RTP流并录制为双轨PCM格式的WAV文件

在Linux上获取MS(如Media Server)中的RTP流并录制为双轨PCM格式的WAV文件 一、RTP流与WAV文件格式二、实现步骤三、伪代码示例四、C语言示例代码五、关键点说明六、总结在Linux操作系统上,从媒体服务器(如Media Server,简称MS)获取RTP(Real-time Transport Protocol)流…

Vue3 简介

Vue3 简介 最新版本&#xff1a; v3.5.13 1、性能提升 打包大小减少 41% - 初次渲染快 55%, 更新渲染快 133%内存减少 54% 2、源码的升级 使用 Proxy 代替 defineProperty 实现响应式。重写虚拟 DOM 的实现和 Tree-Shaking 3、拥抱TypeScript Vue3 可以更好的支持 TypeSc…

Oracle Dataguard(主库为 Oracle 11g 单节点)配置详解(1):Oracle Dataguard 概述

Oracle Dataguard&#xff08;主库为 Oracle 11g 单节点&#xff09;配置详解&#xff08;1&#xff09;&#xff1a;Oracle Dataguard 概述 目录 Oracle Dataguard&#xff08;主库为 Oracle 11g 单节点&#xff09;配置详解&#xff08;1&#xff09;&#xff1a;Oracle Data…

北京某新能源汽车生产及办公网络综合监控项目

北京某新能源汽车是某世界500强汽车集团旗下的新能源公司&#xff0c;也是国内首个获得新能源汽车生产资质、首家进行混合所有制改造、首批践行国有控股企业员工持股的新能源汽车企业&#xff0c;其主营业务包括纯电动乘用车研发设计、生产制造与销售服务。 项目现状 在企业全…

大数据系列之:深入理解学习使用腾讯COS和COS Ranger权限体系解决方案,从hdfs同步数据到cos

大数据系列之&#xff1a;深入理解学习使用腾讯COS和COS Ranger权限体系解决方案&#xff0c;从hdfs同步数据到cos 对象存储COS对象存储基本概念COS Ranger权限体系解决方案部署组件COS Ranger Plugin部署COS-Ranger-Service部署COS Ranger Client部署 COSN 从hdfs同步数据到co…

1月第一讲:WxPython跨平台开发框架之前后端结合实现附件信息的上传及管理

1、功能描述和界面 前端&#xff08;wxPython GUI&#xff09;&#xff1a; 提供文件选择、显示文件列表的界面。支持上传、删除和下载附件。展示上传状态和附件信息&#xff08;如文件名、大小、上传时间&#xff09;。后端&#xff08;REST API 服务&#xff09;&#xff1a…

12.29~12.31[net][review]need to recite[part 2]

网络层 IP 首部的前一部分是固定长度&#xff0c;共 20 字节&#xff0c;是所有 IP 数据报必须具有的 路由器 路由选择协议属于网络层控制层面的内容 l 路由器 的 主要工作&#xff1a; 转发分组。 l 路由 信息协议 RIP (Routing Information Protocol ) 是 一种 分布式的…

免费下载 | 2024网络安全产业发展核心洞察与趋势预测

《2024网络安全产业发展核心洞察与趋势预测》报告的核心内容概要&#xff1a; 网络安全产业概况&#xff1a; 2023年中国网络安全产业市场规模约992亿元&#xff0c;同比增长7%。 预计2024年市场规模将增长至1091亿元&#xff0c;2025年达到1244亿元。 网络安全企业数量超过4…