0% found this document useful (0 votes)
80 views

openSAP Hanasql2 Week 3 Transcript EN

This document discusses the SQLScript optimizer in SAP HANA and how it uses inlining to optimize SQL statements. It explains that the optimizer tries to combine dependent SQL statements into a single query by using a WITH clause. This allows the statements to be executed as a single query internally for better performance. However, in some cases using the NO_INLINE hint can prevent inlining to avoid long compilation times or suboptimal query plans. The document provides an example of how inlining works and how to view the executed statements.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
80 views

openSAP Hanasql2 Week 3 Transcript EN

This document discusses the SQLScript optimizer in SAP HANA and how it uses inlining to optimize SQL statements. It explains that the optimizer tries to combine dependent SQL statements into a single query by using a WITH clause. This allows the statements to be executed as a single query internally for better performance. However, in some cases using the NO_INLINE hint can prevent inlining to avoid long compilation times or suboptimal query plans. The document provides an example of how inlining works and how to view the executed statements.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 21

PUBLIC

openSAP
Using the Optimizer for SQLScript Programming in SAP
HANA

Week 3 Unit 1(I)

00:00:05 Hello, and welcome to the first unit of week three. I'm Jin Yeon Lee and I'm very glad to
present
00:00:12 the content of week three with my colleague Minjeong Lee.
00:00:17 In week one and two, we studied how SQLScript engine was, and how to use its
supportability features.
00:00:27 This week we will study useful methods NO_INLINE hint, BIND_AS_PARAMETER function,

00:00:32 BIND_AS_VALUE function, and SQL hints for SQLScript... By the end of this week, you'll be
familiar
00:00:44 with using these methods to solve performance issues on your SQLScript procedure.
00:00:53 Before explaining the INLINE feature, let me tell about usage of table variables first.
00:01:04 In case we have to make a complex logic in SQL, we usually compose a long and complex
query
00:01:11 with many relational operations like joins and group bys. Sometimes we use subqueries too.

00:01:22 If you have to edit this long complex SQL statement, it is certainly very difficult.
00:01:29 And it sometimes leads to unexpected results. But in SQLScript,
00:01:38 instead of composing very long and complex single SQL statements,
00:01:44 we can make several short SQL statements combined with table variables.
00:01:53 Logically, these are exactly the same, but this way can reduce the complexity of SQL
statements.
00:02:02 Then it is definitely helpful to comprehend the logic, so then you can easily modify them if
needed.
00:02:14 For this reason, using table variables is always recommended. And I'm sure you are already
using table variables a lot
00:02:22 in your SQLScript procedure. But let's think about using table variables
00:02:33 from a performance perspective. What do you think of executing multiple SQL statements
00:02:41 instead of a single long complex query in SQLScript calls? As we learned,
00:02:51 when an SQL statement in SQLScript procedure is executed, SQLScript engine passes that
query to SQL engine,
00:03:00 then gets the result set. The more result sets, the more interactions
00:03:07 between SQLScript engine and SQL engine happen, including memory copy operations and
so on.
00:03:20 And those are expensive from a performance point of view. Instead of multiple short
queries,
00:03:31 if a single long complex query is passed to an SQL engine from an SQLScript engine,
00:03:38 then this query can be executed with the optimal query plan by SQL optimizer.
00:03:44 Then its results set is passed to SQLScript engine one time.
00:03:52 SAP HANA database provides a feature to take both advantages. If you use table variables
to split the long complex query
00:04:03 into multiple short ones, then HANA database executes them
00:04:07 as a single complex one internally. So you don't need to worry about a performance penalty

00:04:14 by multiple short queries with table variables. SQLScript optimizer tries to combine
00:04:25 dependent SQL statements, as many as possible, and make them a single query string.
00:04:34 This is called inlining, one of the optimizations of SQLScript.
00:04:41 It is beneficial to the performance. For example, materialization,
00:04:49 materializing results of table variables are omitted,
00:04:53 and a better join order can be chosen by SQL optimizer. Let me show how the inlining
feature works
00:05:03 with this example procedure. The procedure "get_results" consists of four SQL statements,

00:05:11 and they are linked with table variables. Table variable "final_products" contains the result
00:05:20 of SQL statement one and it is used in SQL statement two.
00:05:28 Table variable "item" is for the result of statement two and used in statement three.
00:05:37 Lastly, the table variable "aggregated_items" comes from statement three,
00:05:43 and it is consumed in statement four. When this procedure is compiled, SQLScript optimizer

00:05:52 checks the dependency of these four SQL statements, then applies the inlining feature.
00:06:02 As I explained before, INLINE features rewrite multiple SQL statements
00:06:07 into an equivalent single SQL statement using WITH clause.
00:06:14 So once these queries are inline, these SQL statements are totally reshaped.
00:06:22 Let's check the result. When you use EXPLAIN PLAN FOR CALL,
00:06:30 you can find which SQL statements are executed, which is the output of SQLScript
optimization,
00:06:37 without executing the procedure. Since we collected EXPLAIN PLAN FOR CALL with the
statement name "INLINE" before,
00:06:47 let's delete existing records having STATEMENT_NAME "INLINE" from
EXPLAIN_CALL_PLANS table first.
00:06:58 Then execute EXPLAIN PLAN FOR CALL for this procedure with input parameters.
00:07:04 Then check the result from EXPLAIN_CALL_PLANS table. As you can see,
OPERATOR_STRING column,
00:07:17 there is only one SQL statement though there are four SQL statements in its definition code.

00:07:26 Now, let's check SQLSCRIPT_PLAN_PROFILER. This shows actual executed SQL
statements,
00:07:38 whereas "EXPLAIN PLAN FOR CALL" shows an SQLScript execution plan, before actual
execution.
00:07:49 Unlike the result of "EXPLAIN PLAN FOR CALL" in the previous slide,
00:07:54 the result of plan profiler for this call statement shows two SQL statements.
00:08:06 To see executed SQL statements, you should check a value in column
OPERATOR_STATEMENT_STRING
00:08:13 where the column operator is Execute SQL Statement. Table Assign Op in column
OPERATOR
00:08:25 is your operation for assigning table variable. And Execute SQL Statement operation

2 / 21
00:08:33 is next to this Table Assign Op. This means a query result from Execute SQL Statement
operation
00:08:43 is stored in given table variables, in this Table Assign Op operation.
00:08:51 Let's check the first SQL statement. The first one starts with a comment.
00:08:58 This comment shows how the inlining feature is applied. It shows which table variables
00:09:07 are used in this WITH clause by showing their name and position of the code.
00:09:15 This information is very important and helpful because you have to modify your SQL script
code.
00:09:24 You can easily find how your change will be reshaped. At the end of this comment,
00:09:34 you can see WITH clause follows. Then let me explain the last SQL statement
00:09:42 which you didn't see in the result of "EXPLAIN PLAN FOR CALL".
00:09:48 This select statement is for fetching the result to output parameter.
00:09:55 "EXPLAIN PLAN FOR CALL" does not execute the procedure, so SQLScript engine does
not need to send the result set
00:10:04 via output parameter. That is why select statement for
00:10:12 this output parameter is not shown,
00:10:16 but SQLScript Plan Profiler shows actual execution of call statement.
00:10:24 When call statement is executed, output parameter is actually selected and returned
00:10:31 as the result of call statement. That's why this last SQL statement is shown here.
00:10:41 Let me show the output of inlining. In the code, four SQL statements are associated
00:10:48 with table variables. After SQLScript optimizer confirms dependency
00:10:56 of these four SQL statements and their table variables, it combines them into a single SQL
statement.
00:11:05 The new single SQL statement starts from WITH clause and three SQL statements
00:11:13 and their table variables are now represented as a subquery in that WITH clause.
00:11:21 When checking the logic of this new SQL statement, you can see its logic is exactly the
same as the one
00:11:27 from four SQL statements in the code. In WITH clause, statement one is merged
00:11:37 as a subquery with query name "_SYS_FINAL_PRODUCT_2".
00:11:44 Statement two is merged with query name "_SYS_ITEMS_2" and statement three is done
with query name
00:11:54 "_SYS_AGGREGATED_ITEMS_2". During the execution of this single statement,
00:12:01 values in table variable, final products, items, and aggregated items are not materialized.
00:12:10 Instead, join and group by operations run on their intermediate result and only the final
results set of aggregated item
00:12:19 is materialized and copied to SQLScript engine.

3 / 21
Week 3 Unit 1(II)

00:00:05 Even though inlining is beneficial to performance in most cases, there may be a rare case
00:00:14 where combined SQL statements lead to a non-optimal query plan.
00:00:20 In this case, blocking a combination of specific SQL statements will help for better
performance.
00:00:28 And you can do that by using the NO_INLINE hint. For example, a procedure has a lot of
dependencies
00:00:40 from many SQL statements. The inlining feature combines them into a very complex query.

00:00:48 SQL optimizer needs more time to optimize the SQL query due to it having so many things
to be checked.
00:00:59 Then it finally results in long compilation time. Normally long compilation is not a problem.
00:01:06 Because once its query plan is stored in SQL plan cache, next time the cached plan is
reused without compilation.
00:01:19 But, in case the long compilation time may affect overall performance,
00:01:25 so you want to reduce the compilation time, then you can use NO_INLINE hint to avoid
inlining.
00:01:34 Let me present an example of this case in the next unit. Another case of blocking inlining
00:01:44 is when a sub-optimal plan is chosen due to a big join size. Let's assume there are two
queries,
00:01:54 called query one and query two inside the procedure. Each query has several joins.
00:02:04 And these two queries are merged into a single query by SQLScript optimizer.
00:02:14 At this point, there may be a situation where joins become very complex and large
00:02:22 after merging joins from two queries, and running into an unexpected out-of-memory
situation.
00:02:30 In this case, we can try to use NO_INLINE hint. Going back to the example, let's try to use
NO_INLINE hint
00:02:42 at the end of the first SQL statement in procedure get_results. As you know, the first SQL
statement is connected
00:02:53 with the second one by table variable final_products. Now, due to the added NO_INLINE
hint,
00:03:05 SQLScript optimizer does not combine the first SQL statement and second one. Even if they
have dependency.
00:03:14 Since the second and third and fourth SQL statement do not have NO_INLINE hint,
00:03:21 they are combined just like before. Then, let's check the result of explain plan for CALL
00:03:28 to see how the execution plan of this procedure is changing. Let's delete the record having
the statement name INLINE
00:03:40 from EXPLAIN_CALL_PLANS table first, because it contains the result of previous explain
plan for CALL.
00:03:52 Then execute explain plan for CALL for this procedure with input parameters again.
00:04:02 Then check the results from the EXPLAIN_CALL_PLANS table. As you can see, two SQL
statements
00:04:13 are in column OPERATOR_STRING now. The first SQL statement shows WITH HINT
NO_INLINE is added.
00:04:25 The other SQL statement is output of the inlining optimization from the second, third, and
fourth SQL statements.
00:04:37 Then now, let's check the result of the SQLScript Plan Profiler. As you expected, it shows
three SQL statements.

4 / 21
00:04:48 The first one is the SQL statement having NO_INLINE hint. The second one is inlined SQL
statement
00:04:58 from the second, third, and fourth SQL statement. This is just the same result as explain
plan for CALL shows.
00:05:12 The last SQL statement is select a statement for output parameters, as you had checked
previously.
00:05:19 As I explained, Table Assign Op is an operation to assign table variables for the next
operation.
00:05:28 Its operator statement string also shows SQL strings that are executed in the next
operation.
00:05:37 But you can see $$_SS_SE_TAB_VAR_FINAL_PRODUCTS_2$$ in FROM clause. The
query looks like it is coming
00:05:52 from the second SQL statement in the code, and
$$_SS_SE_TAB_VAR_FINAL_PRODUCTS_2$$
00:06:03 is in the red box. It looks like the name of
00:06:09 table variable, FINAL_PRODUCTS. It comes from the first SQL statement.
00:06:15 When you check the executed SQL statement,
$$_SS_SE_TAB_VAR_FINAL_PRODUCTS_2$$
00:06:22 in the red box is not shown anymore. Instead, you can see SYS_SS2_TMP_TABLE, some
numbers,
00:06:34 FINAL_PRODUCTS_2 with a long GUID value in the green box here.
00:06:40 Both point the table variable final product, which is assigned from the first SQL statement.
00:06:50 But the name having $$ is a kind of a logical name of a table variable.
00:06:56 And its physical name is the long name having GUID value.
00:07:04 This GUID value is generated newly whenever an SQL script is compiled.
00:07:13 This naming rule for local temp table was explained in unit two of week two before.
00:07:23 And it'll be explained again in the last unit of week three.
00:07:28 So far, we checked what happened when NO_INLINE hint is added at the end of the first
SQL statement.
00:07:39 This time, let's try to break all dependency by adding this hint at the end of the first,
00:07:48 second, and third SQL statements. Let's repeat the step to see the result of explain plan for
CALL.
00:07:58 As you expected, the SQLScript execution plan contains four SQL statements.
00:08:06 Three SQL statements have WITH HINT NO_INLINE. SQLScript Plan Profiler shows the
same result.
00:08:16 You can also see logical temp table with GUID values in their names, from the executed
SQL statement.
00:08:28 It means the results of each SQL statement are stored in corresponding local temp as table
variables.
00:08:39 As I said, in this case values of result sets are materialized. In column OPERATOR
DETAILS, you can see the size
00:08:50 of the table variable where the result of the query is stored. Its unit is bytes.
00:08:58 Okay, so in the previous example, we added NO_INLINE hint
00:09:03 at the end of the first, second, and third SQL statements. So, four SQL statements were
executed separately.
00:09:14 Then, can you guess what will happen if NO_INLINE hint is added to the last SQL
statement?
00:09:22 We learned the procedure flattening optimization rule in week one. It means a procedure A
is called inside another procedure B
00:09:34 by a CALL statement. This CALL statement for procedure A

5 / 21
00:09:39 is replaced with the body of procedure A. Once procedure A is flattened, then all SQL
statements of
00:09:49 procedure A can be inlined with SQL statement of procedure B.
00:09:57 Let's check this example. Procedure get_results_wrapper has a CALL statement
00:10:06 of procedure get_results and one simple SQL statement. Since procedure get_results
already has four SQL statements,
00:10:19 so let's say this simple SQL statement, SELECT * FROM RESULTS_TAB, is statement five.

00:10:28 And all four SQL statements in procedure get_results have NO_INLINE hint.
00:10:38 Here is the result of explain plan for CALL. You can see five SQL statements in the
execution plan,
00:10:49 because NO_INLINE hint at the end of the fourth SQL statement. blocks combining
statement four and statement five.
00:11:00 If you don't add NO_INLINE hint at the end of fourth SQL statement,
00:11:05 then this is explain plan for CALL shows only four SQL statements,
00:11:10 because statements four and five are combined. The last case is adding NO_INLINE hint
00:11:18 at the end of inner CALL statement. Here's an example.
00:11:25 Procedure get_results_wrapper consists of CALL procedure, CALL procedure get_results,
and a simple SELECT statement.
00:11:37 What will happen if NO_INLINE hint is added at the end of the CALL statement of the
procedure get_results?
00:11:46 Let's check the result of explain plan for CALL. As you can see here, CALL statement of
procedure get_results
00:11:56 is executed via operator call. This means procedure get_results is not flattened.
00:12:05 So NO_INLINE hint blocks not only inlining of SQL statement, but also flattening inner CALL
statement.
00:12:17 In week one, we learned four SQL Script optimization rules. Constant propagation,
procedure flattening,
00:12:27 SQL statement inlining, and control flow simplification. You can control inlining optimization

00:12:36 and procedure flattening by using NO_INLINE hint. This hint is very simple to use, but very
powerful.
00:12:48 So that your procedure can be executed in totally different ways. So you always have to
check the result of
00:12:57 explain plan for CALL when you added this NO_INLINE hint. With that, we come to the end
of unit one.
00:13:09 We learned about inline features and NO_INLINE hint. Inlining optimization combines
multiple short queries
00:13:18 associated with table variables into a single query. It can take more advantage of SQL
optimizer,
00:13:27 and lead to less materialization of the result of table variables.
00:13:36 NO_INLINE hint is a way of controlling inlining optimization. It can also control procedure
flattening.
00:13:45 Those are the key takeaways of this unit. In the next unit, I will present a case study of
NO_INLINE hint.
00:13:56 Thank you for your attention. See you.

6 / 21
Week 3 Unit 2

00:00:05 Hello, my name is Jin Yeon Lee. Today, I'm going to explain a case study
00:00:10 of using the INLINE feature. Let us show we have a SQLScript performance issue.
00:00:16 A slow running procedure is observed in the system. It takes about 18 seconds.
00:00:23 That is much longer than expected. The problematic statement is CALL statement
00:00:32 of procedure CL_ABC_READ_DEF_BASIC=>GET_MRP_ELEMENTS3, with the integer
value 717 as an input parameter.
00:00:45 Due to the business application logic, this input parameter value is given
00:00:51 as a constant value, but it keeps changing. In the example, this time it is 717,
00:01:00 or the next time it can be 718, or any other value. When executing the same CALL
statement
00:01:09 with the same input parameter value, it runs quickly, not taking 18 seconds.
00:01:16 But when changing the parameter value, I can see slow response time again.
00:01:23 In this situation, which supportability feature do you think would help to identify
00:01:29 where the most time is spent? Yes, since we know the problematic statement,
00:01:37 let's collect the Plan Visualizer trace first. So the collected Plan Visualizer trace looks like
the following:
00:01:45 The OVERVIEW page shows compilation time is 218 milliseconds and execution time is
about 18 seconds,
00:01:57 under EXECUTION SUMMARY box. DOMINANT PLAN OPERATORS box shows
00:02:03 what is the most expensive operator in this trace. Let's click the most expensive operator
here.
00:02:16 Then you can see the box having number 1 in the blue circle
00:02:20 in the PLAN GRAPH page. And you can also see
00:02:25 its inclusive time is 17.9 seconds. This operator definitely takes a long time,
00:02:35 because the inclusive time of the next operator is just 3.5 seconds. Now let's check the
STATEMENT_STATISTICS page.
00:02:47 The execution time of the CALL statement is about 17,000 milliseconds,
00:02:55 but it's compilation time is 218 milliseconds. When you check which inner SQL statement
takes long,
00:03:04 the second inner SQL statement from the top looks suspicious.
00:03:10 Because each execution time is 423 milliseconds and its compilation time is about 14
seconds.
00:03:22 But here, you might wonder why compilation time of this CALL statement is just 218
milliseconds
00:03:31 though the compilation time of the second inner SQL statement is 14 seconds.
00:03:39 The execution time of the CALL statement is 17,983 milliseconds.
00:03:48 Though the sum of execution time of all inner SQL statements is about only 600
milliseconds.
00:03:58 On the other hand, the compilation time of the CALL statement is 218 milliseconds,
00:04:07 but the sum of the compilation time of inner SQL statement is 17,207 milliseconds.
00:04:16 Where does such a big difference between execution time of CALL statement and the sum
of execution time of all inner statements come from?
00:04:30 In week one, we learned SQLScript engine compiles
00:04:34 SQLScript procedure code. Then it generates its execution plan.

7 / 21
00:04:40 During SQLScript engine executing its execution plan, it passes inner SQL statement string
to SQL engine.
00:04:51 Then SQL engine processes that SQL statement string. So compilation of inner SQL
statements happens
00:05:01 in SQLScript execution step, not SQLScript compilation step.
00:05:09 That is 17,207 milliseconds of the sum of compilation time
00:05:17 of inner SQL statements belong to execution time of CALL statements.
00:05:27 Then we can now see the compilation of the second inner SQL statement is most dominant.

00:05:35 And it is located in line number 295. Timeline view also shows the same information that we
found.
00:05:46 The compilation time of the second inner SQL statement is long. In the STATEMENT
STATISTICS page, you can see the open link
00:05:58 in the Deep Dive field in this inner SQL query. When clicking it, you can get a Plan
Visualizer trace
00:06:09 of this inner SQL statement in a separate window. In that separate Plan Visualizer trace
window
00:06:18 of this inner SQL statement, you can find compilation summary information.
00:06:26 This information is a new feature of SQL analyzer tool, which SAP HANA Studio PlanViz
doesn't have.
00:06:35 Here the rewriting time is 10 seconds. It means this SQL plan is too complex.
00:06:43 So it needs some time to consider many rule-based optimizations.
00:06:48 Let's continue checking more information in STATEMENT STATISTICS page. When inlining
optimization is applied,
00:07:00 a string of inner SQL statement in a SQLScript code is reshaped.
00:07:09 SQLScript engine leaves information about which table variables are used
00:07:14 to combine queries as a comment. Click Show in New View,
00:07:23 after selecting the problematic line. Then you can see comments value
00:07:29 of the long compiled inner query. You can also find the same comment information
00:07:36 in the PROPERTIES tab of the most dominant operator BOX in the PLAN GRAPH page.
00:07:43 According to the comment of the problematic query, it is the output of the inlining
optimization,
00:07:50 by merging 17 inner SQL statements. This inlined query is very complex.
00:07:59 So reducing its complexity looks like a key to solve this performance issue.
00:08:06 Let's add NO_INLINE HINT at the end of these 17 SQL statements
00:08:12 where the comment points. Then, execute this procedure
00:08:18 with a different parameter value to check how fast it is now.
00:08:24 Plan Visualizer trace for the modified procedure shows CALL statement of this procedure
having NO_INLINE HINT
00:08:34 takes now about 2.6 seconds. That is a big improvement
00:08:40 from the previous response time of about 18 seconds. Let's check the STATEMENT
STATISTICS page
00:08:51 of the newly collected Plan Visualizer trace. As you expected,
00:08:58 the long running compiled inner SQL statement is replaced with 17 statement by adding
NO_INLINE hint now.
00:09:10 Previously, the single inlined query took 423 milliseconds for its execution.
00:09:19 And about 14 seconds for its compilation. In the new trace, the sum of execution time
00:09:29 of the new 17 statement is 3,646 milliseconds and the sum of their compilation time is
16,424 milliseconds.

8 / 21
00:09:49 Their total execution and compilation time is actually bigger than ones of
00:09:54 the previous problematic inline inner SQL statement. Then how can this CALL procedure
run faster than before?
00:10:07 To find out the reason why the modified SQLScript procedure is faster,
00:10:12 let's check the TIMELINE view. We see these 17 statements are compiled in parallel,
00:10:20 and they are executed independently. Due to this parallel compilation and execution,
00:10:28 more CPU resources are used than before. But the entire response time
00:10:34 of this CALL statement becomes very short. This is an acceptable trade off,
00:10:42 since the system has enough CPU power. The PLAN GRAPH page also shows 17
statements
00:10:50 are compiled and executed in parallel. In summary, this case shows how we approach a
long
00:11:00 compilation problem of SQLScript procedure. As a solution, we use NO_INLINE hint at the
end of each statement
00:11:11 to block inlining optimization. There is no perfect answer for when NO_INLINE hint must be
used.
00:11:20 Also there are other ways to solve this issue. When you use this NO_INLINE hint in your
production system,
00:11:29 please check how this hint affects your procedure as well as resource and workload of the
system first.
00:11:39 This is the end of unit two. Let me repeat key takeaways.
00:11:47 As I explained, the advantage of inlining feature, it is helpful to run your procedure fast in
most cases.
00:11:58 So if you want to use NO_INLINE hint, please understand the output
00:12:04 of SQLScript optimization first. Then use this hint properly,
00:12:10 only when the output of SQLScript optimization causes an issue. In the next unit
00:12:20 I will explain BIND_AS_PARAMETER and BIND_AS_VALUE SQLScript functions. Thank
you for your attention.
00:12:29 See you.

9 / 21
Week 3 Unit 3

00:00:05 Hello, and welcome to unit three of week three. I am Jin Yeon Lee.
00:00:11 Last time, we learned the inline feature and NO_INLINE hint, which can control statement
inlining and procedure flattening.
00:00:20 Today, we are going to study features that can control constant propagation.
00:00:28 This constant propagation means evaluating SQL expression during compile time,
00:00:35 and if a result can be known, then it is used as a constant value for execution time.
00:00:42 In HANA 2, we can control parameterization behavior of scalar parameters explicitly
00:00:50 by using BIND_AS_PARAMETER and BIND_AS_VALUE SQLScript functions.
00:00:56 In a nutshell, BIND_AS_PARAMETER treats a scalar variable as a query parameter.
00:01:04 On the other hand, BIND_AS_VALUE treats a scalar variable as a constant value.
00:01:12 Here is a procedure get_results having four input parameters and one output parameter.
00:01:20 Out of the four input parameters, please keep your eyes on the input parameters
00:01:27 im_category in the red box, and im_typecode in the blue box. They are used in the first SQL
statement.
00:01:37 And we will observe how they will be changing. Let's collect Explain Plan for CALL of this
procedure
00:01:44 with constant values "Notebooks" and "PR" for im_category and im_typecode.
00:01:53 From the results of Explain Plan, you can see CAST (Notebooks AS NVARCHAR(40))
00:02:00 and CAST (PR AS NVARCHAR(2)) are used instead of im_category and im_typecode.
00:02:09 This means when you use constant values for input parameters, by constant propagation
rule, SQLScript optimizer
00:02:19 changes these input parameters to given constant values. This time, let's use question
marks for input parameters.
00:02:31 When you use a question mark, it means values for input parameters will be given later
00:02:37 after preparing our CALL statement. We call it a parameterized query.
00:02:46 Explain Plan for CALL does not execute our CALL statement. We don't need to bind values
to parameters this time.
00:02:54 The result shows a different SQL statement from the previous result.
00:03:02 Previously im_category and im_typecode were replaced with constant values.
00:03:08 But this time, they were represented as query parameters like __typed_NString_($1, 40).
00:03:19 Here __typed_NString means data type of the parameter, and $1 means parameter
position,
00:03:29 and 40 is the length of the data type. Though it is unknown which value will be given
00:03:37 for im_category at this moment. It comes from the first parameter and it's 40 length
NVARCHAR value.
00:03:50 When a query parameter is given for the input parameter of a procedure, the SQL statement
becomes a parameterized query.
00:04:00 As you can see, this inner SQL statement is changing depending on what is given for input
parameter.
00:04:10 When you use constant value, the constant propagation rule optimizes our query as a literal
one.
00:04:18 If you use query parameters, then these parameters are used in the query
00:04:24 so it becomes a parameterized query. The advantage of using a parameterized query
00:04:31 is that the query plan can be reused, even when parameter values are changing.

10 / 21
00:04:39 A potential disadvantage is that the query plan can be suboptimal for some parameter
values.
00:04:46 Because the query plan is generated with the first given parameter value.
00:04:53 For a literal query when different values are given, the SQL statement is always changing.
00:05:00 So, it needs to compile a new optimal query plan. So when parameter values are changing
frequently,
00:05:10 compilation costs can be bigger than in the case of a parameterized query.
00:05:16 And if a similar query plan having different values are generated a lot in a short time,
00:05:23 SQL plan cache can flood. Which I said, BIND_AS_PARAMETER and BIND_AS_VALUE
00:05:29 SQLScript functions can control parameterization behavior of scalar parameters explicitly.
00:05:38 Let's check how they work. In this example,
00:05:42 BIND_AS_PARAMETER is applied to im_category and BIND_AS_VALUE is applied to
im_typecode.
00:05:51 Let's collect Explain Plan for CALL with constant value 'Notebooks' and 'PR' as parameter
values.
00:06:00 Though constant value 'Notebooks' is given for input parameter im_category. Im_category is
replaced with
00:06:08 query parameter __typed_NString_($1, 40). SQLScript function BIND_AS_PARAMETER
always
00:06:20 uses a query parameter to represent a scalar variable. So constant propagation rule
00:06:28 could not apply to input parameter im_category with constant value 'Notebooks'.
00:06:35 On the other hand, im_typecode is replaced with constant value 'PR'.
00:06:42 Constant propagation rule applies to im_typecode as well. Let me explain
BIND_AS_VALUE further in the next slide.
00:06:54 This time let's check Explain Plan for CALL of this procedure with parameters.
00:07:03 Can you guess how im_category and im_typecode will be changed?
00:07:08 There is no difference in BIND_AS_PARAMETER im_category because a query parameter
is already given.
00:07:17 But BIND_AS_VALUE, im_typecode is replaced with CAST function with some long name.

00:07:24 Since BIND_AS_VALUE always uses a value to represent a scalar variable during
compiling SQL script,
00:07:36 BIND_AS_VALUE im_typecode should become a constant value. But at this moment,
Explain Plan for CALL
00:07:47 does not execute this procedure yet. That is, a value for im_typecode is not yet given.
00:07:56 So SQLScript engine leaves it as a scalar variable name of im_typecode.
00:08:05 Once this call procedure is actually executed, this scalar variable name will be replaced with

00:08:12 a real value again. We will check this part in the next slide again.
00:08:19 Let's check the result of SQLScript Plan Profiler for this case, and check if constant value
'PR'
00:08:27 is used for BIND_AS_VALUE im_typecode. Since Plan Profiler executes a CALL statement,

00:08:36 you have to enter values for parameters. Then the scalar variable name of
00:08:43 im_typecode is replaced with 'PR' now. So you can see CAST (PR AS NVARCHAR(2)).
00:08:53 in the actual executed SQL statement. So far we studied BIND_AS_PARAMETER
00:08:59 and BIND_AS_VALUE SQLScript functions. They can control the parameterization behavior

00:09:06 of scalar variables explicitly. BIND_AS_PARAMETER treats a scalar variable

11 / 21
00:09:13 as a query parameter, so affected SQL statements become parameterized queries.
00:09:23 BIND_AS_VALUE treats scalar variables as a constant value,
00:09:28 so affected SQL statements become literal queries. In the next unit, we will check the
00:09:38 case study of using BIND_AS_VALUE. Looking forward to meeting you there.
00:09:45 Thank you, and goodbye.

12 / 21
Week 3 Unit 4

00:00:05 Hello, welcome to unit four of week three. I'm Jin Yeon Lee.
00:00:10 Let me present a case study of using BIND_AS_VALUE
00:00:15 that shows you one of our SQLScript procedures runs very slow,
00:00:20 very long in the production system. We couldn't see any performance issues
00:00:26 during developing and testing this SQLScript procedure
00:00:30 by executing statements one by one. But now, the application canceled
00:00:38 this very long-running procedure by its timeout logic. To find out the root cause,
00:00:45 we have to narrow down this issue. First of all, we have to find
00:00:50 which procedure is problematic. As a first step, let's collect the SQL Trace
00:00:57 in the production system, when the issue happens. Don't forget to set parameter internal as
true
00:01:04 in the SQL Trace section. Then let's check the collected SQL Trace.
00:01:13 In this scenario, if SQL Trace is collected successfully
00:01:18 while producing the issue, then we can see a trace message
00:01:23 or cancelation of the problematic query. We can find it by using keywords,
00:01:30 "cancelled by request". When scrolling up a little bit,
00:01:34 we can see a CALL statement having an error message. If the statement-execution-id
00:01:41 of that CALL statement is the same as the one in the error message,
00:01:47 then that CALL statement is the problematic one. Then let's find which SQL statement
00:01:54 in that procedure was canceled. When scrolling on SQL Trace
00:02:01 we can find the error query having the same statement-execution-id.
00:02:07 Of course, at this moment we cannot say this canceled SQL query
00:02:12 is our root cause of the timeout issue, because another SQL Trace might take too long
00:02:20 and this query could be canceled as a victim. Since we found the problematic CALL
statement,
00:02:27 then as our next step we have to find out which inner SQL statement takes too long.
00:02:36 Of course, we can also find information of elapsed time of each SQL statement in SQL
Trace.
00:02:44 But this time let's find that information in M_ACTIVE_PROCEDURES monitoring view.
00:02:51 Let's exclude the problematic procedure first. The procedure is not executed
00:03:00 by the application server, but us manually. It will not be canceled by timeout logic.
00:03:10 Instead, we have to check M_ACTIVE_PROCEDURES monitoring view after an amount of
timeout time.
00:03:20 Then the monitoring view will show us information of executed SQL statements
00:03:24 under this CALL procedure. M_ACTIVE_PROCEDURES monitoring view
00:03:30 shows this query takes too long. And this is the canceled query shown in the previous SQL
Trace.
00:03:43 The problematic query is Insert into the select statement on the calc view,
00:03:48 and it is a parameterized query. Parameter values are shown in the SQL Trace file.
00:03:59 Let’s assume we collect a Plan Visualizer Trace for this query,
00:04:05 with those parameter values. Then we find this calc view
00:04:11 has a multi-store table linked with dynamic tiering,
00:04:17 as a base table, and filters are now pushed down

13 / 21
00:04:22 to a remote source in dynamic tiering. Though they are given as parameters.
00:04:29 Since we know each parameter's values are used from an SQL Trace,
00:04:34 let's execute the same query as a literal one. It is executed quickly
00:04:41 and its Plan Visualizer Trace shows filters, given as constant values,
00:04:48 works well for the remote source this time. So it looks like converting
00:04:54 this parameterized query to a literal one can be a solution.
00:05:00 Let's try to use BIND_AS_VALUE. The comment determines which line we should modify.
00:05:10 The problematic SQL statement is located in line 95
00:05:15 of the definition of the procedure. Then we can see three scalar variables are shown
00:05:22 where parameters are located. Apply BIND_AS_VALUE functions
00:05:33 to these scalar variables. Then when you launch this procedure
00:05:39 in the production system, it works very well. Now the performance problem is solved
successfully.
00:05:47 Here are the key takeaways. SQL Trace shows information
00:05:52 about the executed inner SQL statements during execution of the SQLScript procedure.
00:06:01 Don't forget to configure parameter internal as true in the SQL Trace section.
00:06:11 M_ACTIVE_PROCEDURE shows information about all executed inner SQL statements
00:06:16 of an actively running procedure on the fly. Comment in the running SQL statement shows
the position
00:06:26 of its definition code. You can change or parameterize the query
00:06:33 to a literal one or vice versa by using BIND_AS_VALUE
00:06:41 or BIND_AS_PARAMETER SQLScript function. With that,
00:06:48 we've come to the end of this unit. In the next unit,
00:06:56 Minjeong will tell you about using SQL hints in SQLScript.
00:07:02 Thank you for your attention. See you.

14 / 21
Week 3 Unit 5

00:00:05 Hello, and welcome to unit five of week three. I’m Minjeong Lee and I am going to explain
how to use SQL hint in SQLScript.
00:00:15 SQL hint is an instruction for the SAP HANA database and it influences the way an SQL
request is processed.
00:00:25 HANA SQL optimizer determines the access path of a query, but you can override the
optimizer
00:00:32 by specifying hints in the query to enforce a certain access path. Hints are typically used to
optimize performance or memory consumption of a query
00:00:44 without any effect on the query result set. If you find that the query is running slow due to a
sub-optimal plan,
00:00:54 then you can apply SQL hints on that SQL statement to improve its performance. Since the
performance of inner SQL statements
00:01:04 affects the entire performance of SQLScript procedure a lot, using SQL hint for inner SQL
statements
00:01:14 can be a powerful solution to improve your SQLScript procedure performance. So, I am
going to explain how to use SQL hint for SQLScript procedure
00:01:27 during units five and six as the last topic of this course. Like ways to apply SQL hint on SQL
query, using hints for SQLScript is very similar.
00:01:41 You can add an SQL hint at the end of an inner SQL statement of an SQLScript procedure
code directly.
00:01:51 Or you can use statement hint feature or pinning hint feature. Regarding statement hint
feature,
00:02:00 this can be done by executing statement ALTER SYSTEM ADD STATEMENT HINT and
also by using the Statement Hints app of SAP HANA cockpit.
00:02:13 The pinning hint feature can be done by using the statement ALTER SYSTEM PIN SQL
PLAN CACHE ENTRY.
00:02:22 This ALTER statement links SQL hint to a certain execution plan stored in SQL plan cache.

00:02:31 Let’s see one by one. Here is the procedure HINT_TEST, which we are going to apply SQL
hint to.
00:02:44 This procedure has three inner SQL statements and they have dependency with table
variables.
00:02:52 The result of the first statement is stored in table variable RESULT1 and is consumed in the
second statement.
00:03:02 Table variable RESULT2 is used for storing a result of the second statement and it is
consumed in the last SQL statement.
00:03:13 As you learned, these three statements can be merged into a single statement by
SQLScript optimization rule inlining.
00:03:23 You can check the combined statement string via Explain Plan for CALL. Then, in this
procedure,
00:03:35 let’s add USE_HEX_PLAN SQL hint at the end of the third statement. Can you imagine how
this hint will be applied?
00:03:45 To check the answer, let’s collect Explain Plan for CALL. When clicking operator string
column of Explain Plan for CALL result,
00:04:00 you can see where the SQL hint is added. As you can see, in this SQLScript code,
00:04:08 USE_HEX_PLAN hint is added at the end of the third statement. But, SQLScript optimizer
combines the three inner SQL statements into a single one first,
00:04:20 then added SQL hint USE_HEX_PLAN at the end of the combined statement. That means
the added hint works for the combined statement,

15 / 21
00:04:31 not for the third SQL statement. So, it’s important to keep SQLScript optimization rules in
mind
00:04:42 when you are going to add SQL hints somewhere in your SQLScript procedure. Once
adding SQL hints in SQLScript procedure,
00:04:54 you should check how they will be applied by using Explain Plan for CALL, before executing
it. If you miss these two points,
00:05:05 you could be surprised because of unexpected impact of SQL hints. Then, let’s see another
example.
00:05:17 Unlike the previous example, USE_HEX_PLAN hint is added at the end of the second
statement.
00:05:24 Can you guess what will happen? Explain Plan for CALL shows two SQL statements
00:05:33 as the result of SQLScript optimization. The first and second statements are merged into a
single one,
00:05:43 then SQL hint USE_HEX_PLAN is added here. Then, can you expect what the last
statement looks like?
00:05:56 Yes, the last statement comes from the third statement in the code where RESULT2 is
consumed.
00:06:05 Here, what we should know is, adding SQL hint has also the same effect as NO_INLINE
hint
00:06:12 as well as the SQL hint functionality. So, the result of SQLScript optimization is the same
00:06:20 as when NO_INLINE hint is added at the end of the second statement in the code. Simply
speaking, adding SQL hint in SQLScript code
00:06:31 means that SQL hint is added at this position, not for a certain SQL statement only. Then,
inlining optimization stops
00:06:44 between the SQL statement where SQL hint is added and the next statement. I believe you
understand how SQLScript optimizer handles SQL hints.
00:07:00 Then, let me give you another quiz. Going back to the procedure HINT_TEST not having
any SQL hint,
00:07:09 what will happen if USE_HEX_PLAN hint is added at the end of a CALL statement? Where
do you expect this USE_HEX_PLAN hint will is applied?
00:07:26 When checking the Explain Plan for the CALL, you can see this SQL hint is at the CALL
statement itself.
00:07:36 But when checking the operator string of the inner SQL statements, you cannot see this
SQL hint.
00:07:44 This means SQL the hint at CALL statement is not propagated to inner SQL statements.
Another example is SQL hint IGNORE_PLAN_CACHE.
00:08:00 SQL hint IGNORE_PLAN_CACHE is frequently used when you want to ignore the existing
plan cache entry
00:08:08 and enforce the query to compile and execute. In case you need to clean all cached query
plans
00:08:18 including execution plan of CALL statement, you might use this IGNORE_PLAN_CACHE
hint at the end of the CALL statement.
00:08:28 But then, this IGNORE_PLAN_CACHE affects only the CALL statement. I mean that the
Execution Plan of CALL statement is compiled again,
00:08:40 but the cached SQL query plans of inner SQL statements are still used. With this
HINT_TEST procedure,
00:08:50 if you execute “CALL HINT_TEST WITH HINT (IGNORE_PLAN_CACHE)”, then, SQLScript
engine doesn’t look up its execution plan in SQL plan cache,
00:09:04 SQLScript engine compiles the execution plan again for a CALL statement. This means that
this hint works for a CALL statement itself.
00:09:16 But when SQLScript engine passes the inner SQL statement to SQL engine, this
IGNORE_PLAN_CACHE hint isn’t applied for that inner statement.

16 / 21
00:09:30 So, SQL engine will look up SQL plan cache for its query plan first, then reuse it without
query compilation.
00:09:42 But, since HANA 2.0 SPS07 and HANA Cloud QRC 4/2022, a new feature for hint
propagation has been introduced.
00:09:53 If you want to propagate SQL hint from CALL statement to inner SQL statements, you can
use the CASCADE feature,
00:10:03 which allows propagation of a hint into internal SQL statements within a procedure. Here’s
the procedure HINT_TEST again.
00:10:14 This time, it has NO_INLINE hint at the end of the second statement. You know the first two
statements will be combined
00:10:25 and the last statement will be executed separately. For this procedure, what will happen
00:10:34 if you execute this procedure with USE_HEX_PLAN hint with CASCADE option? This
USE_HEX_PLAN hint is propagated
00:10:47 to all statements after SQLScript optimization. As the output of SQLScript optimization,
00:10:57 two statements are generated, as you expected. One of them already has a hint
NO_INLINE.
00:11:05 And USE_HEX_PLAN hint is added additionally for this one. USE_HEX_PLAN is also
added to another statement.
00:11:17 In summary, the hint is applied to both the CALL statement itself and any inner SQL
statements.
00:11:26 When there are nested CALL statements, CASCADE hints are also propagated into the
nested procedures.
00:11:34 This CASCADE is only supported in CALL statements and cannot propagate hints into user-
defined functions.
00:11:47 If CASCADE is used for non-CALL statements, a FEATURE NOT SUPPORTED message
appears.
00:11:58 This is the last page of unit five. Today, we learned about how to use SQL hints in
SQLScript.
00:12:08 As you learned, to apply SQL hints, you can simply modify SQLScript code. But, don’t forget
to check how SQL hints are applied
00:12:21 by checking Explain Plan for CALL before executing it. Because adding hints affects
SQLScript optimization,
00:12:30 for example, inlining optimization stops at the statement with an SQL hint. Also, you learned
that SQL hint at the end of the call statement
00:12:44 is not propagated into inner statements by default. And only the CASCADE feature allows it.

00:12:53 In the next unit, I will continue explaining how to use SQL hint in SQLScript without
modifying SQLScript code.
00:13:03 Thank you for your attention. See you.

17 / 21
Week 3 Unit 6

00:00:05 Hello, and welcome to unit six, the final unit of this week and this course.
00:00:11 I’m Minjeong Lee and today’s topic is pinning SQL hints for SQLScript. As I explained, there
are two way to use SQL hints in SQLScript.
00:00:26 In the previous unit, we learned about using SQL hints by modifying SQLScript code
directly.
00:00:34 In this unit, I would like to talk about how to use SQL hints when you cannot modify
SQLScript code directly.
00:00:44 Without modifying SQL statements, you can add SQL hints by using
00:00:49 ALTER SYSTEM ADD STATEMENT HINT statement or ALTER SYSTEM PIN SQL PLAN
CACHE ENTRY statement.
00:01:01 Statement ALTER SYSTEM ADD STATEMENT HINT is called as "add statement hint"
feature.
00:01:09 This is a feature to add an SQL hint for a certain statement string or its hash value.
00:01:18 Statement ALTER SYSTEM PIN SQL PLAN CACHE ENTRY is called as "pinning
statement" feature.
00:01:28 This feature is originally for pinning a cached query plan in plan cache pool, but it also has
an option to add SQL hints on it.
00:01:40 In this case, Plan ID or its query plan in SQL plan cache is required. Here’s the procedure
HINT_TEST.
00:01:54 As you see, there is no SQL hint in SQLScript code. Let’s check the result of SQLScript
Plan Profiler this time.
00:02:07 It shows a single statement is executed because the three inner SQL statements are in-
lined.
00:02:16 If you’re using HANA Cloud QRC 4/2022, you can find STATEMENT_HASH value of the
executed SQL statements.
00:02:29 With this STATEMENT_HASH value, let’s add an SQL hint on this query.
00:02:35 To add SQL hint USE_HEX_PLAN, you can execute this statement:
00:02:41 ALTER SYSTEM ADD STATEMENT HINT (USE_HEX_PLAN) FOR STATEMENT HASH.
This means the SQL statement having this STATEMENT_HASH value
00:02:52 will be compiled with a given SQL hint when it's executed next time.
00:02:58 So, to do that, already-cached plan for this statement will be evicted.
00:03:10 In case your SQLScript Plan Profiler result doesn’t show STATEMENT_HASH value, then
you need to find it from M_SQL_PLAN_CACHE monitoring view.
00:03:23 Find hash values in M_SQL_PLAN_CACHE by using a proper STATEMENT_STRING
value
00:03:30 as a filter condition. After adding SQL hint,
00:03:39 SQLScript Plan Profiler or Explain plan for CALL result doesn’t show the added hint
00:03:47 since this hint is applied in SQL engine layer, not SQLScript engine.
00:03:55 Then, let’s check sqltrace to confirm if the hint is applied well. Turn on sqltrace with
parameter internal as true
00:04:07 and parameter query_plan_trace as on, then execute CALL HINT_TEST procedure.
00:04:14 Then you can find SQL hint USE_HEX_PLAN is attached well to the query in the collected
sqltrace result.
00:04:29 Here’s an example of pinning SQL hints. Pinning hints feature is a little bit different from
ADD STATEMENT HINT feature
00:04:38 as I explained before. When adding a hint by using statement ALTER SYSTEM ADD
STATEMENT HINT

18 / 21
00:04:47 with a certain statement string or hash value, this command clears the existing cached
query plan of that statement,
00:04:58 then once the same SQL string is requested, SQL engine compiles it with a given SQL hint.

00:05:07 So, if you already know the SQL statement to add the SQL hint, it doesn’t need that query
must be executed first
00:05:16 before executing our ALTER SYSTEM ADD STATEMENT HINT STATEMENT command.
Just before executing it,
00:05:26 you can add the SQL hint by using ALTER SYSTEM ADD STATEMENT HINT. But the
pinning hint works differently.
00:05:35 Pinning hints is using Plan ID of SQL PLAN CACHE ENTRY. This means this SQL
statement must be executed first,
00:05:46 so its query plan must be cached in SQL plan cache. Once executing procedure
HINT_TEST,
00:05:55 you can find the PLAN_ID of query plan of inner SQL statements in
M_SQL_PLAN_CACHE.
00:06:03 Then, you can execute ALTER SYSTEM PIN SQL PLAN CACHE ENTRY with that
PLAN_ID.
00:06:12 In this example, USE_HEX_PLAN hint is added by using the pinning hints feature. You can
use this pinning statement feature to add the SQL hint,
00:06:23 but the original pinning function is pinning a query plan in a plan cache not to be evicted,
00:06:31 until the plan becomes unpinned or the system restarts. Here’s again the procedure
HINT_TEST.
00:06:39 This time, the first statement has NO_INLINE hint. When you check the executed SQL
statement via sqltrace or SQLScript Plan Profiler,
00:06:52 you can see hexadecimal numbers, which is not in the original SQLScript code.
00:06:58 In unit two of week two, we learned it comes from a naming rule
00:07:03 for local temporary table for table variable or table parameter. Since table parameter is also
a table variable,
00:07:12 from now on, I will skip mentioning the table parameter. In this example, two SQL
statements are actually executed in procedure HINT_TEST.
00:07:30 The last one has a hexadecimal number and it is the real name of table variable RESULT1.
00:07:37 As you can see, its alias is RESULT1 This hexadecimal number is a global unique identifier,
GUID.
00:07:50 And it is used for a name of a local temporary table for table variables. The important thing
you must be aware of is
00:08:03 the real name of table variable RESULT1 is generated when the procedure is compiled. So,
if you compile CALL HINT_TEST statement again,
00:08:15 then the real name of table variable RESULT1 will be changed. Here’s an example of a
different name by changing the GUID of table variable RESULT1.
00:08:28 I get it by executing CALL HINT_TEST with hint IGNORE_PLAN_CACHE. You might
wonder why this is important and mentioned here.
00:08:44 If the real name of a table variable is changed with a new GUID value due to recompilation,
then the query strings with that table variable are also changed,
00:08:56 and the corresponding STATEMENT_HASH values too. So, it’s useless the SQL hints
which were added before
00:09:07 by using "add hint statement" feature or "pinning hint" feature
00:09:13 because their SQL statements have changed, so will not be executed anymore.
00:09:21 Instead, new SQL statements with a new actual name of table variable will be executed for
the CALL statement.
00:09:31 So, it is important to keep the real name of the table variable as long as possible

19 / 21
00:09:37 when you are using the "add hint statement" feature or the "pinning hint" feature.
00:09:43 To do that, pinning both a CALL statement and inner SQL statements with hints can be a
solution,
00:09:51 since the real name of a table variable is generated during compilation of a CALL statement.

00:10:02 Here’s an example of pinning both a CALL statement and its inner SQL statement
00:10:08 with SQL hint USE_HEX_PLAN. Check PLAN_ID in M_SQL_PLAN_CACHE after running
this procedure HINT_TEST once.
00:10:20 Then, you can find two Plan ID values, Plan ID of CALL HINT_TEST statement,
00:10:27 and Plan ID of target inner SQL statement,
00:10:36 Then you execute ALTER SYSTEM PIN statement for these two Plan ID values.
00:10:47 For the inner one, with the SQL hint USE_HEX_PLAN clause is added because you want to
add this hint for this inner statement.
00:10:59 For CALL statement, you don’t need any hint clauses because it is just for pinning plan in
SQL plan cache.
00:11:13 Here are the key takeaways of this unit. As I mentioned in the beginning,
00:11:18 adding or pinning statement hints can be a good solution when you cannot modify
SQLScript code directly to inject SQL hints.
00:11:29 When adding or pinning SQL hints, you must apply them on actual executed SQL
statements.
00:11:38 You can use STATEMENT_HASH value or PLAN ID depending on which feature is used.
00:11:45 Lastly, I explained the real names of table parameters or table variables have a GUID,
00:11:53 and this name is changed whenever SQLScript procedure is compiled. So, pinning the
CALL statement itself is very important
00:12:04 to keep SQL hints for inner statements referring to the actual name of a table variable.
00:12:13 And with that, we came to the end of this course unit and also to the end of our course.
00:12:22 During the course, we learned how SQLScript engine works with SQL engine and SQL plan
cache.
00:12:31 Also we learned SQLScript optimization rules. Then, we studied supportability features of
SQLScript,
00:12:42 which can help you to drill down your SQLScript code by yourself. Lastly, we reviewed
useful NO_INLINE hint and bind_as_parameter, bind_as_value functions,
00:12:56 and their usages. We hope you enjoyed this content
00:13:02 and will use tips immediately for your SQLScript codes. Before closing this course,
00:13:10 I would like to thank you, the learners, for your attention and my course expert colleagues
for their contribution to this course.
00:13:20 Good luck for the weekly assignment and the final exam. Goodbye.

20 / 21
© 2023 SAP SE or an SAP affiliate company. All rights reserved.
See Legal Notice on www.sap.com/legal-notice for use terms,
disclaimers, disclosures, or restrictions related to SAP Materials
for general audiences.

You might also like