You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@kyuubi.apache.org by fe...@apache.org on 2023/03/22 05:42:12 UTC
[kyuubi] branch master updated: [KYUUBI #4523] support close engine session gracefully
This is an automated email from the ASF dual-hosted git repository.
feiwang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/kyuubi.git
The following commit(s) were added to refs/heads/master by this push:
new 141919308 [KYUUBI #4523] support close engine session gracefully
141919308 is described below
commit 141919308eef3aef36023581ac6927e12b5e26fa
Author: Tianlin Liao <ti...@ebay.com>
AuthorDate: Wed Mar 22 13:42:03 2023 +0800
[KYUUBI #4523] support close engine session gracefully
### _Why are the changes needed?_
### _How was this patch tested?_
- [ ] Add some test cases that check the changes thoroughly including negative and positive cases if possible
- [ ] Add screenshots for manual tests if appropriate
- [ ] [Run test](https://kyuubi.readthedocs.io/en/master/develop_tools/testing.html#running-tests) locally before make a pull request
Closes #4545 from lightning-L/kyuubi-4523.
Closes #4523
2ee634cd5 [Tianlin Liao] modify conf description; add test case
12b930456 [Tianlin Liao] refer to HIVE-13415
c8a9db6a2 [Tianlin Liao] minor fix
9942d2515 [Tianlin Liao] move logic to SessionManager.closeSession
62b990b3e [Tianlin Liao] [KYUUBI #4523] support close engine session gracefully
Authored-by: Tianlin Liao <ti...@ebay.com>
Signed-off-by: fwang12 <fw...@ebay.com>
---
docs/deployment/settings.md | 1 +
.../org/apache/kyuubi/config/KyuubiConf.scala | 8 +++++
.../apache/kyuubi/service/TFrontendService.scala | 11 ++++--
.../server/KyuubiTBinaryFrontendServiceSuite.scala | 39 +++++++++++++++++++++-
4 files changed, 56 insertions(+), 3 deletions(-)
diff --git a/docs/deployment/settings.md b/docs/deployment/settings.md
index 30f557704..e7d939b9b 100644
--- a/docs/deployment/settings.md
+++ b/docs/deployment/settings.md
@@ -381,6 +381,7 @@ You can configure the Kyuubi properties in `$KYUUBI_HOME/conf/kyuubi-defaults.co
| Key | Default | Meaning [...]
|------------------------------------------------------|-------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- [...]
| kyuubi.session.check.interval | PT5M | The check interval for session timeout. [...]
+| kyuubi.session.close.on.disconnect | true | Session will be closed when client disconnects from kyuubi gateway. Set this to false to have session outlive its parent connection. [...]
| kyuubi.session.conf.advisor | <undefined> | A config advisor plugin for Kyuubi Server. This plugin can provide some custom configs for different users or session configs and overwrite the session configs before opening a new session. This config value should be a subclass of `org.apache.kyuubi.plugin.SessionConfAdvisor` which has a zero-arg constructor. [...]
| kyuubi.session.conf.file.reload.interval | PT10M | When `FileSessionConfAdvisor` is used, this configuration defines the expired time of `$KYUUBI_CONF_DIR/kyuubi-session-<profile>.conf` in the cache. After exceeding this value, the file will be reloaded. [...]
| kyuubi.session.conf.ignore.list || A comma-separated list of ignored keys. If the client connection contains any of them, the key and the corresponding value will be removed silently during engine bootstrap and connection setup. Note that this rule is for server-side protection defined via administrators to prevent some essential configs from tampering but will not forbid users to set dynamic configurations via SET syntax. [...]
diff --git a/kyuubi-common/src/main/scala/org/apache/kyuubi/config/KyuubiConf.scala b/kyuubi-common/src/main/scala/org/apache/kyuubi/config/KyuubiConf.scala
index 359ee1ba5..5a576a819 100644
--- a/kyuubi-common/src/main/scala/org/apache/kyuubi/config/KyuubiConf.scala
+++ b/kyuubi-common/src/main/scala/org/apache/kyuubi/config/KyuubiConf.scala
@@ -1358,6 +1358,14 @@ object KyuubiConf {
.version("1.2.0")
.fallbackConf(SESSION_TIMEOUT)
+ val SESSION_CLOSE_ON_DISCONNECT: ConfigEntry[Boolean] =
+ buildConf("kyuubi.session.close.on.disconnect")
+ .doc("Session will be closed when client disconnects from kyuubi gateway. " +
+ "Set this to false to have session outlive its parent connection.")
+ .version("1.8.0")
+ .booleanConf
+ .createWithDefault(true)
+
val BATCH_SESSION_IDLE_TIMEOUT: ConfigEntry[Long] = buildConf("kyuubi.batch.session.idle.timeout")
.doc("Batch session idle timeout, it will be closed when it's not accessed for this duration")
.version("1.6.2")
diff --git a/kyuubi-common/src/main/scala/org/apache/kyuubi/service/TFrontendService.scala b/kyuubi-common/src/main/scala/org/apache/kyuubi/service/TFrontendService.scala
index 16d5c24f9..e541c37c0 100644
--- a/kyuubi-common/src/main/scala/org/apache/kyuubi/service/TFrontendService.scala
+++ b/kyuubi-common/src/main/scala/org/apache/kyuubi/service/TFrontendService.scala
@@ -31,7 +31,7 @@ import org.apache.thrift.transport.TTransport
import org.apache.kyuubi.{KyuubiSQLException, Logging, Utils}
import org.apache.kyuubi.Utils.stringifyException
-import org.apache.kyuubi.config.KyuubiConf.FRONTEND_CONNECTION_URL_USE_HOSTNAME
+import org.apache.kyuubi.config.KyuubiConf.{FRONTEND_CONNECTION_URL_USE_HOSTNAME, SESSION_CLOSE_ON_DISCONNECT}
import org.apache.kyuubi.config.KyuubiReservedKeys._
import org.apache.kyuubi.operation.{FetchOrientation, OperationHandle}
import org.apache.kyuubi.service.authentication.KyuubiAuthenticationFactory
@@ -608,7 +608,14 @@ abstract class TFrontendService(name: String)
if (handle != null) {
info(s"Session [$handle] disconnected without closing properly, close it now")
try {
- be.closeSession(handle)
+ val needToClose = be.sessionManager.getSession(handle).conf
+ .get(SESSION_CLOSE_ON_DISCONNECT.key).getOrElse("true").toBoolean
+ if (needToClose) {
+ be.closeSession(handle)
+ } else {
+ warn(s"Session not actually closed because configuration " +
+ s"${SESSION_CLOSE_ON_DISCONNECT.key} is set to false")
+ }
} catch {
case e: KyuubiSQLException =>
error("Failed closing session", e)
diff --git a/kyuubi-server/src/test/scala/org/apache/kyuubi/server/KyuubiTBinaryFrontendServiceSuite.scala b/kyuubi-server/src/test/scala/org/apache/kyuubi/server/KyuubiTBinaryFrontendServiceSuite.scala
index 69c10e730..5c54cbbb4 100644
--- a/kyuubi-server/src/test/scala/org/apache/kyuubi/server/KyuubiTBinaryFrontendServiceSuite.scala
+++ b/kyuubi-server/src/test/scala/org/apache/kyuubi/server/KyuubiTBinaryFrontendServiceSuite.scala
@@ -17,7 +17,9 @@
package org.apache.kyuubi.server
-import org.apache.hive.service.rpc.thrift.TOpenSessionReq
+import scala.collection.JavaConverters._
+
+import org.apache.hive.service.rpc.thrift.{TOpenSessionReq, TSessionHandle}
import org.scalatest.time.SpanSugar.convertIntToGrainOfTime
import org.apache.kyuubi.{KyuubiFunSuite, Utils, WithKyuubiServer}
@@ -79,4 +81,39 @@ class KyuubiTBinaryFrontendServiceSuite extends WithKyuubiServer with KyuubiFunS
MetricsConstants.THRIFT_BINARY_CONN_OPEN).getOrElse(0L) - openConnections === 0)
}
}
+
+ test("do not close session when disconnect") {
+ val sessionCount = server.backendService.sessionManager.allSessions().size
+ var handle: TSessionHandle = null
+ TClientTestUtils.withThriftClient(server.frontendServices.head) {
+ client =>
+ val req = new TOpenSessionReq()
+ req.setUsername(Utils.currentUser)
+ req.setPassword("anonymous")
+ req.setConfiguration(Map("kyuubi.session.close.on.disconnect" -> "false").asJava)
+ val resp = client.OpenSession(req)
+ handle = resp.getSessionHandle
+
+ assert(server.backendService.sessionManager.allSessions().size - sessionCount == 1)
+ }
+ Thread.sleep(3000L)
+ assert(server.backendService.sessionManager.allSessions().size - sessionCount == 1)
+ }
+
+ test("close session when disconnect - default behavior") {
+ val sessionCount = server.backendService.sessionManager.allSessions().size
+ var handle: TSessionHandle = null
+ TClientTestUtils.withThriftClient(server.frontendServices.head) {
+ client =>
+ val req = new TOpenSessionReq()
+ req.setUsername(Utils.currentUser)
+ req.setPassword("anonymous")
+ val resp = client.OpenSession(req)
+ handle = resp.getSessionHandle
+
+ assert(server.backendService.sessionManager.allSessions().size - sessionCount == 1)
+ }
+ Thread.sleep(3000L)
+ assert(server.backendService.sessionManager.allSessions().size == sessionCount)
+ }
}