dojo.md 0.2.0 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/courses/GENERATION_LOG.md +45 -0
- package/courses/aws-lambda-debugging/course.yaml +11 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/api-gateway-integration.yaml +71 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/cloudwatch-logs-basics.yaml +64 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/cold-start-basics.yaml +70 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/environment-variable-issues.yaml +72 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/first-debugging-shift.yaml +73 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/handler-import-errors.yaml +71 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/iam-permission-errors.yaml +68 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/invocation-errors.yaml +72 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/lambda-timeout-errors.yaml +65 -0
- package/courses/aws-lambda-debugging/scenarios/level-1/memory-and-oom.yaml +70 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/async-invocation-failures.yaml +72 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/cold-start-optimization.yaml +76 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/dynamodb-streams-debugging.yaml +70 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/intermediate-debugging-shift.yaml +71 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/lambda-concurrency-management.yaml +70 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/lambda-layers-debugging.yaml +76 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/sam-local-debugging.yaml +74 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/sqs-event-source.yaml +72 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/vpc-networking-issues.yaml +71 -0
- package/courses/aws-lambda-debugging/scenarios/level-2/xray-tracing.yaml +62 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/advanced-debugging-shift.yaml +72 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/container-image-lambda.yaml +79 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/cross-account-invocation.yaml +72 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/eventbridge-patterns.yaml +79 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/iac-deployment-debugging.yaml +68 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/kinesis-stream-processing.yaml +64 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/lambda-at-edge.yaml +64 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/lambda-extensions-debugging.yaml +67 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/powertools-observability.yaml +79 -0
- package/courses/aws-lambda-debugging/scenarios/level-3/step-functions-debugging.yaml +80 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/cost-optimization-strategy.yaml +67 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/expert-debugging-shift.yaml +62 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/incident-management-serverless.yaml +61 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/multi-region-serverless.yaml +67 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/observability-platform-design.yaml +71 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/serverless-architecture-design.yaml +64 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/serverless-data-architecture.yaml +66 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/serverless-migration-strategy.yaml +65 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/serverless-security-design.yaml +60 -0
- package/courses/aws-lambda-debugging/scenarios/level-4/serverless-testing-strategy.yaml +62 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/board-serverless-strategy.yaml +63 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/consulting-serverless-adoption.yaml +57 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/industry-serverless-patterns.yaml +62 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/ma-serverless-integration.yaml +75 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/master-debugging-shift.yaml +61 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/organizational-serverless-transformation.yaml +65 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/regulatory-serverless.yaml +61 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/serverless-economics.yaml +65 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/serverless-future-technology.yaml +66 -0
- package/courses/aws-lambda-debugging/scenarios/level-5/serverless-platform-design.yaml +71 -0
- package/courses/docker-container-debugging/course.yaml +11 -0
- package/courses/docker-container-debugging/scenarios/level-1/container-exit-codes.yaml +59 -0
- package/courses/docker-container-debugging/scenarios/level-1/container-networking-basics.yaml +69 -0
- package/courses/docker-container-debugging/scenarios/level-1/docker-logs-debugging.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-1/dockerfile-build-failures.yaml +71 -0
- package/courses/docker-container-debugging/scenarios/level-1/environment-variable-issues.yaml +74 -0
- package/courses/docker-container-debugging/scenarios/level-1/first-debugging-shift.yaml +70 -0
- package/courses/docker-container-debugging/scenarios/level-1/image-pull-failures.yaml +68 -0
- package/courses/docker-container-debugging/scenarios/level-1/port-mapping-issues.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-1/resource-limits-oom.yaml +70 -0
- package/courses/docker-container-debugging/scenarios/level-1/volume-mount-problems.yaml +66 -0
- package/courses/docker-container-debugging/scenarios/level-2/container-health-checks.yaml +73 -0
- package/courses/docker-container-debugging/scenarios/level-2/docker-compose-debugging.yaml +66 -0
- package/courses/docker-container-debugging/scenarios/level-2/docker-exec-debugging.yaml +71 -0
- package/courses/docker-container-debugging/scenarios/level-2/image-layer-optimization.yaml +81 -0
- package/courses/docker-container-debugging/scenarios/level-2/intermediate-debugging-shift.yaml +73 -0
- package/courses/docker-container-debugging/scenarios/level-2/logging-and-log-rotation.yaml +76 -0
- package/courses/docker-container-debugging/scenarios/level-2/multi-stage-build-debugging.yaml +76 -0
- package/courses/docker-container-debugging/scenarios/level-2/network-debugging-tools.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-2/pid1-signal-handling.yaml +71 -0
- package/courses/docker-container-debugging/scenarios/level-2/security-scanning-basics.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-3/advanced-debugging-shift.yaml +77 -0
- package/courses/docker-container-debugging/scenarios/level-3/buildkit-optimization.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-3/container-filesystem-debugging.yaml +70 -0
- package/courses/docker-container-debugging/scenarios/level-3/container-security-hardening.yaml +74 -0
- package/courses/docker-container-debugging/scenarios/level-3/disk-space-management.yaml +74 -0
- package/courses/docker-container-debugging/scenarios/level-3/docker-api-automation.yaml +72 -0
- package/courses/docker-container-debugging/scenarios/level-3/docker-daemon-issues.yaml +73 -0
- package/courses/docker-container-debugging/scenarios/level-3/docker-in-docker-ci.yaml +69 -0
- package/courses/docker-container-debugging/scenarios/level-3/overlay-network-debugging.yaml +70 -0
- package/courses/docker-container-debugging/scenarios/level-3/production-container-ops.yaml +71 -0
- package/courses/docker-container-debugging/scenarios/level-4/cicd-pipeline-design.yaml +66 -0
- package/courses/docker-container-debugging/scenarios/level-4/container-monitoring-observability.yaml +63 -0
- package/courses/docker-container-debugging/scenarios/level-4/container-orchestration-strategy.yaml +62 -0
- package/courses/docker-container-debugging/scenarios/level-4/container-performance-engineering.yaml +64 -0
- package/courses/docker-container-debugging/scenarios/level-4/container-security-architecture.yaml +66 -0
- package/courses/docker-container-debugging/scenarios/level-4/enterprise-image-management.yaml +58 -0
- package/courses/docker-container-debugging/scenarios/level-4/expert-debugging-shift.yaml +63 -0
- package/courses/docker-container-debugging/scenarios/level-4/incident-response-containers.yaml +70 -0
- package/courses/docker-container-debugging/scenarios/level-4/multi-environment-management.yaml +65 -0
- package/courses/docker-container-debugging/scenarios/level-4/stateful-service-containers.yaml +65 -0
- package/courses/docker-container-debugging/scenarios/level-5/board-infrastructure-strategy.yaml +58 -0
- package/courses/docker-container-debugging/scenarios/level-5/consulting-container-strategy.yaml +61 -0
- package/courses/docker-container-debugging/scenarios/level-5/container-platform-architecture.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-5/container-platform-economics.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-5/container-technology-evolution.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-5/disaster-recovery-containers.yaml +66 -0
- package/courses/docker-container-debugging/scenarios/level-5/industry-container-patterns.yaml +71 -0
- package/courses/docker-container-debugging/scenarios/level-5/master-debugging-shift.yaml +62 -0
- package/courses/docker-container-debugging/scenarios/level-5/organizational-transformation.yaml +67 -0
- package/courses/docker-container-debugging/scenarios/level-5/regulatory-compliance-containers.yaml +61 -0
- package/courses/kubernetes-deployment-troubleshooting/course.yaml +12 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/configmap-secret-issues.yaml +69 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/crashloopbackoff.yaml +68 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/deployment-rollout.yaml +56 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/first-troubleshooting-shift.yaml +65 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/health-probe-failures.yaml +70 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/imagepullbackoff.yaml +57 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/kubectl-debugging-basics.yaml +56 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/oomkilled.yaml +70 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/pending-pods.yaml +68 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-1/service-not-reachable.yaml +66 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/dns-resolution-failures.yaml +63 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/helm-deployment-failures.yaml +63 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/hpa-scaling-issues.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/ingress-routing-issues.yaml +63 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/init-container-failures.yaml +63 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/intermediate-troubleshooting-shift.yaml +66 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/network-policy-blocking.yaml +67 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/persistent-volume-issues.yaml +69 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/rbac-permission-denied.yaml +57 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-2/resource-quota-limits.yaml +64 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/advanced-troubleshooting-shift.yaml +69 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/cluster-upgrade-failures.yaml +71 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/gitops-drift-detection.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/job-cronjob-failures.yaml +67 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/monitoring-alerting-gaps.yaml +64 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/multi-container-debugging.yaml +68 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/node-pressure-evictions.yaml +70 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/pod-disruption-budgets.yaml +59 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/service-mesh-debugging.yaml +64 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-3/statefulset-troubleshooting.yaml +69 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/capacity-planning.yaml +65 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/cost-optimization.yaml +57 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/disaster-recovery-design.yaml +56 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/executive-communication.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/expert-troubleshooting-shift.yaml +65 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/incident-management-process.yaml +59 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/multi-cluster-operations.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/multi-tenancy-design.yaml +55 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/platform-engineering.yaml +59 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-4/security-hardening.yaml +58 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/behavioral-science.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/board-strategy.yaml +61 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/cloud-native-future.yaml +65 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/comprehensive-platform.yaml +57 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/consulting-engagement.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/industry-benchmarks.yaml +58 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/ma-integration.yaml +62 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/master-troubleshooting-shift.yaml +73 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/product-development.yaml +65 -0
- package/courses/kubernetes-deployment-troubleshooting/scenarios/level-5/regulatory-compliance.yaml +76 -0
- package/courses/mysql-query-optimization/course.yaml +11 -0
- package/courses/mysql-query-optimization/scenarios/level-1/buffer-pool-basics.yaml +65 -0
- package/courses/mysql-query-optimization/scenarios/level-1/explain-basics.yaml +66 -0
- package/courses/mysql-query-optimization/scenarios/level-1/first-optimization-shift.yaml +78 -0
- package/courses/mysql-query-optimization/scenarios/level-1/innodb-index-fundamentals.yaml +68 -0
- package/courses/mysql-query-optimization/scenarios/level-1/join-basics.yaml +66 -0
- package/courses/mysql-query-optimization/scenarios/level-1/n-plus-one-queries.yaml +67 -0
- package/courses/mysql-query-optimization/scenarios/level-1/query-rewriting-basics.yaml +66 -0
- package/courses/mysql-query-optimization/scenarios/level-1/select-star-problems.yaml +68 -0
- package/courses/mysql-query-optimization/scenarios/level-1/slow-query-diagnosis.yaml +65 -0
- package/courses/mysql-query-optimization/scenarios/level-1/where-clause-optimization.yaml +65 -0
- package/courses/mysql-query-optimization/scenarios/level-2/buffer-pool-tuning.yaml +64 -0
- package/courses/mysql-query-optimization/scenarios/level-2/composite-index-design.yaml +71 -0
- package/courses/mysql-query-optimization/scenarios/level-2/covering-and-invisible-indexes.yaml +69 -0
- package/courses/mysql-query-optimization/scenarios/level-2/cte-and-window-functions.yaml +78 -0
- package/courses/mysql-query-optimization/scenarios/level-2/intermediate-optimization-shift.yaml +68 -0
- package/courses/mysql-query-optimization/scenarios/level-2/join-optimization.yaml +67 -0
- package/courses/mysql-query-optimization/scenarios/level-2/performance-schema-analysis.yaml +69 -0
- package/courses/mysql-query-optimization/scenarios/level-2/query-optimizer-hints.yaml +74 -0
- package/courses/mysql-query-optimization/scenarios/level-2/subquery-optimization.yaml +70 -0
- package/courses/mysql-query-optimization/scenarios/level-2/write-optimization.yaml +63 -0
- package/courses/mysql-query-optimization/scenarios/level-3/advanced-optimization-shift.yaml +71 -0
- package/courses/mysql-query-optimization/scenarios/level-3/connection-management.yaml +67 -0
- package/courses/mysql-query-optimization/scenarios/level-3/full-text-search.yaml +77 -0
- package/courses/mysql-query-optimization/scenarios/level-3/json-optimization.yaml +87 -0
- package/courses/mysql-query-optimization/scenarios/level-3/lock-contention-analysis.yaml +68 -0
- package/courses/mysql-query-optimization/scenarios/level-3/monitoring-alerting.yaml +63 -0
- package/courses/mysql-query-optimization/scenarios/level-3/online-schema-changes.yaml +79 -0
- package/courses/mysql-query-optimization/scenarios/level-3/partitioning-strategies.yaml +83 -0
- package/courses/mysql-query-optimization/scenarios/level-3/query-profiling-deep-dive.yaml +84 -0
- package/courses/mysql-query-optimization/scenarios/level-3/replication-optimization.yaml +66 -0
- package/courses/mysql-query-optimization/scenarios/level-4/aurora-vs-rds-evaluation.yaml +61 -0
- package/courses/mysql-query-optimization/scenarios/level-4/data-architecture.yaml +62 -0
- package/courses/mysql-query-optimization/scenarios/level-4/database-migration-planning.yaml +59 -0
- package/courses/mysql-query-optimization/scenarios/level-4/enterprise-governance.yaml +50 -0
- package/courses/mysql-query-optimization/scenarios/level-4/executive-communication.yaml +54 -0
- package/courses/mysql-query-optimization/scenarios/level-4/expert-optimization-shift.yaml +67 -0
- package/courses/mysql-query-optimization/scenarios/level-4/high-availability-architecture.yaml +60 -0
- package/courses/mysql-query-optimization/scenarios/level-4/optimizer-internals.yaml +62 -0
- package/courses/mysql-query-optimization/scenarios/level-4/performance-sla-design.yaml +52 -0
- package/courses/mysql-query-optimization/scenarios/level-4/read-replica-scaling.yaml +51 -0
- package/courses/mysql-query-optimization/scenarios/level-5/ai-database-future.yaml +45 -0
- package/courses/mysql-query-optimization/scenarios/level-5/behavioral-science.yaml +44 -0
- package/courses/mysql-query-optimization/scenarios/level-5/benchmark-design.yaml +47 -0
- package/courses/mysql-query-optimization/scenarios/level-5/board-strategy.yaml +48 -0
- package/courses/mysql-query-optimization/scenarios/level-5/comprehensive-platform.yaml +49 -0
- package/courses/mysql-query-optimization/scenarios/level-5/consulting-engagement.yaml +52 -0
- package/courses/mysql-query-optimization/scenarios/level-5/ma-database-integration.yaml +47 -0
- package/courses/mysql-query-optimization/scenarios/level-5/master-optimization-shift.yaml +56 -0
- package/courses/mysql-query-optimization/scenarios/level-5/product-development.yaml +48 -0
- package/courses/mysql-query-optimization/scenarios/level-5/regulatory-compliance.yaml +48 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/comprehensive-database-system.yaml +70 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-ai-future.yaml +81 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-behavioral-science.yaml +63 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-board-strategy.yaml +77 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-consulting-engagement.yaml +61 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-industry-benchmarks.yaml +64 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-ma-integration.yaml +71 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-product-development.yaml +72 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/database-regulatory-landscape.yaml +76 -0
- package/courses/postgresql-query-optimization/scenarios/level-5/master-optimization-shift.yaml +66 -0
- package/courses/terraform-infrastructure-setup/course.yaml +11 -0
- package/courses/terraform-infrastructure-setup/scenarios/level-1/terraform-init-errors.yaml +72 -0
- package/dist/mcp/session-manager.d.ts +7 -4
- package/dist/mcp/session-manager.d.ts.map +1 -1
- package/dist/mcp/session-manager.js +23 -8
- package/dist/mcp/session-manager.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: cte-and-window-functions
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Optimize CTEs and window functions — use MySQL 8.0 features effectively while understanding their performance implications"
|
|
7
|
+
tags: [MySQL, CTE, window-functions, MySQL-8, optimization, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your team is migrating queries from subqueries to CTEs and window
|
|
13
|
+
functions (MySQL 8.0 upgrade). Some rewritten queries are faster,
|
|
14
|
+
but others are unexpectedly slower. You need to understand why.
|
|
15
|
+
|
|
16
|
+
Query 1 — CTE that got slower:
|
|
17
|
+
-- Old (subquery, 200ms):
|
|
18
|
+
SELECT * FROM (SELECT customer_id, SUM(total) AS total_spent
|
|
19
|
+
FROM orders GROUP BY customer_id) AS sub
|
|
20
|
+
WHERE total_spent > 10000;
|
|
21
|
+
|
|
22
|
+
-- New (CTE, 500ms):
|
|
23
|
+
WITH high_spenders AS (
|
|
24
|
+
SELECT customer_id, SUM(total) AS total_spent
|
|
25
|
+
FROM orders GROUP BY customer_id
|
|
26
|
+
)
|
|
27
|
+
SELECT * FROM high_spenders WHERE total_spent > 10000;
|
|
28
|
+
|
|
29
|
+
Why is the CTE slower? MySQL 8.0 may materialize the CTE into a
|
|
30
|
+
temporary table, while the derived table (subquery) gets merged into
|
|
31
|
+
the outer query by the optimizer.
|
|
32
|
+
|
|
33
|
+
Query 2 — Window function vs self-join:
|
|
34
|
+
-- Old (self-join, 5 seconds):
|
|
35
|
+
SELECT o1.*, (SELECT COUNT(*) FROM orders o2
|
|
36
|
+
WHERE o2.customer_id = o1.customer_id
|
|
37
|
+
AND o2.created_at <= o1.created_at) AS order_number
|
|
38
|
+
FROM orders o1 WHERE o1.customer_id = 42;
|
|
39
|
+
|
|
40
|
+
-- New (window function, 50ms):
|
|
41
|
+
SELECT *, ROW_NUMBER() OVER (
|
|
42
|
+
PARTITION BY customer_id ORDER BY created_at
|
|
43
|
+
) AS order_number
|
|
44
|
+
FROM orders WHERE customer_id = 42;
|
|
45
|
+
|
|
46
|
+
Query 3 — Running total with window function:
|
|
47
|
+
SELECT id, amount,
|
|
48
|
+
SUM(amount) OVER (ORDER BY created_at
|
|
49
|
+
ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS running_total,
|
|
50
|
+
AVG(amount) OVER (ORDER BY created_at
|
|
51
|
+
ROWS BETWEEN 6 PRECEDING AND CURRENT ROW) AS moving_avg_7
|
|
52
|
+
FROM transactions WHERE account_id = 1;
|
|
53
|
+
|
|
54
|
+
Questions:
|
|
55
|
+
1. When do CTEs get materialized vs merged?
|
|
56
|
+
2. How do window functions handle the OVER clause efficiently?
|
|
57
|
+
3. Can window functions use indexes?
|
|
58
|
+
4. What's the performance impact of multiple OVER clauses?
|
|
59
|
+
|
|
60
|
+
Task: Explain CTE and window function optimization in MySQL 8.0.
|
|
61
|
+
Write: when CTEs are materialized vs merged (and how to control it),
|
|
62
|
+
how window functions are executed (sort-based processing), when window
|
|
63
|
+
functions outperform self-joins, how to optimize queries with multiple
|
|
64
|
+
window functions, and common pitfalls.
|
|
65
|
+
|
|
66
|
+
assertions:
|
|
67
|
+
- type: llm_judge
|
|
68
|
+
criteria: "CTE materialization is explained — MySQL 8.0 may materialize CTEs into temporary tables (adding overhead), while derived tables can be merged into the outer query. A CTE is materialized if: referenced more than once, is recursive, or optimizer chooses materialization. Use EXPLAIN to check. Can influence with optimizer_switch derived_merge"
|
|
69
|
+
weight: 0.35
|
|
70
|
+
description: "CTE materialization explained"
|
|
71
|
+
- type: llm_judge
|
|
72
|
+
criteria: "Window function execution is explained — MySQL sorts data by the PARTITION BY and ORDER BY columns, then processes the window frame for each row. Multiple OVER clauses with different orderings may require multiple sorts. Same OVER clause shared across functions avoids re-sorting. Indexes on (partition_col, order_col) help avoid explicit sorts"
|
|
73
|
+
weight: 0.35
|
|
74
|
+
description: "Window function execution"
|
|
75
|
+
- type: llm_judge
|
|
76
|
+
criteria: "Practical optimization advice is provided — use named WINDOW clauses to share sort operations, prefer ROW_NUMBER over self-joins for ranking, be aware that window functions process all rows before LIMIT (so add WHERE filters to reduce the window), and compare CTE vs derived table performance with EXPLAIN"
|
|
77
|
+
weight: 0.30
|
|
78
|
+
description: "Practical optimization advice"
|
package/courses/mysql-query-optimization/scenarios/level-2/intermediate-optimization-shift.yaml
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: intermediate-optimization-shift
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Intermediate optimization shift — tune a MySQL server for a growing SaaS application combining indexing, buffer pool, and query optimization"
|
|
7
|
+
tags: [MySQL, shift-simulation, SaaS, tuning, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
You're the sole DBA for a SaaS application that's grown from 100
|
|
13
|
+
to 10,000 customers in 6 months. MySQL was set up once and never
|
|
14
|
+
tuned. Performance has degraded steadily, and the CEO says "the
|
|
15
|
+
app feels slow — fix it by Friday."
|
|
16
|
+
|
|
17
|
+
Server: MySQL 8.0 on RDS (db.r6g.2xlarge, 8 vCPU, 64GB RAM)
|
|
18
|
+
|
|
19
|
+
Performance Schema top issues:
|
|
20
|
+
1. 45 queries with full table scans (type=ALL in EXPLAIN)
|
|
21
|
+
2. Buffer pool hit ratio: 82% (innodb_buffer_pool_size=8GB)
|
|
22
|
+
3. 38 unused indexes consuming 5GB
|
|
23
|
+
4. Top query by total time: multi-tenant dashboard query
|
|
24
|
+
SELECT * FROM activities
|
|
25
|
+
WHERE tenant_id = ? AND created_at >= ?
|
|
26
|
+
ORDER BY created_at DESC LIMIT 50;
|
|
27
|
+
— No composite index on (tenant_id, created_at)
|
|
28
|
+
— Executes 200K times/day, avg 500ms each
|
|
29
|
+
|
|
30
|
+
5. Second highest: user search
|
|
31
|
+
SELECT * FROM users WHERE LOWER(email) LIKE '%@gmail.com';
|
|
32
|
+
— Full table scan (function on column + leading wildcard)
|
|
33
|
+
— Executes 50K times/day, avg 200ms each
|
|
34
|
+
|
|
35
|
+
6. Lock contention on the subscriptions table:
|
|
36
|
+
UPDATE subscriptions SET status = 'expired'
|
|
37
|
+
WHERE end_date < NOW() AND status = 'active';
|
|
38
|
+
— Runs every minute via cron, locks 5,000 rows for 3 seconds
|
|
39
|
+
— Blocks checkout flow (which also updates subscriptions)
|
|
40
|
+
|
|
41
|
+
7. Slow nightly report:
|
|
42
|
+
SELECT tenant_id, COUNT(*), SUM(amount)
|
|
43
|
+
FROM invoices GROUP BY tenant_id;
|
|
44
|
+
— 50M rows, takes 8 minutes, pollutes buffer pool
|
|
45
|
+
|
|
46
|
+
8. Connection issues:
|
|
47
|
+
max_connections = 151 (default)
|
|
48
|
+
Current connections: 145 (at capacity during peak)
|
|
49
|
+
Many connections in Sleep state (idle 300+ seconds)
|
|
50
|
+
|
|
51
|
+
Task: Write the optimization plan. Include: the immediate fixes
|
|
52
|
+
(what to do today), the index changes (add and remove), the
|
|
53
|
+
configuration tuning (buffer pool, connections), the query rewrites,
|
|
54
|
+
and the priority order with expected impact.
|
|
55
|
+
|
|
56
|
+
assertions:
|
|
57
|
+
- type: llm_judge
|
|
58
|
+
criteria: "Immediate fixes are high-impact — adds composite index on activities(tenant_id, created_at) as top priority (200K queries × 500ms → <10ms = saves 27 hours/day of query time), increases buffer pool to 48GB (75% of 64GB), and increases max_connections or adds connection timeout to handle the Sleep connections"
|
|
59
|
+
weight: 0.35
|
|
60
|
+
description: "High-impact immediate fixes"
|
|
61
|
+
- type: llm_judge
|
|
62
|
+
criteria: "All 8 issues are addressed — full table scans (add indexes), buffer pool (resize), unused indexes (make invisible then drop), dashboard query (composite index), user search (rewrite LOWER + wildcard, consider full-text search), lock contention (batch the UPDATE into smaller chunks or use WHERE + LIMIT), nightly report (run on read replica), connection management (reduce wait_timeout, consider ProxySQL)"
|
|
63
|
+
weight: 0.35
|
|
64
|
+
description: "All issues addressed"
|
|
65
|
+
- type: llm_judge
|
|
66
|
+
criteria: "Priority order maximizes impact — ranks fixes by total time saved or risk reduction, estimates improvement for each fix, and groups into 'do today' (index + buffer pool), 'this week' (query rewrites, connection tuning), and 'next sprint' (lock contention redesign, read replica for reports)"
|
|
67
|
+
weight: 0.30
|
|
68
|
+
description: "Prioritized action plan"
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: join-optimization
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Optimize MySQL JOIN execution — understand join buffer, block nested loop, hash join, and how to choose the right join strategy"
|
|
7
|
+
tags: [MySQL, JOIN, hash-join, block-nested-loop, join-buffer, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your analytics report query joins 5 tables and takes 45 seconds.
|
|
13
|
+
The EXPLAIN output reveals a mix of efficient and inefficient join
|
|
14
|
+
methods:
|
|
15
|
+
|
|
16
|
+
SELECT o.id, c.name, p.name, cat.name, s.tracking_number
|
|
17
|
+
FROM orders o
|
|
18
|
+
JOIN customers c ON c.id = o.customer_id
|
|
19
|
+
JOIN order_items oi ON oi.order_id = o.id
|
|
20
|
+
JOIN products p ON p.id = oi.product_id
|
|
21
|
+
JOIN categories cat ON cat.code = p.category_code
|
|
22
|
+
JOIN shipments s ON s.order_id = o.id AND s.status = 'shipped'
|
|
23
|
+
WHERE o.created_at >= '2025-01-01'
|
|
24
|
+
AND o.created_at < '2025-02-01';
|
|
25
|
+
|
|
26
|
+
EXPLAIN:
|
|
27
|
+
| table | type | key | rows | Extra |
|
|
28
|
+
|-------|---------|-------------------|--------|-----------------------------|
|
|
29
|
+
| o | range | idx_created_at | 500000 | Using index condition |
|
|
30
|
+
| c | eq_ref | PRIMARY | 1 | |
|
|
31
|
+
| oi | ref | idx_order_id | 3 | |
|
|
32
|
+
| p | eq_ref | PRIMARY | 1 | |
|
|
33
|
+
| cat | ALL | NULL | 500 | Using where; Using join buf |
|
|
34
|
+
| s | ref | idx_order_id | 1 | Using where |
|
|
35
|
+
|
|
36
|
+
Problems identified:
|
|
37
|
+
1. categories table uses ALL (full table scan per join iteration) even
|
|
38
|
+
though it's only 500 rows — no index on categories.code
|
|
39
|
+
2. The join buffer (block nested-loop) is being used for categories
|
|
40
|
+
3. With 500K orders × 3 items × 500 categories = many iterations
|
|
41
|
+
4. join_buffer_size is default 256KB
|
|
42
|
+
|
|
43
|
+
MySQL 8.0 changes:
|
|
44
|
+
- MySQL 8.0.18+ uses hash join instead of block nested-loop for
|
|
45
|
+
equi-joins without indexes
|
|
46
|
+
- MySQL 8.0.20+ removed block nested-loop entirely
|
|
47
|
+
- Hash join performance depends on join_buffer_size
|
|
48
|
+
|
|
49
|
+
Task: Optimize this join query. Write: why the categories join is
|
|
50
|
+
slow (missing index + join strategy), the difference between nested-
|
|
51
|
+
loop, block nested-loop, and hash join, how join_buffer_size affects
|
|
52
|
+
performance, the optimal indexes for this query, and how to read the
|
|
53
|
+
join-related EXPLAIN output.
|
|
54
|
+
|
|
55
|
+
assertions:
|
|
56
|
+
- type: llm_judge
|
|
57
|
+
criteria: "Categories join fix is correct — ADD INDEX idx_code(code) on categories table eliminates the full table scan, changing type from ALL to eq_ref. Explains that even though categories is small (500 rows), the full scan is repeated for each row from the products join (1.5M iterations)"
|
|
58
|
+
weight: 0.35
|
|
59
|
+
description: "Categories join fix"
|
|
60
|
+
- type: llm_judge
|
|
61
|
+
criteria: "Join algorithms are explained — nested-loop (for each outer row, scan inner table using index), block nested-loop (buffer outer rows, scan inner table once per buffer-full, pre-8.0.20), hash join (build hash table on smaller table, probe with larger table, 8.0.18+). Hash join is used when no index available on join column. join_buffer_size controls how much memory for hash/block-NL"
|
|
62
|
+
weight: 0.35
|
|
63
|
+
description: "Join algorithms explained"
|
|
64
|
+
- type: llm_judge
|
|
65
|
+
criteria: "EXPLAIN join-related output is decoded — 'Using join buffer (Block Nested Loop)' or 'Using join buffer (hash join)' in Extra, how the rows column estimates are multiplied across joins (500K × 3 × 1 × 1 × 500 × 1 for this query), and how eq_ref vs ref vs ALL determines the join strategy per table"
|
|
66
|
+
weight: 0.30
|
|
67
|
+
description: "EXPLAIN join output decoded"
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: performance-schema-analysis
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Analyze MySQL with Performance Schema — use events_statements, sys schema views, and digest tables to identify optimization targets"
|
|
7
|
+
tags: [MySQL, Performance-Schema, sys-schema, monitoring, analysis, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your team needs to identify the top optimization opportunities across
|
|
13
|
+
your MySQL database. The slow query log captures individual slow
|
|
14
|
+
queries, but you want a complete picture of all query performance.
|
|
15
|
+
Performance Schema is enabled but nobody on the team knows how to
|
|
16
|
+
use it effectively.
|
|
17
|
+
|
|
18
|
+
Available data sources:
|
|
19
|
+
1. performance_schema.events_statements_summary_by_digest
|
|
20
|
+
— Aggregated query statistics (the most valuable table)
|
|
21
|
+
2. performance_schema.events_waits_summary_by_instance
|
|
22
|
+
— Where time is spent waiting (I/O, locks, mutexes)
|
|
23
|
+
3. sys.schema_unused_indexes
|
|
24
|
+
— Indexes that haven't been used since last server restart
|
|
25
|
+
4. sys.statements_with_full_table_scans
|
|
26
|
+
— Queries performing full table scans
|
|
27
|
+
5. sys.innodb_lock_waits
|
|
28
|
+
— Current lock wait chains
|
|
29
|
+
|
|
30
|
+
Your initial analysis reveals:
|
|
31
|
+
|
|
32
|
+
Top 5 queries by total time (events_statements_summary_by_digest):
|
|
33
|
+
| digest_text (truncated) | count | avg_ms | total_min | rows_exam | rows_sent |
|
|
34
|
+
|-------------------------------|--------|--------|-----------|-----------|-----------|
|
|
35
|
+
| SELECT * FROM orders WHERE... | 500K | 50 | 416 | 2.5B | 500K |
|
|
36
|
+
| SELECT p.*, COUNT(r...)... | 50K | 200 | 166 | 5B | 50K |
|
|
37
|
+
| INSERT INTO audit_log... | 2M | 5 | 166 | 0 | 0 |
|
|
38
|
+
| SELECT * FROM users WHERE... | 1M | 10 | 166 | 100M | 1M |
|
|
39
|
+
| UPDATE inventory SET... | 100K | 100 | 166 | 100M | 0 |
|
|
40
|
+
|
|
41
|
+
Unused indexes: 45 indexes consuming 12GB of storage
|
|
42
|
+
|
|
43
|
+
Full table scan queries: 23 queries, top one examining 2B rows/day
|
|
44
|
+
|
|
45
|
+
Questions to answer:
|
|
46
|
+
1. How to interpret the rows_examined vs rows_sent ratio?
|
|
47
|
+
2. Which query should we optimize first?
|
|
48
|
+
3. How to use sys schema for quick wins?
|
|
49
|
+
4. How to track query performance after optimization?
|
|
50
|
+
|
|
51
|
+
Task: Write the Performance Schema analysis guide. Include: how to
|
|
52
|
+
query the key Performance Schema tables, how to interpret the results
|
|
53
|
+
(which metrics matter most), the prioritization framework (which
|
|
54
|
+
queries to optimize first), the sys schema quick wins, and how to
|
|
55
|
+
set up ongoing monitoring.
|
|
56
|
+
|
|
57
|
+
assertions:
|
|
58
|
+
- type: llm_judge
|
|
59
|
+
criteria: "Key queries for Performance Schema are provided — shows SQL for top queries by total time, by rows examined, by frequency, and the rows_examined/rows_sent ratio as an efficiency metric. Explains that a ratio of 5000:1 (query #1) means 5000 rows are read for every 1 returned — a clear index problem"
|
|
60
|
+
weight: 0.35
|
|
61
|
+
description: "Performance Schema queries"
|
|
62
|
+
- type: llm_judge
|
|
63
|
+
criteria: "Prioritization framework is practical — optimizes by total time impact (not just per-query time), considers query #1 first (500K executions × 50ms = 416 minutes/day, high volume), explains that the INSERT query (#3) has high total time but low per-query time (may not be optimizable), and the UPDATE (#5) has high per-query time suggesting a missing index or lock contention"
|
|
64
|
+
weight: 0.35
|
|
65
|
+
description: "Practical prioritization"
|
|
66
|
+
- type: llm_judge
|
|
67
|
+
criteria: "Sys schema quick wins are identified — sys.schema_unused_indexes (drop 45 unused indexes to save 12GB and speed writes), sys.statements_with_full_table_scans (add indexes for top full-scan queries), sys.innodb_lock_waits (identify blocking transactions), and explains how to reset Performance Schema counters (TRUNCATE TABLE) to measure improvement after changes"
|
|
68
|
+
weight: 0.30
|
|
69
|
+
description: "Sys schema quick wins"
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: query-optimizer-hints
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Use MySQL optimizer hints — influence query plans with index hints, optimizer_switch, and MySQL 8.0 hint syntax"
|
|
7
|
+
tags: [MySQL, optimizer-hints, USE-INDEX, FORCE-INDEX, optimizer-switch, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your application has a query that usually runs in 5ms but
|
|
13
|
+
occasionally switches to a slow plan (15 seconds). The DBA says
|
|
14
|
+
the optimizer's statistics are sometimes stale, causing it to choose
|
|
15
|
+
a full table scan instead of an index scan. You need to understand
|
|
16
|
+
how to influence the optimizer's choices.
|
|
17
|
+
|
|
18
|
+
The query:
|
|
19
|
+
SELECT * FROM orders
|
|
20
|
+
WHERE customer_id = 42 AND status = 'pending'
|
|
21
|
+
ORDER BY created_at DESC LIMIT 10;
|
|
22
|
+
|
|
23
|
+
Fast plan (normal): Uses idx_customer_status (customer_id, status)
|
|
24
|
+
Slow plan (occasional): Full table scan when optimizer estimates
|
|
25
|
+
the index will return too many rows (stale statistics)
|
|
26
|
+
|
|
27
|
+
MySQL hint mechanisms:
|
|
28
|
+
|
|
29
|
+
1. Traditional index hints (SQL-level):
|
|
30
|
+
SELECT * FROM orders USE INDEX (idx_customer_status) WHERE ...
|
|
31
|
+
SELECT * FROM orders FORCE INDEX (idx_customer_status) WHERE ...
|
|
32
|
+
SELECT * FROM orders IGNORE INDEX (idx_status) WHERE ...
|
|
33
|
+
|
|
34
|
+
2. MySQL 8.0+ optimizer hints (comment-based):
|
|
35
|
+
SELECT /*+ INDEX(orders idx_customer_status) */ * FROM orders ...
|
|
36
|
+
SELECT /*+ NO_INDEX(orders idx_status) */ * FROM orders ...
|
|
37
|
+
SELECT /*+ JOIN_ORDER(orders, customers) */ ...
|
|
38
|
+
SELECT /*+ SET_VAR(join_buffer_size=16M) */ ...
|
|
39
|
+
SELECT /*+ MAX_EXECUTION_TIME(5000) */ ... -- timeout in ms
|
|
40
|
+
|
|
41
|
+
3. optimizer_switch (session/global):
|
|
42
|
+
SET optimizer_switch = 'index_merge=off';
|
|
43
|
+
SET optimizer_switch = 'block_nested_loop=off';
|
|
44
|
+
SET optimizer_switch = 'derived_merge=off';
|
|
45
|
+
|
|
46
|
+
4. ANALYZE TABLE (update statistics):
|
|
47
|
+
ANALYZE TABLE orders; -- Recalculate index statistics
|
|
48
|
+
|
|
49
|
+
Common scenarios where hints are needed:
|
|
50
|
+
A. Plan instability (same query, different plans)
|
|
51
|
+
B. Optimizer choosing wrong join order
|
|
52
|
+
C. Index merge being slower than single index
|
|
53
|
+
D. Derived table merging causing performance regression
|
|
54
|
+
E. Setting per-query memory limits
|
|
55
|
+
|
|
56
|
+
Task: Explain when and how to use optimizer hints. Write: the
|
|
57
|
+
difference between USE INDEX, FORCE INDEX, and IGNORE INDEX, the
|
|
58
|
+
MySQL 8.0 hint syntax and available hints, when to use ANALYZE TABLE
|
|
59
|
+
vs hints (root cause vs workaround), common optimizer_switch settings,
|
|
60
|
+
and the risks of using hints in production.
|
|
61
|
+
|
|
62
|
+
assertions:
|
|
63
|
+
- type: llm_judge
|
|
64
|
+
criteria: "Index hints are correctly differentiated — USE INDEX suggests the optimizer consider only these indexes (but it may still choose a table scan), FORCE INDEX tells the optimizer to use the index unless impossible (treats table scan as very expensive), IGNORE INDEX excludes specific indexes. FORCE INDEX is stronger than USE INDEX"
|
|
65
|
+
weight: 0.35
|
|
66
|
+
description: "Index hints differentiated"
|
|
67
|
+
- type: llm_judge
|
|
68
|
+
criteria: "MySQL 8.0 hints are explained — /*+ ... */ syntax is preferred over traditional hints because they don't change SQL semantics, support more features (JOIN_ORDER, SET_VAR, MAX_EXECUTION_TIME), and can be added without modifying query structure. Shows examples of common hints and their use cases"
|
|
69
|
+
weight: 0.35
|
|
70
|
+
description: "MySQL 8.0 hints explained"
|
|
71
|
+
- type: llm_judge
|
|
72
|
+
criteria: "Risks and best practices are discussed — hints are workarounds, not fixes (ANALYZE TABLE and index design are better long-term solutions), hints can become counter-productive when data distribution changes, they should be documented and reviewed periodically, and per-query SET_VAR/MAX_EXECUTION_TIME are safer than global optimizer_switch changes"
|
|
73
|
+
weight: 0.30
|
|
74
|
+
description: "Risks and best practices"
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: subquery-optimization
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Optimize MySQL subqueries — understand semi-join, materialization, and how the optimizer transforms subqueries internally"
|
|
7
|
+
tags: [MySQL, subqueries, semi-join, materialization, optimizer, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your application has several queries using subqueries, and some are
|
|
13
|
+
fast while others are unexpectedly slow. You need to understand how
|
|
14
|
+
MySQL's optimizer handles subqueries differently from JOINs.
|
|
15
|
+
|
|
16
|
+
Query 1 — Fast (uses semi-join optimization):
|
|
17
|
+
SELECT * FROM customers
|
|
18
|
+
WHERE id IN (SELECT customer_id FROM orders WHERE total > 1000);
|
|
19
|
+
-- EXPLAIN: Shows semi-join optimization (FirstMatch or Materialization)
|
|
20
|
+
-- Time: 50ms
|
|
21
|
+
|
|
22
|
+
Query 2 — Slow (correlated subquery, no optimization):
|
|
23
|
+
SELECT * FROM customers c
|
|
24
|
+
WHERE (SELECT SUM(total) FROM orders WHERE customer_id = c.id) > 10000;
|
|
25
|
+
-- EXPLAIN: Shows DEPENDENT SUBQUERY executed 500K times
|
|
26
|
+
-- Time: 30 seconds
|
|
27
|
+
|
|
28
|
+
Query 3 — Tricky (NOT IN with NULLs):
|
|
29
|
+
SELECT * FROM customers
|
|
30
|
+
WHERE id NOT IN (SELECT customer_id FROM orders);
|
|
31
|
+
-- If orders.customer_id can be NULL, MySQL can't use anti-join
|
|
32
|
+
-- Falls back to full scan with subquery-per-row
|
|
33
|
+
-- Time: 45 seconds
|
|
34
|
+
|
|
35
|
+
Query 4 — Derived table (materialized once):
|
|
36
|
+
SELECT c.*, order_stats.total_spent
|
|
37
|
+
FROM customers c
|
|
38
|
+
JOIN (SELECT customer_id, SUM(total) AS total_spent
|
|
39
|
+
FROM orders GROUP BY customer_id) AS order_stats
|
|
40
|
+
ON order_stats.customer_id = c.id
|
|
41
|
+
WHERE order_stats.total_spent > 10000;
|
|
42
|
+
-- Derived table materialized once, then joined
|
|
43
|
+
-- Time: 2 seconds (better than Query 2)
|
|
44
|
+
|
|
45
|
+
MySQL 8.0 subquery optimizations:
|
|
46
|
+
- Semi-join strategies: FirstMatch, LooseScan, Materialization,
|
|
47
|
+
DuplicateWeedout, TablePullout
|
|
48
|
+
- Derived table merging: optimizer may merge derived tables into
|
|
49
|
+
outer query instead of materializing
|
|
50
|
+
- optimizer_switch settings control which strategies are enabled
|
|
51
|
+
|
|
52
|
+
Task: Explain MySQL's subquery optimization. Write: how semi-join
|
|
53
|
+
transforms IN subqueries (the 5 strategies), why correlated
|
|
54
|
+
subqueries are expensive, the NOT IN NULL trap and how to avoid it,
|
|
55
|
+
derived table materialization vs merging, and when to manually
|
|
56
|
+
rewrite subqueries as JOINs.
|
|
57
|
+
|
|
58
|
+
assertions:
|
|
59
|
+
- type: llm_judge
|
|
60
|
+
criteria: "Semi-join strategies are explained — FirstMatch (stop at first match per outer row), LooseScan (scan inner table index, skip duplicates), Materialization (materialize subquery result into temp table), DuplicateWeedout (use temp table to remove duplicates), TablePullout (convert subquery to join when inner table is unique). Explains that these apply to IN/EXISTS subqueries"
|
|
61
|
+
weight: 0.35
|
|
62
|
+
description: "Semi-join strategies explained"
|
|
63
|
+
- type: llm_judge
|
|
64
|
+
criteria: "Correlated subquery and NOT IN issues are addressed — correlated subqueries with aggregate functions (Query 2) can't be semi-joined and execute once per outer row (500K times). NOT IN with nullable columns prevents anti-join optimization because NULL IN (...NULL...) is UNKNOWN. Fix: use NOT EXISTS, or add WHERE customer_id IS NOT NULL in the subquery"
|
|
65
|
+
weight: 0.35
|
|
66
|
+
description: "Correlated and NOT IN issues"
|
|
67
|
+
- type: llm_judge
|
|
68
|
+
criteria: "Practical rewrite guidance is provided — shows how to rewrite Query 2 as a JOIN (like Query 4), when the optimizer's automatic transformations are sufficient vs when manual rewriting helps, and how to check what the optimizer did (EXPLAIN FORMAT=JSON shows 'attached_subqueries' vs 'nested_loop' for semi-join)"
|
|
69
|
+
weight: 0.30
|
|
70
|
+
description: "Practical rewrite guidance"
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: write-optimization
|
|
3
|
+
level: 2
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Optimize MySQL writes — use bulk INSERT, LOAD DATA INFILE, transaction batching, and InnoDB flush settings for high-throughput writes"
|
|
7
|
+
tags: [MySQL, InnoDB, write-optimization, bulk-insert, LOAD-DATA, intermediate]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your data pipeline needs to insert 10 million rows per hour into MySQL.
|
|
13
|
+
Currently it takes 4 hours — you need to make it fit within 1 hour.
|
|
14
|
+
|
|
15
|
+
Current approach (slow):
|
|
16
|
+
for each row in data:
|
|
17
|
+
cursor.execute("INSERT INTO events VALUES (%s, %s, %s, ...)", row)
|
|
18
|
+
connection.commit()
|
|
19
|
+
|
|
20
|
+
Time: 4 hours for 10M rows (700 inserts/second)
|
|
21
|
+
|
|
22
|
+
Settings: All defaults (innodb_flush_log_at_trx_commit=1, autocommit=1)
|
|
23
|
+
|
|
24
|
+
Table: events (20 columns, 3 secondary indexes)
|
|
25
|
+
- PRIMARY KEY (id) — auto_increment BIGINT
|
|
26
|
+
- INDEX idx_user (user_id)
|
|
27
|
+
- INDEX idx_type_date (event_type, created_at)
|
|
28
|
+
- INDEX idx_session (session_id)
|
|
29
|
+
|
|
30
|
+
Benchmarks you've run:
|
|
31
|
+
A. Single-row INSERT with autocommit: 700/sec (current)
|
|
32
|
+
B. Multi-row INSERT (1000 per statement): 15,000/sec
|
|
33
|
+
C. Multi-row INSERT + batch commit (10K per txn): 50,000/sec
|
|
34
|
+
D. LOAD DATA INFILE: 200,000/sec
|
|
35
|
+
E. LOAD DATA INFILE + disabled indexes: 500,000/sec
|
|
36
|
+
|
|
37
|
+
The DBA warns about trade-offs:
|
|
38
|
+
1. innodb_flush_log_at_trx_commit=2 speeds up 30% but risks 1 second
|
|
39
|
+
of data loss on OS crash
|
|
40
|
+
2. Disabling unique_checks and foreign_key_checks speeds up 20% but
|
|
41
|
+
risks data integrity if data is bad
|
|
42
|
+
3. Dropping secondary indexes before load and rebuilding after is
|
|
43
|
+
faster but table is unusable during rebuild
|
|
44
|
+
|
|
45
|
+
Task: Design the write optimization strategy for the data pipeline.
|
|
46
|
+
Write: why single-row inserts are slow (per-row commit overhead),
|
|
47
|
+
the multi-row INSERT technique and optimal batch size, LOAD DATA
|
|
48
|
+
INFILE usage and best practices, the InnoDB flush settings trade-off,
|
|
49
|
+
and the index management strategy during bulk loads.
|
|
50
|
+
|
|
51
|
+
assertions:
|
|
52
|
+
- type: llm_judge
|
|
53
|
+
criteria: "Root cause of slow writes is explained — single-row inserts with autocommit=1 flush the redo log to disk on every INSERT (fsync per row). With 10M rows, that's 10M fsyncs. Batching reduces fsyncs: 1000-row batches = 10K fsyncs, transaction batching (10K rows per commit) = 1K fsyncs. LOAD DATA INFILE uses internal bulk loading with minimal logging"
|
|
54
|
+
weight: 0.35
|
|
55
|
+
description: "Write bottleneck explained"
|
|
56
|
+
- type: llm_judge
|
|
57
|
+
criteria: "Optimization techniques are ranked correctly — LOAD DATA INFILE is fastest (200K/sec), followed by multi-row INSERT with batch commits (50K/sec), then multi-row INSERT with autocommit (15K/sec). Explains optimal batch size (1000-10000 rows per INSERT statement, 10K-100K rows per transaction), and how innodb_flush_log_at_trx_commit=2 provides a balanced speed/safety trade-off"
|
|
58
|
+
weight: 0.35
|
|
59
|
+
description: "Techniques ranked correctly"
|
|
60
|
+
- type: llm_judge
|
|
61
|
+
criteria: "Index management strategy is practical — for large bulk loads, consider: (1) disable secondary indexes (ALTER TABLE DISABLE KEYS for MyISAM, or drop/recreate for InnoDB), (2) load data, (3) rebuild indexes. For ongoing ingestion, keep indexes but use INSERT IGNORE or ON DUPLICATE KEY UPDATE. Quantifies the trade-off between index maintenance overhead and query availability"
|
|
62
|
+
weight: 0.30
|
|
63
|
+
description: "Index management strategy"
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: advanced-optimization-shift
|
|
3
|
+
level: 3
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Advanced optimization shift — handle a complex MySQL performance crisis combining replication failure, lock contention, and slow query regression"
|
|
7
|
+
tags: [MySQL, shift-simulation, crisis, replication, lock-contention, advanced]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
You're on-call when multiple MySQL alerts fire simultaneously during
|
|
13
|
+
a product launch event. The application is partially down and the
|
|
14
|
+
engineering VP is asking for status updates every 5 minutes.
|
|
15
|
+
|
|
16
|
+
Alert timeline:
|
|
17
|
+
|
|
18
|
+
14:00 — Traffic starts at 4x normal for product launch.
|
|
19
|
+
|
|
20
|
+
14:10 — Alert: Primary CPU 92%, query latency P99 jumps to 5 seconds.
|
|
21
|
+
Performance Schema shows a new query (from the launch feature):
|
|
22
|
+
SELECT p.*, r.*, u.name
|
|
23
|
+
FROM products p
|
|
24
|
+
JOIN reviews r ON r.product_id = p.id
|
|
25
|
+
JOIN users u ON u.id = r.user_id
|
|
26
|
+
WHERE p.id = ?
|
|
27
|
+
ORDER BY r.created_at DESC;
|
|
28
|
+
Missing index on reviews.product_id — full table scan on 50M reviews.
|
|
29
|
+
|
|
30
|
+
14:15 — Alert: Replication lag on Replica 1 at 120 seconds.
|
|
31
|
+
Analytics query running for 45 minutes holding open transaction,
|
|
32
|
+
preventing relay log application on the replica.
|
|
33
|
+
|
|
34
|
+
14:18 — Alert: "Lock wait timeout exceeded" errors at 100/minute.
|
|
35
|
+
The launch feature's "add to cart" UPDATE:
|
|
36
|
+
UPDATE inventory SET reserved = reserved + 1
|
|
37
|
+
WHERE product_id = ? AND warehouse_id = ?;
|
|
38
|
+
200 concurrent users trying to reserve the same hot product.
|
|
39
|
+
InnoDB row lock wait queue backing up.
|
|
40
|
+
|
|
41
|
+
14:22 — Alert: Connection pool exhausted. ProxySQL reports 0 available
|
|
42
|
+
backend connections. Queries queuing in ProxySQL.
|
|
43
|
+
Many connections stuck waiting for locks from 14:18 issue.
|
|
44
|
+
|
|
45
|
+
14:25 — Replica 2 also lagging 90 seconds. Read traffic can't be
|
|
46
|
+
served from replicas. All traffic hitting primary.
|
|
47
|
+
|
|
48
|
+
14:28 — Disk usage alert: 88%. Binlog accumulation from high write
|
|
49
|
+
volume + relay logs backing up on replicas.
|
|
50
|
+
|
|
51
|
+
Current state: Application returning 50% error rate.
|
|
52
|
+
Revenue impact: $20K/minute lost.
|
|
53
|
+
|
|
54
|
+
Task: Write the incident response. Include: the immediate triage
|
|
55
|
+
(first 5 minutes — what to fix first and why), the stabilization
|
|
56
|
+
steps (next 30 minutes), the root cause for each issue, the
|
|
57
|
+
post-incident action items, and the war-room communication template.
|
|
58
|
+
|
|
59
|
+
assertions:
|
|
60
|
+
- type: llm_judge
|
|
61
|
+
criteria: "Triage prioritization is correct — fixes the most impactful issue first: kill the blocking analytics query on the replica (unblocking replication), add the missing index on reviews.product_id (fixing the slow query driving CPU), and increase ProxySQL backend connection limits or kill stuck connections. Lock contention on hot product addressed with application-level serialization or optimistic locking"
|
|
62
|
+
weight: 0.35
|
|
63
|
+
description: "Correct triage prioritization"
|
|
64
|
+
- type: llm_judge
|
|
65
|
+
criteria: "All issues are resolved with specific actions — missing index (CREATE INDEX CONCURRENTLY or online DDL), replication lag (kill blocking query, enable parallel replication for future), lock contention (change to optimistic locking or queue-based reservation), connection exhaustion (increase pool, reduce per-query lock hold time), disk (purge old binlogs, extend disk)"
|
|
66
|
+
weight: 0.35
|
|
67
|
+
description: "All issues resolved"
|
|
68
|
+
- type: llm_judge
|
|
69
|
+
criteria: "Post-incident improvements prevent recurrence — query review in CI/CD (catch missing indexes before deploy), load testing before launch events, replica query timeout (prevent long-running analytics from blocking replication), hot-product inventory pattern (Redis cache or queue-based reservation), and ProxySQL connection limits tuned for peak traffic"
|
|
70
|
+
weight: 0.30
|
|
71
|
+
description: "Prevention measures"
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
meta:
|
|
2
|
+
id: connection-management
|
|
3
|
+
level: 3
|
|
4
|
+
course: mysql-query-optimization
|
|
5
|
+
type: output
|
|
6
|
+
description: "Optimize MySQL connections — deploy ProxySQL for connection pooling, read/write splitting, and query routing"
|
|
7
|
+
tags: [MySQL, ProxySQL, connection-pooling, read-write-split, routing, advanced]
|
|
8
|
+
|
|
9
|
+
state: {}
|
|
10
|
+
|
|
11
|
+
trigger: |
|
|
12
|
+
Your application is experiencing "Too many connections" errors during
|
|
13
|
+
peak hours. The MySQL server has max_connections=500 but 20
|
|
14
|
+
microservices are each opening 50 connections, totaling 1,000
|
|
15
|
+
potential connections. Most connections sit idle in Sleep state.
|
|
16
|
+
|
|
17
|
+
Current state:
|
|
18
|
+
- MySQL max_connections: 500
|
|
19
|
+
- Application connections needed: 1,000 (20 services × 50)
|
|
20
|
+
- Active queries at peak: only 80 concurrent
|
|
21
|
+
- Sleep connections: 420 (84% idle)
|
|
22
|
+
- Memory per connection: ~10MB (thread stack + buffers)
|
|
23
|
+
- Total connection memory: 500 × 10MB = 5GB wasted on idle connections
|
|
24
|
+
|
|
25
|
+
SHOW PROCESSLIST during peak:
|
|
26
|
+
- 80 connections in Query state (active)
|
|
27
|
+
- 420 connections in Sleep state (idle, wasting resources)
|
|
28
|
+
- Error: "Too many connections" — 500 rejected in last hour
|
|
29
|
+
|
|
30
|
+
Architecture problem:
|
|
31
|
+
- Each microservice maintains its own connection pool
|
|
32
|
+
- No connection sharing between services
|
|
33
|
+
- Read queries (70%) go to primary — replicas underutilized
|
|
34
|
+
- No query routing — all services connect directly to MySQL
|
|
35
|
+
|
|
36
|
+
ProxySQL deployment plan:
|
|
37
|
+
- Insert ProxySQL between applications and MySQL
|
|
38
|
+
- Multiplex: 1,000 frontend connections → 200 backend connections
|
|
39
|
+
- Read/write split: writes → primary, reads → replicas
|
|
40
|
+
- Query routing rules: route by query pattern, user, schema
|
|
41
|
+
- Connection pooling: reuse backend connections across services
|
|
42
|
+
|
|
43
|
+
Questions:
|
|
44
|
+
1. How does ProxySQL multiplex connections?
|
|
45
|
+
2. How to configure read/write splitting?
|
|
46
|
+
3. How to handle prepared statements through a proxy?
|
|
47
|
+
4. What about MySQL Router (official) vs ProxySQL?
|
|
48
|
+
5. How to monitor connection pool health?
|
|
49
|
+
|
|
50
|
+
Task: Design the connection management architecture. Write: the
|
|
51
|
+
ProxySQL deployment plan, the read/write splitting configuration,
|
|
52
|
+
the query routing rules, the connection pool sizing (frontend and
|
|
53
|
+
backend), and the comparison with MySQL Router.
|
|
54
|
+
|
|
55
|
+
assertions:
|
|
56
|
+
- type: llm_judge
|
|
57
|
+
criteria: "ProxySQL multiplexing is explained — frontend connections from applications are mapped to a smaller pool of backend connections to MySQL. ProxySQL maintains the session state and switches backend connections as needed. This reduces MySQL from 500+ connections to ~200 backend connections, saving memory and reducing context switching"
|
|
58
|
+
weight: 0.35
|
|
59
|
+
description: "ProxySQL multiplexing explained"
|
|
60
|
+
- type: llm_judge
|
|
61
|
+
criteria: "Read/write split is configured — ProxySQL query rules route SELECT to read replicas (hostgroup for readers) and INSERT/UPDATE/DELETE to primary (hostgroup for writers). Handles edge cases: SELECT ... FOR UPDATE goes to primary, queries within transactions go to primary, and freshly-written data reads may need primary (session stickiness or replication-lag-aware routing)"
|
|
62
|
+
weight: 0.35
|
|
63
|
+
description: "Read/write split configured"
|
|
64
|
+
- type: llm_judge
|
|
65
|
+
criteria: "Pool sizing and comparison are provided — backend pool size calculation (based on active query concurrency, not application pool size), ProxySQL vs MySQL Router comparison (ProxySQL: more features, query routing, caching; MySQL Router: simpler, better InnoDB Cluster integration, no connection pooling), and monitoring queries for pool health (ProxySQL stats tables)"
|
|
66
|
+
weight: 0.30
|
|
67
|
+
description: "Pool sizing and comparison"
|