This is an automated email from the ASF dual-hosted git repository.
yiguolei pushed a commit to branch branch-2.1
in repository https://gitbox.apache.org/repos/asf/doris.git
The following commit(s) were added to refs/heads/branch-2.1 by this push:
new 21b8887b543 [feat](profile) Print changed session var in profile
#41016 (#41317)
21b8887b543 is described below
commit 21b8887b543c3e950479bdfd4e209498ef33c30c
Author: zhiqiang <[email protected]>
AuthorDate: Fri Sep 27 09:55:43 2024 +0800
[feat](profile) Print changed session var in profile #41016 (#41317)
cherry pick from #41016
---
.../org/apache/doris/common/profile/Profile.java | 17 ++++++-
.../org/apache/doris/common/util/DebugUtil.java | 59 ++++++++++++++++++++++
.../java/org/apache/doris/qe/StmtExecutor.java | 2 +
.../main/java/org/apache/doris/qe/VariableMgr.java | 36 +++++++++++++
4 files changed, 113 insertions(+), 1 deletion(-)
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/common/profile/Profile.java
b/fe/fe-core/src/main/java/org/apache/doris/common/profile/Profile.java
index b9cefdd0c4a..f92cf5cb938 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/common/profile/Profile.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/common/profile/Profile.java
@@ -59,8 +59,8 @@ public class Profile {
private List<ExecutionProfile> executionProfiles = Lists.newArrayList();
private boolean isFinished;
private Map<Integer, String> planNodeMap;
-
private int profileLevel = 3;
+ private String changedSessionVarCache = "";
public Profile(String name, boolean isEnable, int profileLevel, boolean
isPipelineX) {
this.name = name;
@@ -122,6 +122,7 @@ public class Profile {
// add summary to builder
summaryProfile.prettyPrint(builder);
waitProfileCompleteIfNeeded();
+ getChangedSessionVars(builder);
// Only generate merged profile for select, insert into select.
// Not support broker load now.
if (this.profileLevel == MergedProfileLevel &&
this.executionProfiles.size() == 1) {
@@ -186,4 +187,18 @@ public class Profile {
Gson gson = new GsonBuilder().setPrettyPrinting().create();
return gson.toJson(rootProfile.toBrief());
}
+
+ public void setChangedSessionVar(String changedSessionVar) {
+ this.changedSessionVarCache = changedSessionVar;
+ }
+
+ private void getChangedSessionVars(StringBuilder builder) {
+ if (builder == null) {
+ builder = new StringBuilder();
+ }
+
+ builder.append("\nChanged Session Variables:\n");
+ builder.append(changedSessionVarCache);
+ builder.append("\n");
+ }
}
diff --git
a/fe/fe-core/src/main/java/org/apache/doris/common/util/DebugUtil.java
b/fe/fe-core/src/main/java/org/apache/doris/common/util/DebugUtil.java
index 2a52420a96d..287f35f32a9 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/common/util/DebugUtil.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/common/util/DebugUtil.java
@@ -26,6 +26,7 @@ import com.google.common.base.Strings;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.text.DecimalFormat;
+import java.util.List;
import java.util.UUID;
public class DebugUtil {
@@ -177,4 +178,62 @@ public class DebugUtil {
e.printStackTrace(new PrintWriter(sw));
return sw.toString();
}
+
+ public static String prettyPrintChangedSessionVar(List<List<String>>
nestedList) {
+ if (nestedList == null || nestedList.isEmpty()) {
+ return "";
+ }
+
+ StringBuilder output = new StringBuilder();
+
+ // Assuming each inner list has exactly 3 columns
+ int[] columnWidths = new int[3];
+
+ // Calculate the maximum width of each column
+ // First consider the header widths: "VarName", "CurrentValue",
"DefaultValue"
+ String[] headers = {"VarName", "CurrentValue", "DefaultValue"};
+ for (int i = 0; i < headers.length; i++) {
+ columnWidths[i] = headers[i].length(); // Initialize with header
length
+ }
+
+ // Update column widths based on data
+ for (List<String> row : nestedList) {
+ for (int i = 0; i < row.size(); i++) {
+ columnWidths[i] = Math.max(columnWidths[i],
row.get(i).length());
+ }
+ }
+
+ // Build the table header
+ for (int i = 0; i < headers.length; i++) {
+ output.append(String.format("%-" + columnWidths[i] + "s",
headers[i]));
+ if (i < headers.length - 1) {
+ output.append(" | "); // Separator between columns
+ }
+ }
+ output.append("\n"); // Newline after the header
+
+ // Add a separator line for better readability (optional)
+ for (int i = 0; i < headers.length; i++) {
+ output.append(String.format("%-" + columnWidths[i] + "s",
Strings.repeat("-", columnWidths[i])));
+ if (i < headers.length - 1) {
+ output.append("-|-"); // Separator between columns
+ }
+ }
+ output.append("\n"); // Newline after the separator
+
+ // Build the table body with proper alignment based on column widths
+ for (List<String> row : nestedList) {
+ for (int i = 0; i < row.size(); i++) {
+ String element = row.get(i);
+ // Pad with spaces if the element is shorter than the column
width
+ output.append(String.format("%-" + columnWidths[i] + "s",
element));
+ if (i < row.size() - 1) {
+ output.append(" | "); // Separator between columns
+ }
+ }
+ output.append("\n"); // Newline after each row
+ }
+
+ return output.toString();
+ }
}
diff --git a/fe/fe-core/src/main/java/org/apache/doris/qe/StmtExecutor.java
b/fe/fe-core/src/main/java/org/apache/doris/qe/StmtExecutor.java
index 8d59f49b0c1..24a9a98814d 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/qe/StmtExecutor.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/qe/StmtExecutor.java
@@ -648,6 +648,8 @@ public class StmtExecutor {
context.setQueryId(queryId);
context.setStartTime();
profile.getSummaryProfile().setQueryBeginTime();
+ List<List<String>> changedSessionVar =
VariableMgr.dumpChangedVars(context.getSessionVariable());
+
profile.setChangedSessionVar(DebugUtil.prettyPrintChangedSessionVar(changedSessionVar));
context.setStmtId(STMT_ID_GENERATOR.incrementAndGet());
parseByNereids();
diff --git a/fe/fe-core/src/main/java/org/apache/doris/qe/VariableMgr.java
b/fe/fe-core/src/main/java/org/apache/doris/qe/VariableMgr.java
index 38a8b5239d3..3515e9e0861 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/qe/VariableMgr.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/qe/VariableMgr.java
@@ -795,6 +795,42 @@ public class VariableMgr {
return changedRows;
}
+ public static List<List<String>> dumpChangedVars(SessionVariable
sessionVar) {
+ // Hold the read lock when session dump, because this option need to
access global variable.
+ rlock.lock();
+ List<List<String>> changedRows = Lists.newArrayList();
+ try {
+ for (Map.Entry<String, VarContext> entry :
ctxByDisplayVarName.entrySet()) {
+ VarContext ctx = entry.getValue();
+ List<String> row = Lists.newArrayList();
+ String varName = entry.getKey();
+ String curValue = getValue(sessionVar, ctx.getField());
+ String defaultValue = ctx.getDefaultValue();
+ if (VariableVarConverters.hasConverter(varName)) {
+ try {
+ defaultValue = VariableVarConverters.decode(varName,
Long.valueOf(defaultValue));
+ curValue = VariableVarConverters.decode(varName,
Long.valueOf(curValue));
+ } catch (DdlException e) {
+ LOG.warn("Decode session variable {} failed, reason:
{}", varName, e.getMessage());
+ }
+ }
+
+ if (curValue.equals(defaultValue)) {
+ continue;
+ }
+
+ row.add(varName);
+ row.add(curValue);
+ row.add(defaultValue);
+ changedRows.add(row);
+ }
+ } finally {
+ rlock.unlock();
+ }
+
+ return changedRows;
+ }
+
@Retention(RetentionPolicy.RUNTIME)
public @interface VarAttr {
// Name in show variables and set statement;
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]