<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: TiDB Community</title>
    <description>The latest articles on DEV Community by TiDB Community (@tidbcommunity).</description>
    <link>https://dev.to/tidbcommunity</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F1045612%2Fd8180cc8-8419-41b4-93d7-a42d20cf6e53.jpg</url>
      <title>DEV Community: TiDB Community</title>
      <link>https://dev.to/tidbcommunity</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/tidbcommunity"/>
    <language>en</language>
    <item>
      <title>How to Build an AI Agent that Builds Full-Stack Apps</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Tue, 06 Jan 2026 07:33:22 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/how-to-build-an-ai-agent-that-builds-full-stack-apps-5c1d</link>
      <guid>https://dev.to/tidbcommunity/how-to-build-an-ai-agent-that-builds-full-stack-apps-5c1d</guid>
      <description>&lt;p&gt;By Hao Huo, Director of AI Innovation at PingCAP&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;An open-source starter kit for building a “Lovable.dev”-style AI agent&lt;/strong&gt;&lt;br&gt;
More and more, we’re seeing AI agents build entire applications from a single prompt. Platforms like Lovable.dev and Manus are pioneering this space. Many of them are using &lt;a href="https://www.pingcap.com/tidb/cloud/" rel="noopener noreferrer"&gt;TiDB Cloud&lt;/a&gt; to power their data layer. So, we decided to build one too, as a &lt;a href="https://github.com/pingcap/full-stack-app-builder-ai-agent" rel="noopener noreferrer"&gt;public, open-source dev kit available on GitHub&lt;/a&gt; that you can use as a starting point to build your own AI-driven development platform.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Video walkthrough:&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
Watch the YouTube walkthrough of the &lt;a href="https://www.youtube.com/watch?v=kyWZzj57wwY" rel="noopener noreferrer"&gt;Full Stack App Builder AI Agent&lt;/a&gt;&lt;/p&gt;

&lt;h1&gt;
  
  
  What can this agent do?
&lt;/h1&gt;

&lt;p&gt;This agent is an AI chat app and codegen platform that ties together everything you need to prompt (i.e., vibe code) complete web applications end-to-end. It can:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Generate complete web apps from a prompt&lt;/strong&gt;: You describe what you want to build, and the agent scaffolds it automatically with the correct files, dependencies, and setup.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Provision a TiDB Cloud database automatically&lt;/strong&gt;: Every generated project gets its own TiDB Cloud cluster including database, schema, and a connection string fully preconfigured. Each instruction within the same project is versioned as a separate TiDB Cloud branch, ensuring isolated and trackable iterations.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Track project versions&lt;/strong&gt;: The agent stores every generated app and its database credentials (user, password, branch info), so you can revisit previous versions or roll back safely. Most importantly, your database always stays in sync with the selected project version.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Run and preview apps instantly&lt;/strong&gt;: Test each generated project directly from the UI or open the preview URL immediately.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Keep context between generations&lt;/strong&gt;: The agent remembers your previous instructions and builds on them, enabling iterative refinement instead of isolated one-shot generations.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Scale down when idle&lt;/strong&gt;: Each generated app uses TiDB Cloud, which automatically scales to zero when unused.&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  Architecture Overview
&lt;/h1&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fni8x8pgtokn4z6role8m.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fni8x8pgtokn4z6role8m.png" alt=" " width="800" height="446"&gt;&lt;/a&gt;&lt;br&gt;
This architecture transforms natural-language prompts into production-ready web apps by combining:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Codex (gpt-5.1-codex) or Claude Code&lt;/strong&gt; for reasoning and codegen&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;TiDB Cloud&lt;/strong&gt; for cluster-level, branchable data environments&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Kysely&lt;/strong&gt; for type-safe SQL&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Vercel&lt;/strong&gt; for execution and deployment&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GitHub&lt;/strong&gt; for version control&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;At the center of this stack is &lt;a href="https://www.pingcap.com/tidb/cloud/" rel="noopener noreferrer"&gt;TiDB Cloud&lt;/a&gt;, acting as the central nervous system for the entire operation. It serves as both the control-plane database for the platform itself and provides the branchable, on-demand data environments for every app the agent generates.&lt;/p&gt;

&lt;h1&gt;
  
  
  How It Works: The Agent’s End-to-End Flow
&lt;/h1&gt;

&lt;p&gt;This entire process can be broken down into two key parts: the tools the agent needs to do its job, and the step-by-step workflow it follows to build an application.&lt;/p&gt;

&lt;h2&gt;
  
  
  Part 1: The Agent’s Toolkit
&lt;/h2&gt;

&lt;p&gt;Before the agent can generate or deploy anything, it must authenticate itself against all the external systems it orchestrates. These credentials form the &lt;strong&gt;control plane&lt;/strong&gt; — the unified interface through which the agent provisions environments, generates code, manages data, and ships applications.&lt;/p&gt;

&lt;p&gt;The agent requires:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;GitHub tokens&lt;/strong&gt;: Creates repositories, pushes generated code, and manages branches. GitHub becomes the source of truth for code checkpoints.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Vercel tokens&lt;/strong&gt;: Creates ephemeral sandboxes, uploads build artifacts, and deploys web apps. Vercel acts as the execution layer.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Codex or Claude Code API keys&lt;/strong&gt;: Enable reasoning and planning. The model acts as the brain of the system.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://docs.pingcap.com/tidbcloud/api-overview/?_gl=1*3xocmp*_gcl_aw*R0NMLjE3NjYxMTAzMjUuQ2owS0NRaUE2WTdLQmhDa0FSSXNBT3hocXRPM1N4TmlHMnJrdUIyS0dBcHVZejdvSVdwLUUydURMbzF4WnNjUjlma0hhWG9xVUEwX1F5RWFBcmhKRUFMd193Y0I.*_gcl_au*MjAyNTA4NDM5Mi4xNzYwOTQ0MzQ5*_ga*MTQ1MTc3NjUwOS4xNzQ1MjA3OTY3*_ga_3JVXJ41175*czE3Njc2ODMwMjEkbzQ3MyRnMSR0MTc2NzY4NDA3OSRqMzckbDAkaDIyMTUxODExNA..*_ga_ZEL0RNV6R2*czE3Njc2ODMwMzYkbzM4MSRnMSR0MTc2NzY4NDA1NyRqNjAkbDAkaDA.*_ga_CPG2VW1Y41*czE3Njc2ODMwMjQkbzQ5OSRnMSR0MTc2NzY4NDA3MyRqNDMkbDAkaDA." rel="noopener noreferrer"&gt;TiDB Cloud API keys&lt;/a&gt;&lt;/strong&gt;: Allow the agent to programmatically create, manage, and branch TiDB Cloud clusters. This provides isolated data environments and the backbone for safe iteration.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Together, these credentials let the agent fully automate the lifecycle: &lt;strong&gt;plan → provision → generate → migrate → deploy → iterate.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Part 2: The App-Building Workflow in Action
&lt;/h2&gt;

&lt;p&gt;Now, let’s see how the agent uses its toolkit in a real-world scenario. From the initial prompt to the final deployment, the agent follows a precise, automated sequence to turn an idea into a running application.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ffbl2zyebkrmf1skum5uo.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ffbl2zyebkrmf1skum5uo.png" alt=" " width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Prompt
&lt;/h3&gt;

&lt;p&gt;It begins when the user creates a request, such as: “Build a Todo List app.”&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 2: Plan
&lt;/h3&gt;

&lt;p&gt;Immediately upon receiving the prompt, the model analyzes the requirements and generates a comprehensive execution plan.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 3: Provision
&lt;/h3&gt;

&lt;p&gt;Once the plan is set, the agent provisions the necessary infrastructure. It creates a new TiDB Cloud cluster, a Vercel Sandbox, and a GitHub repo while simultaneously configuring the required environment variables.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 4: Generate Code
&lt;/h3&gt;

&lt;p&gt;With the environment ready, Codex or Claude Code proceeds to generate the application code. This includes creating pages, components, and API routes, alongside the Kysely schema and migration files.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 5: Database Migration
&lt;/h3&gt;

&lt;p&gt;Next, to ensure data consistency, Kysely applies the typed migrations directly to the TiDB Cloud cluster.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 6: Deploy
&lt;/h3&gt;

&lt;p&gt;Following the successful migration, the agent commits the code to GitHub and automatically triggers a Vercel deployment to bring the app live.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 7: Iterate with Follow-Up Instruction
&lt;/h3&gt;

&lt;p&gt;Finally, the process becomes cyclical. For example, when you provide a follow-up instruction like “Add a username field,” the agent creates a new &lt;a href="https://docs.pingcap.com/tidbcloud/branch-manage/?plan=starter&amp;amp;_gl=1*11ztd5r*_gcl_aw*R0NMLjE3NjYxMTAzMjUuQ2owS0NRaUE2WTdLQmhDa0FSSXNBT3hocXRPM1N4TmlHMnJrdUIyS0dBcHVZejdvSVdwLUUydURMbzF4WnNjUjlma0hhWG9xVUEwX1F5RWFBcmhKRUFMd193Y0I.*_gcl_au*MjAyNTA4NDM5Mi4xNzYwOTQ0MzQ5*_ga*MTQ1MTc3NjUwOS4xNzQ1MjA3OTY3*_ga_3JVXJ41175*czE3Njc2ODMwMjEkbzQ3MyRnMSR0MTc2NzY4NDI1MSRqNjAkbDAkaDIyMTUxODExNA..*_ga_ZEL0RNV6R2*czE3Njc2ODMwMzYkbzM4MSRnMSR0MTc2NzY4NDA1NyRqNjAkbDAkaDA.*_ga_CPG2VW1Y41*czE3Njc2ODMwMjQkbzQ5OSRnMSR0MTc2NzY4NDA3MyRqNDMkbDAkaDA." rel="noopener noreferrer"&gt;TiDB Cloud branch&lt;/a&gt;. It then updates the schema, regenerates and applies migrations, updates the UI/API code, and redeploys. Because of this branching capability, everything stays isolated and fully reversible.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fnp1d5lz7z5tue67pyb3v.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fnp1d5lz7z5tue67pyb3v.png" alt=" " width="800" height="502"&gt;&lt;/a&gt;&lt;br&gt;
This is critical for iterative development. Because Kysely generates both an up and a down migration for every schema change, the agent can not only apply new structures but also safely reverse them. This ensures that every iteration is clean and fully reversible without manual database intervention.&lt;/p&gt;

&lt;h1&gt;
  
  
  Magic Features: Where It All Clicks
&lt;/h1&gt;

&lt;p&gt;While the workflow seems straightforward, a few key techniques are what make this system robust, safe, and efficient. Let’s look at the ‘magic’ that makes it all click.&lt;/p&gt;

&lt;h2&gt;
  
  
  Technique 1: Syncing Code and Data with Git + TiDB Branches
&lt;/h2&gt;

&lt;p&gt;Every instruction becomes a lightweight checkpoint for both code and data. Each version stores the Git repo name and branch name alongside the TiDB Cloud cluster ID and branch name, ensuring perfect code–data synchronization.&lt;/p&gt;

&lt;h3&gt;
  
  
  Example: Creating a TiDB Cloud Branch Programmatically
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import fetch from "node-fetch";

const SERVERLESS_API_BASE = "https://serverless.tidbapi.com/v1beta1";

async function createBranch(clusterId, newBranchName, publicKey, privateKey) {
  const url = `${SERVERLESS_API_BASE}/clusters/${clusterId}/branches`;
  const body = JSON.stringify({ displayName: newBranchName });

  const response = await fetch(url, {
    method: "POST",
    headers: {
      "Content-Type": "application/json",
      Authorization:
        "Basic " + Buffer.from(`${publicKey}:${privateKey}`).toString("base64"),
    },
    body,
  });

  if (!response.ok) {
    const text = await response.text();
    throw new Error(`Failed to create branch: ${response.status} ${text}`);
  }

  const data = await response.json();
  return data.branchId;
}

createBranch(
  "1234567890",
  "new-feature-branch",
  process.env.TIDB_CLOUD_PUBLIC_KEY,
  process.env.TIDB_CLOUD_PRIVATE_KEY
)
  .then((branchId) =&amp;gt; console.log("Branch created:", branchId))
  .catch(console.error);
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Technique 2: Safe, Type-Safe Schema Migrations with Kysely
&lt;/h2&gt;

&lt;p&gt;When the agent needs to change the schema, it generates a Kysely migration file. This makes schema evolution safe, reversible, and fully automated.&lt;/p&gt;

&lt;h3&gt;
  
  
  Example: A Kysely Migration File
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import type { Kysely } from "kysely";

export async function up(db: Kysely&amp;lt;any&amp;gt;) {
  await db.schema
    .alterTable("todo_list")
    .addColumn("username", "varchar(255)", (col) =&amp;gt; col.notNull().defaultTo(""))
    .execute();
}

export async function down(db: Kysely&amp;lt;any&amp;gt;) {
  await db.schema
    .alterTable("todo_list")
    .dropColumn("username")
    .execute();
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is critical for iterative development. Because Kysely generates both an “up” and a “down” migration for every schema change, the agent can not only apply new structures but also safely reverse them. This ensures that every iteration is clean and fully reversible without manual database intervention.&lt;/p&gt;

&lt;h2&gt;
  
  
  Technique 3: On-Demand Dev Environments with Scale-to-Zero
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;TiDB Cloud&lt;/strong&gt; automatically scales down to &lt;strong&gt;$0 when idle&lt;/strong&gt;. This enables:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Ephemeral, AI-generated apps.&lt;/li&gt;
&lt;li&gt;On-demand development environments.&lt;/li&gt;
&lt;li&gt;Branch-per-instruction workflows.&lt;/li&gt;
&lt;li&gt;Burst-heavy workloads from agents.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The agent can create many isolated environments without persistent costs.&lt;/p&gt;

&lt;h1&gt;
  
  
  Wrapping Up
&lt;/h1&gt;

&lt;p&gt;This starter kit is more than just code; it’s a blueprint for building dynamic, AI-driven applications. The key takeaway is treating your database not as a static box, but as a programmable, API-driven resource. We’ve open-sourced the entire project for you to explore. We encourage you to fork the repo, use the code, and see what you can create.&lt;/p&gt;

&lt;p&gt;Ready to Build Your Own? Try &lt;a href="https://tidbcloud.com/free-trial/?__hstc=86493575.c6e7d21b887b2e3b026440935507c5f3.1745207968826.1767668045538.1767683027502.383&amp;amp;__hssc=86493575.14.1767683027502&amp;amp;__hsfp=4235207616&amp;amp;_gl=1*fmep1r*_gcl_aw*R0NMLjE3NjYxMTAzMjUuQ2owS0NRaUE2WTdLQmhDa0FSSXNBT3hocXRPM1N4TmlHMnJrdUIyS0dBcHVZejdvSVdwLUUydURMbzF4WnNjUjlma0hhWG9xVUEwX1F5RWFBcmhKRUFMd193Y0I.*_gcl_au*MjAyNTA4NDM5Mi4xNzYwOTQ0MzQ5*_ga*MTQ1MTc3NjUwOS4xNzQ1MjA3OTY3*_ga_3JVXJ41175*czE3Njc2ODMwMjEkbzQ3MyRnMSR0MTc2NzY4NDM4MCRqNjAkbDAkaDIyMTUxODExNA..*_ga_ZEL0RNV6R2*czE3Njc2ODMwMzYkbzM4MSRnMSR0MTc2NzY4NDA1NyRqNjAkbDAkaDA.*_ga_9FRXHHPYVY*czE3Njc2ODMwMjQkbzQzMSRnMSR0MTc2NzY4NDA3MyRqNDMkbDAkaDA." rel="noopener noreferrer"&gt;TiDB Cloud&lt;/a&gt; for free to test out the database branching and scale-to-zero features used in this project. No credit card is required to get started.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>database</category>
      <category>webdev</category>
      <category>fullstack</category>
    </item>
    <item>
      <title>TiKV Component GC (Physical Space Reclamation) Principles and Common Issues</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Fri, 04 Jul 2025 04:11:55 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/tikv-component-gc-physical-space-reclamation-principles-and-common-issues-33a1</link>
      <guid>https://dev.to/tidbcommunity/tikv-component-gc-physical-space-reclamation-principles-and-common-issues-33a1</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;This article was written by Shirly Wu, Support Escalation Engineer at PingCAP.&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;In TiDB, the GC worker uploads the GC safepoint to the PD server, and all TiKV instances regularly fetch the GC safepoint from PD. If there is any change, the TiKV instances will use the latest GC safepoint to start the local GC process. In this article, we will focus on the principles of TiKV-side GC and discuss some common issues.&lt;/p&gt;

&lt;h1&gt;
  
  
  GC Key in TiKV
&lt;/h1&gt;

&lt;p&gt;During GC, TiDB clears all locks before the GC safepoint across the entire cluster using the resolve locks mechanism. This means that once the data reaches TiKV, all transaction statuses before the GC safepoint are already resolved, and there are no remaining locks. The transaction statuses can be retrieved from the primary key of the distributed transaction. At this point, we can confidently and safely delete old version data.&lt;/p&gt;

&lt;p&gt;So, how exactly does the deletion process work?&lt;/p&gt;

&lt;p&gt;Let’s look at the following example:&lt;/p&gt;

&lt;p&gt;The current key has four versions, written in the following sequence:&lt;/p&gt;

&lt;p&gt;1:00 — New write or update, data stored in the default CF&lt;br&gt;
2:00 — Update, data stored in the default CF&lt;br&gt;
3:00 — Delete&lt;br&gt;
4:00 — New write, data stored in the default CF&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh2qxx2mm1iggf7m8ra6k.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh2qxx2mm1iggf7m8ra6k.png" alt="Image description" width="800" height="356"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If the GC safepoint is &lt;strong&gt;2:30&lt;/strong&gt;, which ensures snapshot consistency up to 2:30, we will retain the version read at 2:30: &lt;strong&gt;key_02:00 =&amp;gt; (PUT, 01:30)&lt;/strong&gt;. All previous versions before 2:30 will be deleted, including &lt;strong&gt;key_01:00&lt;/strong&gt;. The write-cf and default cf corresponding to this transaction will both be deleted.&lt;/p&gt;

&lt;p&gt;What if the GC safepoint is 3:30?&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F8mzvzezifucorwwi9247.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F8mzvzezifucorwwi9247.png" alt="Image description" width="800" height="384"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Similarly, the version read at 3:30,&lt;strong&gt;key_03:00 =&amp;gt; DELETE&lt;/strong&gt;, will be retained. All versions before 3:00 will be deleted.&lt;/p&gt;

&lt;p&gt;We see that the snapshot at 3:30 indicates that the transaction for key_03:00 is deleting this key.So, is it necessary to retain the MVCC version at 03:00? Not necessary. Therefore, under normal circumstances, if the GC safepoint is 3:30, the data that needs to be garbage collected for this key will be:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fnblrknbdz9u1a007ppkp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fnblrknbdz9u1a007ppkp.png" alt="Image description" width="800" height="382"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is how the GC process works for a specific key — TiKV’s GC process requires scanning all the keys on the current TiKV instance and deleting the old versions that meet the GC criteria.&lt;/p&gt;
&lt;h2&gt;
  
  
  Related Monitoring
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;gc_keys&lt;/strong&gt; can create read pressure on the system since it needs to scan all versions of the current key to determine whether old versions should be deleted. Related monitoring can be found in &lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; GC scan write/default details&lt;/strong&gt;, which records the pressure on RocksDB’s write/default CF during GC worker execution:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpi08qbar3kcn6l4ixnov.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpi08qbar3kcn6l4ixnov.png" alt="Image description" width="800" height="119"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The duration of gc_keys can be seen in &lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; GC tasks duration&lt;/strong&gt;. If there is high latency in this area, it indicates significant GC pressure or that the read/write pressure on the system is affecting the GC process.&lt;/p&gt;
&lt;h1&gt;
  
  
  GC in TiKV
&lt;/h1&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Feaengscirfwze2lawnle.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Feaengscirfwze2lawnle.png" alt="Image description" width="800" height="405"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h1&gt;
  
  
  GC Worker
&lt;/h1&gt;

&lt;p&gt;Each TiKV instance has a GC worker thread responsible for handling specific GC tasks. The GC worker in TiKV mainly handles the following two types of requests:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;GC_keys&lt;/strong&gt;: This involves scanning and deleting old versions of a specific key that meet the GC criteria. The detailed process was described in the first chapter.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GC(range)&lt;/strong&gt;: This involves using GC_keys on a specified range of keys, performing GC on each key individually within the range.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;unsafe-destroy-range&lt;/strong&gt;: This is the direct physical cleanup of a continuous range of data, corresponding to operations like truncate/drop table/partition mentioned in the previous article.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Currently, the GC worker has two key configurations, which cannot be adjusted:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Thread count&lt;/strong&gt;: Currently, the GC worker only has one thread. This is hardcoded in the code here, and no external configuration is provided.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GC_MAX_PENDING_TASKS&lt;/strong&gt;: This is the maximum number of tasks the GC worker queue can handle, set to 4096.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
  
  
  Related Monitoring
&lt;/h2&gt;

&lt;p&gt;GC tasks QPS/duration can be monitored in tikv-details -&amp;gt; GC -&amp;gt; GC tasks/GC tasks duration. If the GC tasks duration is high, we need to check whether the GC worker’s CPU resources are sufficient, in combination with the QPS.&lt;/p&gt;

&lt;p&gt;GC worker CPU usage: &lt;strong&gt;tikv-details -&amp;gt; thread CPU -&amp;gt; GC worker&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbtvz0x86cm8xd1lx5ypa.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbtvz0x86cm8xd1lx5ypa.png" alt="Image description" width="800" height="202"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h1&gt;
  
  
  GC manager
&lt;/h1&gt;

&lt;p&gt;The GC manager is the thread responsible for driving the GC work in TiKV. The main steps are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Syncing the GC safepoint to local memory&lt;/li&gt;
&lt;li&gt;Globally guiding the execution of specific GC tasks&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;1. Syncing GC Safepoint to Local&lt;/strong&gt;&lt;br&gt;
The GC manager regularly requests the latest GC safepoint from PD every ten seconds and refreshes the safepoint in memory. The related monitoring can be found in &lt;strong&gt;tikv-details -&amp;gt; GC&lt;/strong&gt;:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ftuornk2im91o3muj97wp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ftuornk2im91o3muj97wp.png" alt="Image description" width="791" height="335"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Common Issues&lt;/strong&gt;&lt;br&gt;
When monitoring shows that the TiKV auto GC safepoint is stuck for a long time and not advancing, it indicates that the GC state on the TiDB side may have a problem. At this point, you need to follow the troubleshooting steps in the previous article to investigate why GC on the TiDB side is stuck.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Implementing GC Jobs&lt;/strong&gt;&lt;br&gt;
If the GC manager detects that the GC safepoint has advanced, it begins implementing the specific GC tasks based on the current system configuration. This part is mainly divided into two methods based on the &lt;strong&gt;gc.enable-compaction-filter&lt;/strong&gt; parameter:&lt;/p&gt;

&lt;p&gt;a. Traditional GC, where GC(range) is called for each region.&lt;/p&gt;

&lt;p&gt;b. GC via compaction filter (default method after 5.0): Instead of performing a real GC, this method waits until RocksDB performs compaction, at which point old versions are reclaimed using the compaction filter.&lt;/p&gt;
&lt;h1&gt;
  
  
  TiKV GC Implementation Methods
&lt;/h1&gt;

&lt;p&gt;Next, we will explain the principles and common troubleshooting steps for these two GC methods.&lt;/p&gt;
&lt;h2&gt;
  
  
  GC by Region (Traditional GC)
&lt;/h2&gt;

&lt;p&gt;In traditional GC, when &lt;strong&gt;gc.enable-compaction-filter&lt;/strong&gt; is set to false, the GC manager performs GC on each TiKV region one by one. This process is referred to as “GC a round.”&lt;/p&gt;
&lt;h3&gt;
  
  
  GC a Round
&lt;/h3&gt;

&lt;p&gt;In traditional GC, a round of GC is completed when GC has been executed on all regions, and we mark the progress as 100%. If GC progress never reaches 100%, it indicates that GC pressure is high, and the physical space reclamation process is being affected. GC progress can be monitored in &lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; tikv-auto-gc-progress&lt;/strong&gt;. We can also observe the time taken for each round of GC in TiKV.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F32szgo5zfhbqqmttv9y7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F32szgo5zfhbqqmttv9y7.png" alt="Image description" width="800" height="375"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;After introducing the concept of a ‘GC round,’ let’s now look at how TiKV defines a round during execution.&lt;/p&gt;

&lt;p&gt;In simple terms, the GC manager starts GC work from the first region, continuing until the last region’s GC work is completed. However, if there is too much GC work, the GC safepoint may advance before the GC reaches the last region. In this case, do we continue using the old safepoint or the new one?&lt;/p&gt;

&lt;p&gt;The answer is to use the latest GC safepoint in real time for each region that follows. This is a simple optimization of traditional GC.&lt;/p&gt;

&lt;p&gt;Here’s an &lt;strong&gt;example&lt;/strong&gt; of how TiKV processes an updated GC safepoint during GC execution&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qenkuqyrupilxxohoqq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qenkuqyrupilxxohoqq.png" alt="Image description" width="800" height="387"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;When GC starts, gc-safepoint is 10, and we use safepoint=10 for GC regions 1 and 2.&lt;/li&gt;
&lt;li&gt;After finishing GC in region 2, the GC safepoint advances to 20. From this point on, we use 20 to continue GC in the remaining regions.&lt;/li&gt;
&lt;li&gt;Once all regions have been GC’d with gc safepoint=20, we start again from the first region, now using gc safepoint=20 for GC.&lt;/li&gt;
&lt;/ol&gt;
&lt;h3&gt;
  
  
  Common Issues
&lt;/h3&gt;

&lt;p&gt;In traditional GC, since all old versions must be scanned before being deleted, and then the delete operation is written to RocksDB’s MVCC, the system is heavily impacted. This is manifested in the following ways:&lt;/p&gt;

&lt;p&gt;1.Impact on GC Progress:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The GC worker becomes a bottleneck. Since all reclamation tasks need to be handled by the GC worker, which only has one thread, its CPU usage will be fully occupied. You can monitor this using: tikv-details -&amp;gt; thread CPU -&amp;gt; GC worker&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;2.Impact on Business Read/Write:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Raftstore read/write pressure increases: The GC worker needs to scan all data versions and then delete the matching ones during GC_keys tasks.&lt;/li&gt;
&lt;li&gt;The increased write load on RocksDB in the short term causes rapid accumulation of L0 files, triggering RocksDB compaction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;3.Physical Space Usage Increases:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Since a DELETE operation in RocksDB ultimately results in writing a new version of the current key, physical space usage might actually increase.&lt;/li&gt;
&lt;li&gt;Only after RocksDB compaction completes will the physical space be reclaimed, and this compaction requires temporary space.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In such cases where business cannot tolerate these impacts, the workaround is to enable the gc.enable-compaction-filter parameter.&lt;/p&gt;
&lt;h1&gt;
  
  
  GC with Compaction Filter
&lt;/h1&gt;

&lt;p&gt;As mentioned earlier, in traditional GC, we scan TiKV’s MVCC entries one by one and use the safepoint to determine which data can be deleted, sending a DELETE key operation to Raftstore (RocksDB). Since RocksDB uses an LSM tree architecture and its internal MVCC mechanism, old versions of data are not immediately deleted when new data is written, even during a DELETE operation. They are retained alongside the new data.&lt;/p&gt;
&lt;h2&gt;
  
  
  Why Compaction in RocksDB?
&lt;/h2&gt;

&lt;p&gt;Let’s explore the RocksDB architecture to understand the compaction mechanism.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flw01jagfu1oknw8iaknu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flw01jagfu1oknw8iaknu.png" alt="Image description" width="800" height="412"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;RocksDB uses an LSM tree structure to improve write performance.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;RocksDB Write Flow&lt;/strong&gt;&lt;br&gt;
When RocksDB receives a write operation (PUT(key =&amp;gt; value)), the complete process is as follows:&lt;/p&gt;

&lt;p&gt;1.When a new key is written, it is first written to the WAL and memtable, and then a success response is returned.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;RocksDB appends the data directly to the WAL file, persisting it locally.&lt;/li&gt;
&lt;li&gt;The data is written on an active memtable, which is fast because it operates in memory, and the data in the memtable is ordered.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;2.As more data is written, the memtable gradually fills up. When it becomes full, the active memtable is marked as immutable, and a new active memtable is created to store new writes.&lt;/p&gt;

&lt;p&gt;3.The data from the immutable memtable is flushed to a local file, which we call an SST file.&lt;/p&gt;

&lt;p&gt;4.Over time, more SST files are created. Note that SST files directly converted from memtables contain ordered data, but the data ranges are global [~, ~]. These SST files are placed in Level 0.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;RocksDB Read Flow&lt;/strong&gt;&lt;br&gt;
When a read request is received, the lookup follows this sequence:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Search in the memtable. If the key is found, return the value.&lt;/li&gt;
&lt;li&gt;Search in the block-cache (the data in the block-cache comes from SST files, which we will refer to as SST here). Search for the corresponding key in the SST files. Since the SST files in Level 0 are the most recent, data will be searched first in these files. Additionally, the SST files in Level 0 are directly converted from memtables, and their data ranges are global. In extreme cases, it may be necessary to search through all such SST files one by one.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Compaction for Improved Read Performance&lt;/strong&gt;&lt;br&gt;
From the above read flow, we can see that if we only have SST data in Level 0, as more and more files accumulate in Level 0, RocksDB’s read performance will degrade. To improve read performance, RocksDB performs merge sorting on the SST files in Level 0, a process known as compaction. The main tasks of RocksDB compaction are:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Merging multiple SST files into one.&lt;/li&gt;
&lt;li&gt;Keeping only the latest MVCC version from RocksDB’s perspective (GC).&lt;/li&gt;
&lt;li&gt;Compacting lower levels into Level 1~Level 6.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;From the above process, we can see that RocksDB’s compaction work is similar to what we do during GC. So, is it possible to combine TiKV’s GC process with RocksDB’s compaction? Of course, it is.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Combining TiKV GC with Compaction&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;RocksDB provides an interface for compaction filters, which allows us to define rules for filtering keys during the compaction process. Based on the rules we provide in the compaction filter, we can decide whether to discard the key during this phase.&lt;/p&gt;
&lt;h2&gt;
  
  
  Implementation Principle
&lt;/h2&gt;

&lt;p&gt;Let’s take TiKV‘s GC as an example to understand how data is reclaimed during the compaction process when the compaction filter is enabled.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TiKV‘s Compaction Filter Only Affects Write-CF&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;First, TiKV’s compaction filter only affects write-cf. Why? Because write-cf stores MVCC data, while data-cf stores the actual data. As for lock-cf, as we’ve discussed on the TiDB side, after the GC safepoint is updated to PD, there are no more locks in lock-cf before the safepoint.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Directly Filtering Unnecessary MVCC Keys in Compaction&lt;/strong&gt;&lt;br&gt;
Next, let’s look at how an MVCC key a behaves during a compaction process:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Foj2v2x9poh6z7s7occde.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Foj2v2x9poh6z7s7occde.png" alt="Image description" width="800" height="315"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The TiKV MVCC key &lt;strong&gt;a&lt;/strong&gt; in write-cf has a commit_ts suffix. Initially, let’s assume we are compacting two SST files on the left, which are in Level 2 and Level 3. After compaction, these files will be stored in Level 3.&lt;/li&gt;
&lt;li&gt;The SST file in Level 2 contains &lt;strong&gt;a_90&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;The SST file in Level 3 contains &lt;strong&gt;a_85, a_82,&lt;/strong&gt; and &lt;strong&gt;a_80&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;The current GC safepoint is 89. Based on the GC key processing rules from Chapter 1, we know we need to retain the older version a_85, meaning all versions before a_85 can be deleted.&lt;/li&gt;
&lt;li&gt;From the right, we can see that the new SST file only contains a_85 and a_90. The other versions, along with the corresponding data in default-cf, are deleted during compaction.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;In summary, compared to traditional GC, using a compaction filter for GC has the following advantages:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;It eliminates the need to read from RocksDB.&lt;/li&gt;
&lt;li&gt;The deletion (write) process for RocksDB is simplified.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Although compaction introduces some pressure, it completely removes the impact of GC on RocksDB’s read/write operations, resulting in a significant performance optimization.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Compaction on Non-L6 SST Files with Write_type::DEL&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzdh3rx64bkc1o20u2ug3.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzdh3rx64bkc1o20u2ug3.png" alt="Image description" width="800" height="356"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When compaction occurs, if we encounter the latest version of data as &lt;strong&gt;write_type::DEL&lt;/strong&gt;, should we delete it directly? &lt;strong&gt;The answer is no.&lt;/strong&gt; Unlike the gc_keys interface, which scans all versions of the key, compaction only scans the versions within the SST files involved in the current compaction. Therefore, if we delete &lt;strong&gt;write_type::DEL&lt;/strong&gt; at the current level during compaction, there might still be older versions of the key at lower levels. For example, if we delete &lt;strong&gt;a_85 =&amp;gt; write_type::DEL&lt;/strong&gt; during this compaction, when users read the snapshot at &lt;strong&gt;gc_safepoint=89&lt;/strong&gt;, &lt;strong&gt;a_85&lt;/strong&gt; would be missing, and the latest matching version would be &lt;strong&gt;a_78&lt;/strong&gt;, which breaks the correctness of the snapshot at &lt;strong&gt;gc_safepoint=89&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Handling Write_type::DEL in Compaction Filter&lt;/strong&gt;&lt;br&gt;
As we know from the gc_keys section, &lt;strong&gt;write_type::DEL&lt;/strong&gt; is a special case. When the compaction filter is enabled, how do we handle this type of key? The answer is yes, it requires special handling. First, we need to consider when we can delete &lt;strong&gt;write_type::DEL&lt;/strong&gt; data.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5c4m4yufexvehymbacjt.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5c4m4yufexvehymbacjt.png" alt="Image description" width="800" height="371"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When compacting the Lowest-level SST files, if we find that the current key meets the following conditions, we can safetly reclaim this version using &lt;strong&gt;gc_keys(a,89)&lt;/strong&gt;:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The current key is the latest version before the gc_safepoint 89.&lt;/li&gt;
&lt;li&gt;The current key is in Level 6, and it is the only remaining version. This ensures there are no earlier versions (and ensures no additional writes are generated during gc_keys).&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;After this compaction:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The new &lt;strong&gt;SST&lt;/strong&gt; file will still include a &lt;strong&gt;write_type::DEL&lt;/strong&gt; version.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;gc_keys&lt;/strong&gt; will write a &lt;strong&gt;(DELETE, a_85)&lt;/strong&gt; operation to &lt;strong&gt;RocksDB&lt;/strong&gt;. &lt;strong&gt;This is the only way to generate a tombstone for write-cf with the compaction filter enabled&lt;/strong&gt;.&lt;/li&gt;
&lt;/ol&gt;
&lt;h2&gt;
  
  
  Related Configuration
&lt;/h2&gt;

&lt;p&gt;As we’ve discussed, when the compaction filter is enabled, most physical data reclamation is completed during the RocksDB write CF compaction. For each key:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;For tso &amp;gt; gc safepoint, the key is retained and skipped.&lt;/li&gt;
&lt;li&gt;For tso &amp;lt;= gc safepoint: The latest version is retained, and older versions are filtered.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg4faauhmye8qo7qmw669.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg4faauhmye8qo7qmw669.png" alt="Image description" width="800" height="188"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Now, the next question is: Since the GC process (physical space reclamation) relies heavily on RocksDB’s compaction, how can we stimulate RocksDB’s compaction process?&lt;/p&gt;

&lt;p&gt;In addition to automatic triggers, TiKV also runs a thread that periodically checks the status of each region and decides whether to trigger compaction based on the presence of old versions in the region. Currently, we offer the following &lt;a href="https://docs.pingcap.com/tidb/stable/tikv-configuration-file/" rel="noopener noreferrer"&gt;parameters&lt;/a&gt; to control the speed of region checks and whether a region should initiate compaction:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-check-interval&lt;/strong&gt;: Generally, this does not need adjustment.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-check-step&lt;/strong&gt;: Generally, this does not need adjustment.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-min-tombstones&lt;/strong&gt;: The number of tombstones required to trigger RocksDB compaction. Default: 10,000.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-tombstones-percent&lt;/strong&gt;: The percentage of tombstones required to trigger RocksDB compaction. Default: 30%.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-min-redundant-rows&lt;/strong&gt; (introduced in v7.1.0): The number of redundant MVCC data rows needed to trigger RocksDB compaction. Default: 50,000.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-redundant-rows-percent&lt;/strong&gt; (introduced in v7.1.0): The percentage of redundant MVCC data rows required to trigger RocksDB compaction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Notably, for versions prior to 7.1.0, since we did not have the redundant MVCC version detection, we must manually compact regions to trigger the first round of compaction.&lt;/p&gt;
&lt;h2&gt;
  
  
  Related Monitoring
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; GC in Compaction-filter:&lt;/strong&gt;&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjpst7hj6wmoiqkj2puiy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjpst7hj6wmoiqkj2puiy.png" alt="Image description" width="800" height="177"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Key field definitions: During the compaction filter process, if the key-value meets the following conditions:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3cvq0lwow4mhe7wv1h24.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3cvq0lwow4mhe7wv1h24.png" alt="Image description" width="800" height="227"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;If it is before the GC safepoint and not the latest version (a-v1, a-v5, b-v5):&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;filtered: The number of old versions directly filtered (physically deleted, no new writes) by the compaction filter, representing the effective reclamation of old version data. If this metric is empty, it means there are no old versions to reclaim.&lt;/li&gt;
&lt;li&gt;Orphan-version: After the old version is deleted from write-cf, data in default-cf needs to be cleaned up. If cleaning fails, it will be handled via GcTask::OrphanVersions. If there is data here, it indicates that there were too many versions to delete, causing RocksDB to be overloaded.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Latest version before the GC safepoint (the oldest version to retain, a-v10, b-v12):&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;rollback/lock&lt;/strong&gt;: Write types of Rollback/Lock, which will create a tombstone in RocksDB.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_met&lt;/strong&gt;: Write type = DELETE, and it’s the lowest-level SST file.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_handled&lt;/strong&gt;: Data with write type = DELETE reclaimed through gc_keys().&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_wasted&lt;/strong&gt;: Data reclaimed through gc_keys() that was already deleted.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_wasted + mvcc_deletion_handled&lt;/strong&gt;: The number of keys with type = DELETE that, at the bottommost level, only have one version.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
  
  
  Common Issues
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;The Problem of Physical Space Not Being Released Long-Term After Deleting Data Using Compaction-filter&lt;/strong&gt;&lt;br&gt;
Although the compaction filter GC can directly clean up old data during the compaction stage and alleviate GC pressure, we know from the above principles that relying on RocksDB’s compaction for data reclamation means that if RocksDB’s compaction is not triggered, physical space will not be released even after the GC safepoint has passed.&lt;/p&gt;

&lt;p&gt;Therefore, stimulating RocksDB compaction becomes crucial in such cases.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Workaround 1: Adjusting Compaction Frequency via Parameters&lt;/strong&gt;&lt;br&gt;
For large DELETE operations, since no new writes occur after the data is deleted, it becomes more difficult to stimulate RocksDB’s automatic compaction.&lt;/p&gt;

&lt;p&gt;In versions 7.1.0 and later, we can adjust the parameters related to MVCC redundant versions to stimulate RocksDB compaction, with key parameters including:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;region-compact-min-redundant-rows&lt;/code&gt; (introduced in v7.1.0): The number of redundant MVCC data rows required to trigger RocksDB compaction. Default: 50,000.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;region-compact-redundant-rows-percent&lt;/code&gt; (introduced in v7.1.0): The percentage of redundant MVCC data rows required to trigger RocksDB compaction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In versions before 7.1.0, this feature was not available, so these versions require manual compaction. However, adjusting the above two parameters in such cases has minimal effect.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Currently, there are no parameters that stimulate compaction by counting deleted MVCC versions, so in most cases, this data cannot be automatically reclaimed. We can track this issue: &lt;a href="https://github.com/tikv/tikv/issues/17269" rel="noopener noreferrer"&gt;GitHub issue #17269&lt;/a&gt;.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Workaround 2: Manual Compaction&lt;/strong&gt;&lt;br&gt;
If we’ve performed a large DELETE operation on a table, and the deletion has passed the GC lifetime, we can quickly reclaim physical space by manually compacting the region:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Method 1: Perform Full Table Compaction During Off-Peak Hours&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;1.Query the minimum and maximum keys for the table (the key is computed from TiKV and has already been converted to memcomparable):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;select min(START_KEY) as START_KEY, max(END_KEY) as END_KEY from information_schema.tikv_region_status where db_name='' and table_name=''
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;2.Convert the *&lt;em&gt;start and end keys *&lt;/em&gt; to escaped format using tikv-ctl:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;----compact write cf----
   tiup ctl:v7.5.0 tikv --host "127.0.0.1:20160" compact --bottommost force -c write --from "zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372" --to "t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370"
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 compact --bottommost force -c write --from zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372 --to t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370
store:"127.0.0.1:20160" compact db:Kv cf:write range:[[122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 183, 95, 114, 128, 0, 0, 0, 0, 255, 69, 67, 29, 0, 0, 0, 0, 0, 250], [116, 128, 0, 0, 0, 0, 0, 0, 255, 186, 0, 0, 0, 0, 0, 0, 0, 248]) success!
  ---If the above doesn’t work, try compact default cf---
  tiup ctl:v7.1.1 tikv --host IP:port compact --bottomost force -c default --from 'zr\000\000\001\000\000\000\000\373' --to 'zt\200\000\000\000\000\000\000\377[\000\000\000\000\000\000\000\370'
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;3.Use tikv-ctl to perform compaction, adding a z prefix to the converted string, and compact both write-cf and default-cf (for all TiKV instances):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;----compact write cf----
   tiup ctl:v7.5.0 tikv --host "127.0.0.1:20160" compact --bottommost force -c write --from "zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372" --to "t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370"
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 compact --bottommost force -c write --from zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372 --to t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370
store:"127.0.0.1:20160" compact db:Kv cf:write range:[[122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 183, 95, 114, 128, 0, 0, 0, 0, 255, 69, 67, 29, 0, 0, 0, 0, 0, 250], [116, 128, 0, 0, 0, 0, 0, 0, 255, 186, 0, 0, 0, 0, 0, 0, 0, 248]) success!
  ---If the above doesn’t work, try compact default cf---
  tiup ctl:v7.1.1 tikv --host IP:port compact --bottomost force -c default --from 'zr\000\000\001\000\000\000\000\373' --to 'zt\200\000\000\000\000\000\000\377[\000\000\000\000\000\000\000\370'
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt;: As we learned earlier when cleaning up writeType::DELETE, when DELETE is the latest version, this version becomes the only version of the key to delete. It needs to be compacted to the lowest level of RocksDB before it can be fully cleaned. Therefore, we generally need to run the compaction command at least twice to reclaim physical space.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt;: RocksDB compaction requires temporary space. If the TiKV instance doesn’t have sufficient temporary space, it’s recommended to use Method 2 to split the compaction pressure.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Method 2: For large tables, to reduce performance impact on the cluster, compact by region instead of the entire table:&lt;/strong&gt;&lt;br&gt;
1.Query all regions of the table:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;select * from information_schema.tikv_region_status where db_name='' and table_name=''
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;2.For all regions in the table, run the following commands on their respective TiKV replicas:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Use tikv-ctl to query the MVCC properties of the current region. If the mvcc.num_deletes and write_cf.num_deletes are small, the region has been processed, and you can skip to the next region.
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;tikv-ctl --host tikv-host:20160. region-properties -r  {region-id}
-- example-- 
 tiup ctl:v7.5.0 tikv --host  "127.0.0.1:20160" region-properties -r 20026
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 region-properties -r 20026
mvcc.min_ts: 440762314407804933
mvcc.max_ts: 447448067356491781
mvcc.num_rows: 2387047
mvcc.num_puts: 2454144
mvcc.num_deletes: 9688
mvcc.num_versions: 2464879
mvcc.max_row_versions: 952
writecf.num_entries: 2464879
writecf.num_deletes: 0
writecf.num_files: 3
writecf.sst_files: 053145.sst, 061055.sst, 057591.sst
defaultcf.num_entries: 154154
defaultcf.num_files: 1
defaultcf.sst_files: 058164.sst
region.start_key: 7480000000000000ff545f720380000000ff0000000403800000ff0000000004038000ff0000000006a80000fd
region.end_key: 7480000000000000ff545f720380000000ff0000000703800000ff0000000002038000ff0000000002300000fd
region.middle_key_by_approximate_size: 7480000000000000ff545f720380000000ff0000000503800000ff0000000009038000ff0000000005220000fdf9ca5f5c3067ffc1
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Use tikv-ctl to manually compact the current region. After completion, continue looping to check whether the region’s properties have changed.
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;tiup ctl:v7.5.0 tikv --pd IP:port compact --bottommost force -c write --region {region-id}
  tiup ctl:v7.5.0 tikv --pd IP:port compact --bottommost force -c default --region {region-id}
 --example--
 tiup ctl:v7.5.0 tikv --host  "127.0.0.1:20160" compact --bottommost force -c write -r 20026
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 compact --bottommost force -c write -r 20026
store:"127.0.0.1:20160" compact_region db:Kv cf:write range:[[122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 84, 95, 114, 3, 128, 0, 0, 0, 255, 0, 0, 0, 4, 3, 128, 0, 0, 255, 0, 0, 0, 0, 4, 3, 128, 0, 255, 0, 0, 0, 0, 6, 168, 0, 0, 253], [122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 84, 95, 114, 3, 128, 0, 0, 0, 255, 0, 0, 0, 7, 3, 128, 0, 0, 255, 0, 0, 0, 0, 2, 3, 128, 0, 255, 0, 0, 0, 0, 2, 48, 0, 0, 253]) success!
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Method 3: Before v7.1.0, you can directly disable the compaction filter and use the traditional GC method.&lt;/strong&gt;&lt;br&gt;
This approach can significantly impact the system’s read and write performance during GC, so use it with caution.&lt;/p&gt;

</description>
      <category>database</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>TiKV Component GC (Physical Space Reclamation) Principles and Common Issues</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Fri, 04 Jul 2025 04:11:54 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/tikv-component-gc-physical-space-reclamation-principles-and-common-issues-3paj</link>
      <guid>https://dev.to/tidbcommunity/tikv-component-gc-physical-space-reclamation-principles-and-common-issues-3paj</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;This article was written by Shirly Wu, Support Escalation Engineer at PingCAP.&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;In TiDB, the GC worker uploads the GC safepoint to the PD server, and all TiKV instances regularly fetch the GC safepoint from PD. If there is any change, the TiKV instances will use the latest GC safepoint to start the local GC process. In this article, we will focus on the principles of TiKV-side GC and discuss some common issues.&lt;/p&gt;

&lt;h1&gt;
  
  
  GC Key in TiKV
&lt;/h1&gt;

&lt;p&gt;During GC, TiDB clears all locks before the GC safepoint across the entire cluster using the resolve locks mechanism. This means that once the data reaches TiKV, all transaction statuses before the GC safepoint are already resolved, and there are no remaining locks. The transaction statuses can be retrieved from the primary key of the distributed transaction. At this point, we can confidently and safely delete old version data.&lt;/p&gt;

&lt;p&gt;So, how exactly does the deletion process work?&lt;/p&gt;

&lt;p&gt;Let’s look at the following example:&lt;/p&gt;

&lt;p&gt;The current key has four versions, written in the following sequence:&lt;/p&gt;

&lt;p&gt;1:00 — New write or update, data stored in the default CF&lt;br&gt;
2:00 — Update, data stored in the default CF&lt;br&gt;
3:00 — Delete&lt;br&gt;
4:00 — New write, data stored in the default CF&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh2qxx2mm1iggf7m8ra6k.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh2qxx2mm1iggf7m8ra6k.png" alt="Image description" width="800" height="356"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If the GC safepoint is &lt;strong&gt;2:30&lt;/strong&gt;, which ensures snapshot consistency up to 2:30, we will retain the version read at 2:30: &lt;strong&gt;key_02:00 =&amp;gt; (PUT, 01:30)&lt;/strong&gt;. All previous versions before 2:30 will be deleted, including &lt;strong&gt;key_01:00&lt;/strong&gt;. The write-cf and default cf corresponding to this transaction will both be deleted.&lt;/p&gt;

&lt;p&gt;What if the GC safepoint is 3:30?&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F8mzvzezifucorwwi9247.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F8mzvzezifucorwwi9247.png" alt="Image description" width="800" height="384"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Similarly, the version read at 3:30,&lt;strong&gt;key_03:00 =&amp;gt; DELETE&lt;/strong&gt;, will be retained. All versions before 3:00 will be deleted.&lt;/p&gt;

&lt;p&gt;We see that the snapshot at 3:30 indicates that the transaction for key_03:00 is deleting this key.So, is it necessary to retain the MVCC version at 03:00? Not necessary. Therefore, under normal circumstances, if the GC safepoint is 3:30, the data that needs to be garbage collected for this key will be:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fnblrknbdz9u1a007ppkp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fnblrknbdz9u1a007ppkp.png" alt="Image description" width="800" height="382"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is how the GC process works for a specific key — TiKV’s GC process requires scanning all the keys on the current TiKV instance and deleting the old versions that meet the GC criteria.&lt;/p&gt;
&lt;h2&gt;
  
  
  Related Monitoring
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;gc_keys&lt;/strong&gt; can create read pressure on the system since it needs to scan all versions of the current key to determine whether old versions should be deleted. Related monitoring can be found in &lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; GC scan write/default details&lt;/strong&gt;, which records the pressure on RocksDB’s write/default CF during GC worker execution:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpi08qbar3kcn6l4ixnov.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fpi08qbar3kcn6l4ixnov.png" alt="Image description" width="800" height="119"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The duration of gc_keys can be seen in &lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; GC tasks duration&lt;/strong&gt;. If there is high latency in this area, it indicates significant GC pressure or that the read/write pressure on the system is affecting the GC process.&lt;/p&gt;
&lt;h1&gt;
  
  
  GC in TiKV
&lt;/h1&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Feaengscirfwze2lawnle.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Feaengscirfwze2lawnle.png" alt="Image description" width="800" height="405"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h1&gt;
  
  
  GC Worker
&lt;/h1&gt;

&lt;p&gt;Each TiKV instance has a GC worker thread responsible for handling specific GC tasks. The GC worker in TiKV mainly handles the following two types of requests:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;GC_keys&lt;/strong&gt;: This involves scanning and deleting old versions of a specific key that meet the GC criteria. The detailed process was described in the first chapter.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GC(range)&lt;/strong&gt;: This involves using GC_keys on a specified range of keys, performing GC on each key individually within the range.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;unsafe-destroy-range&lt;/strong&gt;: This is the direct physical cleanup of a continuous range of data, corresponding to operations like truncate/drop table/partition mentioned in the previous article.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Currently, the GC worker has two key configurations, which cannot be adjusted:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Thread count&lt;/strong&gt;: Currently, the GC worker only has one thread. This is hardcoded in the code here, and no external configuration is provided.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GC_MAX_PENDING_TASKS&lt;/strong&gt;: This is the maximum number of tasks the GC worker queue can handle, set to 4096.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
  
  
  Related Monitoring
&lt;/h2&gt;

&lt;p&gt;GC tasks QPS/duration can be monitored in tikv-details -&amp;gt; GC -&amp;gt; GC tasks/GC tasks duration. If the GC tasks duration is high, we need to check whether the GC worker’s CPU resources are sufficient, in combination with the QPS.&lt;/p&gt;

&lt;p&gt;GC worker CPU usage: &lt;strong&gt;tikv-details -&amp;gt; thread CPU -&amp;gt; GC worker&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbtvz0x86cm8xd1lx5ypa.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbtvz0x86cm8xd1lx5ypa.png" alt="Image description" width="800" height="202"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h1&gt;
  
  
  GC manager
&lt;/h1&gt;

&lt;p&gt;The GC manager is the thread responsible for driving the GC work in TiKV. The main steps are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Syncing the GC safepoint to local memory&lt;/li&gt;
&lt;li&gt;Globally guiding the execution of specific GC tasks&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;1. Syncing GC Safepoint to Local&lt;/strong&gt;&lt;br&gt;
The GC manager regularly requests the latest GC safepoint from PD every ten seconds and refreshes the safepoint in memory. The related monitoring can be found in &lt;strong&gt;tikv-details -&amp;gt; GC&lt;/strong&gt;:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ftuornk2im91o3muj97wp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ftuornk2im91o3muj97wp.png" alt="Image description" width="791" height="335"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Common Issues&lt;/strong&gt;&lt;br&gt;
When monitoring shows that the TiKV auto GC safepoint is stuck for a long time and not advancing, it indicates that the GC state on the TiDB side may have a problem. At this point, you need to follow the troubleshooting steps in the previous article to investigate why GC on the TiDB side is stuck.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Implementing GC Jobs&lt;/strong&gt;&lt;br&gt;
If the GC manager detects that the GC safepoint has advanced, it begins implementing the specific GC tasks based on the current system configuration. This part is mainly divided into two methods based on the &lt;strong&gt;gc.enable-compaction-filter&lt;/strong&gt; parameter:&lt;/p&gt;

&lt;p&gt;a. Traditional GC, where GC(range) is called for each region.&lt;/p&gt;

&lt;p&gt;b. GC via compaction filter (default method after 5.0): Instead of performing a real GC, this method waits until RocksDB performs compaction, at which point old versions are reclaimed using the compaction filter.&lt;/p&gt;
&lt;h1&gt;
  
  
  TiKV GC Implementation Methods
&lt;/h1&gt;

&lt;p&gt;Next, we will explain the principles and common troubleshooting steps for these two GC methods.&lt;/p&gt;
&lt;h2&gt;
  
  
  GC by Region (Traditional GC)
&lt;/h2&gt;

&lt;p&gt;In traditional GC, when &lt;strong&gt;gc.enable-compaction-filter&lt;/strong&gt; is set to false, the GC manager performs GC on each TiKV region one by one. This process is referred to as “GC a round.”&lt;/p&gt;
&lt;h3&gt;
  
  
  GC a Round
&lt;/h3&gt;

&lt;p&gt;In traditional GC, a round of GC is completed when GC has been executed on all regions, and we mark the progress as 100%. If GC progress never reaches 100%, it indicates that GC pressure is high, and the physical space reclamation process is being affected. GC progress can be monitored in &lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; tikv-auto-gc-progress&lt;/strong&gt;. We can also observe the time taken for each round of GC in TiKV.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F32szgo5zfhbqqmttv9y7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F32szgo5zfhbqqmttv9y7.png" alt="Image description" width="800" height="375"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;After introducing the concept of a ‘GC round,’ let’s now look at how TiKV defines a round during execution.&lt;/p&gt;

&lt;p&gt;In simple terms, the GC manager starts GC work from the first region, continuing until the last region’s GC work is completed. However, if there is too much GC work, the GC safepoint may advance before the GC reaches the last region. In this case, do we continue using the old safepoint or the new one?&lt;/p&gt;

&lt;p&gt;The answer is to use the latest GC safepoint in real time for each region that follows. This is a simple optimization of traditional GC.&lt;/p&gt;

&lt;p&gt;Here’s an &lt;strong&gt;example&lt;/strong&gt; of how TiKV processes an updated GC safepoint during GC execution&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qenkuqyrupilxxohoqq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qenkuqyrupilxxohoqq.png" alt="Image description" width="800" height="387"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;When GC starts, gc-safepoint is 10, and we use safepoint=10 for GC regions 1 and 2.&lt;/li&gt;
&lt;li&gt;After finishing GC in region 2, the GC safepoint advances to 20. From this point on, we use 20 to continue GC in the remaining regions.&lt;/li&gt;
&lt;li&gt;Once all regions have been GC’d with gc safepoint=20, we start again from the first region, now using gc safepoint=20 for GC.&lt;/li&gt;
&lt;/ol&gt;
&lt;h3&gt;
  
  
  Common Issues
&lt;/h3&gt;

&lt;p&gt;In traditional GC, since all old versions must be scanned before being deleted, and then the delete operation is written to RocksDB’s MVCC, the system is heavily impacted. This is manifested in the following ways:&lt;/p&gt;

&lt;p&gt;1.Impact on GC Progress:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The GC worker becomes a bottleneck. Since all reclamation tasks need to be handled by the GC worker, which only has one thread, its CPU usage will be fully occupied. You can monitor this using: tikv-details -&amp;gt; thread CPU -&amp;gt; GC worker&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;2.Impact on Business Read/Write:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Raftstore read/write pressure increases: The GC worker needs to scan all data versions and then delete the matching ones during GC_keys tasks.&lt;/li&gt;
&lt;li&gt;The increased write load on RocksDB in the short term causes rapid accumulation of L0 files, triggering RocksDB compaction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;3.Physical Space Usage Increases:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Since a DELETE operation in RocksDB ultimately results in writing a new version of the current key, physical space usage might actually increase.&lt;/li&gt;
&lt;li&gt;Only after RocksDB compaction completes will the physical space be reclaimed, and this compaction requires temporary space.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In such cases where business cannot tolerate these impacts, the workaround is to enable the gc.enable-compaction-filter parameter.&lt;/p&gt;
&lt;h1&gt;
  
  
  GC with Compaction Filter
&lt;/h1&gt;

&lt;p&gt;As mentioned earlier, in traditional GC, we scan TiKV’s MVCC entries one by one and use the safepoint to determine which data can be deleted, sending a DELETE key operation to Raftstore (RocksDB). Since RocksDB uses an LSM tree architecture and its internal MVCC mechanism, old versions of data are not immediately deleted when new data is written, even during a DELETE operation. They are retained alongside the new data.&lt;/p&gt;
&lt;h2&gt;
  
  
  Why Compaction in RocksDB?
&lt;/h2&gt;

&lt;p&gt;Let’s explore the RocksDB architecture to understand the compaction mechanism.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flw01jagfu1oknw8iaknu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Flw01jagfu1oknw8iaknu.png" alt="Image description" width="800" height="412"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;RocksDB uses an LSM tree structure to improve write performance.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;RocksDB Write Flow&lt;/strong&gt;&lt;br&gt;
When RocksDB receives a write operation (PUT(key =&amp;gt; value)), the complete process is as follows:&lt;/p&gt;

&lt;p&gt;1.When a new key is written, it is first written to the WAL and memtable, and then a success response is returned.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;RocksDB appends the data directly to the WAL file, persisting it locally.&lt;/li&gt;
&lt;li&gt;The data is written on an active memtable, which is fast because it operates in memory, and the data in the memtable is ordered.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;2.As more data is written, the memtable gradually fills up. When it becomes full, the active memtable is marked as immutable, and a new active memtable is created to store new writes.&lt;/p&gt;

&lt;p&gt;3.The data from the immutable memtable is flushed to a local file, which we call an SST file.&lt;/p&gt;

&lt;p&gt;4.Over time, more SST files are created. Note that SST files directly converted from memtables contain ordered data, but the data ranges are global [~, ~]. These SST files are placed in Level 0.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;RocksDB Read Flow&lt;/strong&gt;&lt;br&gt;
When a read request is received, the lookup follows this sequence:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Search in the memtable. If the key is found, return the value.&lt;/li&gt;
&lt;li&gt;Search in the block-cache (the data in the block-cache comes from SST files, which we will refer to as SST here). Search for the corresponding key in the SST files. Since the SST files in Level 0 are the most recent, data will be searched first in these files. Additionally, the SST files in Level 0 are directly converted from memtables, and their data ranges are global. In extreme cases, it may be necessary to search through all such SST files one by one.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Compaction for Improved Read Performance&lt;/strong&gt;&lt;br&gt;
From the above read flow, we can see that if we only have SST data in Level 0, as more and more files accumulate in Level 0, RocksDB’s read performance will degrade. To improve read performance, RocksDB performs merge sorting on the SST files in Level 0, a process known as compaction. The main tasks of RocksDB compaction are:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Merging multiple SST files into one.&lt;/li&gt;
&lt;li&gt;Keeping only the latest MVCC version from RocksDB’s perspective (GC).&lt;/li&gt;
&lt;li&gt;Compacting lower levels into Level 1~Level 6.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;From the above process, we can see that RocksDB’s compaction work is similar to what we do during GC. So, is it possible to combine TiKV’s GC process with RocksDB’s compaction? Of course, it is.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Combining TiKV GC with Compaction&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;RocksDB provides an interface for compaction filters, which allows us to define rules for filtering keys during the compaction process. Based on the rules we provide in the compaction filter, we can decide whether to discard the key during this phase.&lt;/p&gt;
&lt;h2&gt;
  
  
  Implementation Principle
&lt;/h2&gt;

&lt;p&gt;Let’s take TiKV‘s GC as an example to understand how data is reclaimed during the compaction process when the compaction filter is enabled.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TiKV‘s Compaction Filter Only Affects Write-CF&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;First, TiKV’s compaction filter only affects write-cf. Why? Because write-cf stores MVCC data, while data-cf stores the actual data. As for lock-cf, as we’ve discussed on the TiDB side, after the GC safepoint is updated to PD, there are no more locks in lock-cf before the safepoint.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Directly Filtering Unnecessary MVCC Keys in Compaction&lt;/strong&gt;&lt;br&gt;
Next, let’s look at how an MVCC key a behaves during a compaction process:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Foj2v2x9poh6z7s7occde.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Foj2v2x9poh6z7s7occde.png" alt="Image description" width="800" height="315"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The TiKV MVCC key &lt;strong&gt;a&lt;/strong&gt; in write-cf has a commit_ts suffix. Initially, let’s assume we are compacting two SST files on the left, which are in Level 2 and Level 3. After compaction, these files will be stored in Level 3.&lt;/li&gt;
&lt;li&gt;The SST file in Level 2 contains &lt;strong&gt;a_90&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;The SST file in Level 3 contains &lt;strong&gt;a_85, a_82,&lt;/strong&gt; and &lt;strong&gt;a_80&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;The current GC safepoint is 89. Based on the GC key processing rules from Chapter 1, we know we need to retain the older version a_85, meaning all versions before a_85 can be deleted.&lt;/li&gt;
&lt;li&gt;From the right, we can see that the new SST file only contains a_85 and a_90. The other versions, along with the corresponding data in default-cf, are deleted during compaction.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;In summary, compared to traditional GC, using a compaction filter for GC has the following advantages:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;It eliminates the need to read from RocksDB.&lt;/li&gt;
&lt;li&gt;The deletion (write) process for RocksDB is simplified.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Although compaction introduces some pressure, it completely removes the impact of GC on RocksDB’s read/write operations, resulting in a significant performance optimization.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Compaction on Non-L6 SST Files with Write_type::DEL&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzdh3rx64bkc1o20u2ug3.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzdh3rx64bkc1o20u2ug3.png" alt="Image description" width="800" height="356"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When compaction occurs, if we encounter the latest version of data as &lt;strong&gt;write_type::DEL&lt;/strong&gt;, should we delete it directly? &lt;strong&gt;The answer is no.&lt;/strong&gt; Unlike the gc_keys interface, which scans all versions of the key, compaction only scans the versions within the SST files involved in the current compaction. Therefore, if we delete &lt;strong&gt;write_type::DEL&lt;/strong&gt; at the current level during compaction, there might still be older versions of the key at lower levels. For example, if we delete &lt;strong&gt;a_85 =&amp;gt; write_type::DEL&lt;/strong&gt; during this compaction, when users read the snapshot at &lt;strong&gt;gc_safepoint=89&lt;/strong&gt;, &lt;strong&gt;a_85&lt;/strong&gt; would be missing, and the latest matching version would be &lt;strong&gt;a_78&lt;/strong&gt;, which breaks the correctness of the snapshot at &lt;strong&gt;gc_safepoint=89&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Handling Write_type::DEL in Compaction Filter&lt;/strong&gt;&lt;br&gt;
As we know from the gc_keys section, &lt;strong&gt;write_type::DEL&lt;/strong&gt; is a special case. When the compaction filter is enabled, how do we handle this type of key? The answer is yes, it requires special handling. First, we need to consider when we can delete &lt;strong&gt;write_type::DEL&lt;/strong&gt; data.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5c4m4yufexvehymbacjt.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5c4m4yufexvehymbacjt.png" alt="Image description" width="800" height="371"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When compacting the Lowest-level SST files, if we find that the current key meets the following conditions, we can safetly reclaim this version using &lt;strong&gt;gc_keys(a,89)&lt;/strong&gt;:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The current key is the latest version before the gc_safepoint 89.&lt;/li&gt;
&lt;li&gt;The current key is in Level 6, and it is the only remaining version. This ensures there are no earlier versions (and ensures no additional writes are generated during gc_keys).&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;After this compaction:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The new &lt;strong&gt;SST&lt;/strong&gt; file will still include a &lt;strong&gt;write_type::DEL&lt;/strong&gt; version.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;gc_keys&lt;/strong&gt; will write a &lt;strong&gt;(DELETE, a_85)&lt;/strong&gt; operation to &lt;strong&gt;RocksDB&lt;/strong&gt;. &lt;strong&gt;This is the only way to generate a tombstone for write-cf with the compaction filter enabled&lt;/strong&gt;.&lt;/li&gt;
&lt;/ol&gt;
&lt;h2&gt;
  
  
  Related Configuration
&lt;/h2&gt;

&lt;p&gt;As we’ve discussed, when the compaction filter is enabled, most physical data reclamation is completed during the RocksDB write CF compaction. For each key:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;For tso &amp;gt; gc safepoint, the key is retained and skipped.&lt;/li&gt;
&lt;li&gt;For tso &amp;lt;= gc safepoint: The latest version is retained, and older versions are filtered.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg4faauhmye8qo7qmw669.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg4faauhmye8qo7qmw669.png" alt="Image description" width="800" height="188"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Now, the next question is: Since the GC process (physical space reclamation) relies heavily on RocksDB’s compaction, how can we stimulate RocksDB’s compaction process?&lt;/p&gt;

&lt;p&gt;In addition to automatic triggers, TiKV also runs a thread that periodically checks the status of each region and decides whether to trigger compaction based on the presence of old versions in the region. Currently, we offer the following &lt;a href="https://docs.pingcap.com/tidb/stable/tikv-configuration-file/" rel="noopener noreferrer"&gt;parameters&lt;/a&gt; to control the speed of region checks and whether a region should initiate compaction:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-check-interval&lt;/strong&gt;: Generally, this does not need adjustment.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-check-step&lt;/strong&gt;: Generally, this does not need adjustment.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-min-tombstones&lt;/strong&gt;: The number of tombstones required to trigger RocksDB compaction. Default: 10,000.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-tombstones-percent&lt;/strong&gt;: The percentage of tombstones required to trigger RocksDB compaction. Default: 30%.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-min-redundant-rows&lt;/strong&gt; (introduced in v7.1.0): The number of redundant MVCC data rows needed to trigger RocksDB compaction. Default: 50,000.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;region-compact-redundant-rows-percent&lt;/strong&gt; (introduced in v7.1.0): The percentage of redundant MVCC data rows required to trigger RocksDB compaction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Notably, for versions prior to 7.1.0, since we did not have the redundant MVCC version detection, we must manually compact regions to trigger the first round of compaction.&lt;/p&gt;
&lt;h2&gt;
  
  
  Related Monitoring
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;tikv-details -&amp;gt; GC -&amp;gt; GC in Compaction-filter:&lt;/strong&gt;&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjpst7hj6wmoiqkj2puiy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjpst7hj6wmoiqkj2puiy.png" alt="Image description" width="800" height="177"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Key field definitions: During the compaction filter process, if the key-value meets the following conditions:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3cvq0lwow4mhe7wv1h24.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3cvq0lwow4mhe7wv1h24.png" alt="Image description" width="800" height="227"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;If it is before the GC safepoint and not the latest version (a-v1, a-v5, b-v5):&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;filtered: The number of old versions directly filtered (physically deleted, no new writes) by the compaction filter, representing the effective reclamation of old version data. If this metric is empty, it means there are no old versions to reclaim.&lt;/li&gt;
&lt;li&gt;Orphan-version: After the old version is deleted from write-cf, data in default-cf needs to be cleaned up. If cleaning fails, it will be handled via GcTask::OrphanVersions. If there is data here, it indicates that there were too many versions to delete, causing RocksDB to be overloaded.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Latest version before the GC safepoint (the oldest version to retain, a-v10, b-v12):&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;rollback/lock&lt;/strong&gt;: Write types of Rollback/Lock, which will create a tombstone in RocksDB.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_met&lt;/strong&gt;: Write type = DELETE, and it’s the lowest-level SST file.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_handled&lt;/strong&gt;: Data with write type = DELETE reclaimed through gc_keys().&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_wasted&lt;/strong&gt;: Data reclaimed through gc_keys() that was already deleted.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;mvcc_deletion_wasted + mvcc_deletion_handled&lt;/strong&gt;: The number of keys with type = DELETE that, at the bottommost level, only have one version.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
  
  
  Common Issues
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;The Problem of Physical Space Not Being Released Long-Term After Deleting Data Using Compaction-filter&lt;/strong&gt;&lt;br&gt;
Although the compaction filter GC can directly clean up old data during the compaction stage and alleviate GC pressure, we know from the above principles that relying on RocksDB’s compaction for data reclamation means that if RocksDB’s compaction is not triggered, physical space will not be released even after the GC safepoint has passed.&lt;/p&gt;

&lt;p&gt;Therefore, stimulating RocksDB compaction becomes crucial in such cases.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Workaround 1: Adjusting Compaction Frequency via Parameters&lt;/strong&gt;&lt;br&gt;
For large DELETE operations, since no new writes occur after the data is deleted, it becomes more difficult to stimulate RocksDB’s automatic compaction.&lt;/p&gt;

&lt;p&gt;In versions 7.1.0 and later, we can adjust the parameters related to MVCC redundant versions to stimulate RocksDB compaction, with key parameters including:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;region-compact-min-redundant-rows&lt;/code&gt; (introduced in v7.1.0): The number of redundant MVCC data rows required to trigger RocksDB compaction. Default: 50,000.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;region-compact-redundant-rows-percent&lt;/code&gt; (introduced in v7.1.0): The percentage of redundant MVCC data rows required to trigger RocksDB compaction.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In versions before 7.1.0, this feature was not available, so these versions require manual compaction. However, adjusting the above two parameters in such cases has minimal effect.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Currently, there are no parameters that stimulate compaction by counting deleted MVCC versions, so in most cases, this data cannot be automatically reclaimed. We can track this issue: &lt;a href="https://github.com/tikv/tikv/issues/17269" rel="noopener noreferrer"&gt;GitHub issue #17269&lt;/a&gt;.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Workaround 2: Manual Compaction&lt;/strong&gt;&lt;br&gt;
If we’ve performed a large DELETE operation on a table, and the deletion has passed the GC lifetime, we can quickly reclaim physical space by manually compacting the region:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Method 1: Perform Full Table Compaction During Off-Peak Hours&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;1.Query the minimum and maximum keys for the table (the key is computed from TiKV and has already been converted to memcomparable):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;select min(START_KEY) as START_KEY, max(END_KEY) as END_KEY from information_schema.tikv_region_status where db_name='' and table_name=''
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;2.Convert the *&lt;em&gt;start and end keys *&lt;/em&gt; to escaped format using tikv-ctl:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;----compact write cf----
   tiup ctl:v7.5.0 tikv --host "127.0.0.1:20160" compact --bottommost force -c write --from "zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372" --to "t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370"
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 compact --bottommost force -c write --from zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372 --to t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370
store:"127.0.0.1:20160" compact db:Kv cf:write range:[[122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 183, 95, 114, 128, 0, 0, 0, 0, 255, 69, 67, 29, 0, 0, 0, 0, 0, 250], [116, 128, 0, 0, 0, 0, 0, 0, 255, 186, 0, 0, 0, 0, 0, 0, 0, 248]) success!
  ---If the above doesn’t work, try compact default cf---
  tiup ctl:v7.1.1 tikv --host IP:port compact --bottomost force -c default --from 'zr\000\000\001\000\000\000\000\373' --to 'zt\200\000\000\000\000\000\000\377[\000\000\000\000\000\000\000\370'
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;3.Use tikv-ctl to perform compaction, adding a z prefix to the converted string, and compact both write-cf and default-cf (for all TiKV instances):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;----compact write cf----
   tiup ctl:v7.5.0 tikv --host "127.0.0.1:20160" compact --bottommost force -c write --from "zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372" --to "t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370"
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 compact --bottommost force -c write --from zt\200\000\000\000\000\000\000\377\267_r\200\000\000\000\000\377EC\035\000\000\000\000\000\372 --to t\200\000\000\000\000\000\000\377\272\000\000\000\000\000\000\000\370
store:"127.0.0.1:20160" compact db:Kv cf:write range:[[122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 183, 95, 114, 128, 0, 0, 0, 0, 255, 69, 67, 29, 0, 0, 0, 0, 0, 250], [116, 128, 0, 0, 0, 0, 0, 0, 255, 186, 0, 0, 0, 0, 0, 0, 0, 248]) success!
  ---If the above doesn’t work, try compact default cf---
  tiup ctl:v7.1.1 tikv --host IP:port compact --bottomost force -c default --from 'zr\000\000\001\000\000\000\000\373' --to 'zt\200\000\000\000\000\000\000\377[\000\000\000\000\000\000\000\370'
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt;: As we learned earlier when cleaning up writeType::DELETE, when DELETE is the latest version, this version becomes the only version of the key to delete. It needs to be compacted to the lowest level of RocksDB before it can be fully cleaned. Therefore, we generally need to run the compaction command at least twice to reclaim physical space.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Note&lt;/strong&gt;: RocksDB compaction requires temporary space. If the TiKV instance doesn’t have sufficient temporary space, it’s recommended to use Method 2 to split the compaction pressure.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Method 2: For large tables, to reduce performance impact on the cluster, compact by region instead of the entire table:&lt;/strong&gt;&lt;br&gt;
1.Query all regions of the table:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;select * from information_schema.tikv_region_status where db_name='' and table_name=''
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;2.For all regions in the table, run the following commands on their respective TiKV replicas:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Use tikv-ctl to query the MVCC properties of the current region. If the mvcc.num_deletes and write_cf.num_deletes are small, the region has been processed, and you can skip to the next region.
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;tikv-ctl --host tikv-host:20160. region-properties -r  {region-id}
-- example-- 
 tiup ctl:v7.5.0 tikv --host  "127.0.0.1:20160" region-properties -r 20026
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 region-properties -r 20026
mvcc.min_ts: 440762314407804933
mvcc.max_ts: 447448067356491781
mvcc.num_rows: 2387047
mvcc.num_puts: 2454144
mvcc.num_deletes: 9688
mvcc.num_versions: 2464879
mvcc.max_row_versions: 952
writecf.num_entries: 2464879
writecf.num_deletes: 0
writecf.num_files: 3
writecf.sst_files: 053145.sst, 061055.sst, 057591.sst
defaultcf.num_entries: 154154
defaultcf.num_files: 1
defaultcf.sst_files: 058164.sst
region.start_key: 7480000000000000ff545f720380000000ff0000000403800000ff0000000004038000ff0000000006a80000fd
region.end_key: 7480000000000000ff545f720380000000ff0000000703800000ff0000000002038000ff0000000002300000fd
region.middle_key_by_approximate_size: 7480000000000000ff545f720380000000ff0000000503800000ff0000000009038000ff0000000005220000fdf9ca5f5c3067ffc1
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Use tikv-ctl to manually compact the current region. After completion, continue looping to check whether the region’s properties have changed.
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;tiup ctl:v7.5.0 tikv --pd IP:port compact --bottommost force -c write --region {region-id}
  tiup ctl:v7.5.0 tikv --pd IP:port compact --bottommost force -c default --region {region-id}
 --example--
 tiup ctl:v7.5.0 tikv --host  "127.0.0.1:20160" compact --bottommost force -c write -r 20026
Starting component `ctl`: /home/tidb/.tiup/components/ctl/v7.5.0/ctl tikv --host 127.0.0.1:20160 compact --bottommost force -c write -r 20026
store:"127.0.0.1:20160" compact_region db:Kv cf:write range:[[122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 84, 95, 114, 3, 128, 0, 0, 0, 255, 0, 0, 0, 4, 3, 128, 0, 0, 255, 0, 0, 0, 0, 4, 3, 128, 0, 255, 0, 0, 0, 0, 6, 168, 0, 0, 253], [122, 116, 128, 0, 0, 0, 0, 0, 0, 255, 84, 95, 114, 3, 128, 0, 0, 0, 255, 0, 0, 0, 7, 3, 128, 0, 0, 255, 0, 0, 0, 0, 2, 3, 128, 0, 255, 0, 0, 0, 0, 2, 48, 0, 0, 253]) success!
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Method 3: Before v7.1.0, you can directly disable the compaction filter and use the traditional GC method.&lt;/strong&gt;&lt;br&gt;
This approach can significantly impact the system’s read and write performance during GC, so use it with caution.&lt;/p&gt;

</description>
      <category>database</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>TiDB’s Chat2Query: Instant Business Insights, No SQL Required</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Tue, 15 Apr 2025 10:56:26 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/tidbs-chat2query-instant-business-insights-no-sql-required-1l8i</link>
      <guid>https://dev.to/tidbcommunity/tidbs-chat2query-instant-business-insights-no-sql-required-1l8i</guid>
      <description>&lt;p&gt;What if you could interact with your data just like you would with a colleague? No need for complicated SQL queries or advanced data analysis tools—just ask your data a question and get an immediate, clear answer. Sounds like magic, right? Well, it’s not. It’s TiDB’s Chat2Query, and it’s changing the game in how businesses explore and understand their data.&lt;/p&gt;

&lt;p&gt;In this post, we’ll dive into how Chat2Query works, the Text2SQL magic behind it, and why it’s been so successful at transforming the way businesses get insights. If you missed our &lt;a href="https://www.pingcap.com/blog/ai-powered-data-exploration-unpacking-the-latest-innovations-in-tidb-cloud/" rel="noopener noreferrer"&gt;previous post&lt;/a&gt;, where we discussed Chat2Query’s recent breakthroughs and its performance on industry benchmarks (86.30 on the Spider benchmark and Top 4 on the BIRD benchmark), we recommend checking that out for more context.&lt;/p&gt;

&lt;p&gt;Let’s get started!&lt;/p&gt;

&lt;h2&gt;
  
  
  What is Chat2Query?
&lt;/h2&gt;

&lt;p&gt;Forget the jargon. Forget the complicated queries. Chat2Query lets you ask questions in plain language and get answers straight from your data—instantly.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Want to know, “What were our sales last quarter?”&lt;/li&gt;
&lt;li&gt;Curious about, “Which product category performed the best?”&lt;/li&gt;
&lt;li&gt;Or maybe you’re wondering, “What are the trends in customer complaints this month?”&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Just type your question in simple language, and Chat2Query will translate it into SQL, pull the data, and serve it up in an easy-to-read format, complete with visuals. It’s as if your data speaks directly to you—no SQL required.&lt;/p&gt;

&lt;h2&gt;
  
  
  How Does Chat2Query Work?
&lt;/h2&gt;

&lt;p&gt;It’s surprisingly simple—and powerful.&lt;/p&gt;

&lt;h3&gt;
  
  
  1. Enrich the Data Context
&lt;/h3&gt;

&lt;p&gt;First, Chat2Query needs to get familiar with your data. To do this, it analyzes your database using both relational and vector databases. This hybrid approach allows Chat2Query to understand the structure of the database and the relationships between tables, columns, and entities. The vector database is key for enriching the context by storing more complex, high-dimensional data that helps Chat2Query better understand the relationships between data points. The more Chat2Query knows about the data, the more accurate and insightful the responses.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Ask Your Questions
&lt;/h3&gt;

&lt;p&gt;Once the data context is enriched, you can start asking questions. Chat2Query then converts your question into a SQL query, pulls the data, and gives you your answer—usually with a handy chart or graph to make it even easier to digest.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fqnkqycyr9fl7n2a2byri.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fqnkqycyr9fl7n2a2byri.png" alt="Image description" width="800" height="470"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Chat2Query Works So Well
&lt;/h2&gt;

&lt;p&gt;For Chat2Query to function effectively, it needs to understand the database schema. That’s where “Understand db” comes in. It’s like giving Chat2Query a roadmap of your data—helping it understand relationships between tables, columns, and entities.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Why it matters&lt;/strong&gt;: This step alone can improve SQL accuracy by 2-3% on benchmarks like &lt;a href="https://yale-lily.github.io/spider" rel="noopener noreferrer"&gt;Spider&lt;/a&gt;. A small increase, but a big deal when you’re dealing with large datasets.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh59eafpmwglwdvn5xqog.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fh59eafpmwglwdvn5xqog.png" alt="Image description" width="800" height="594"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Perfecting Prompts: Prompt Engineering
&lt;/h2&gt;

&lt;p&gt;You can’t just throw any question at a system and expect it to work perfectly. So, we engineer our prompts to ensure Chat2Query really nails it. By using advanced techniques like Chain of Thought (COT) and Retrieval Augmented Generation (RAG), we guide the system to reason through the question step-by-step, ensuring the most accurate SQL possible.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Why it matters&lt;/strong&gt;: Our COT + RAG combo helps Chat2Query consistently crush benchmarks like Spider and BIRD. It’s the secret sauce behind those impressive scores.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fx0mx73pbwhzdinrqp7sj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fx0mx73pbwhzdinrqp7sj.png" alt="Image description" width="800" height="874"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Fine-Tuning with Post-Processing
&lt;/h2&gt;

&lt;p&gt;Even with advanced technologies like LLMs, sometimes hallucinations can occur. That’s why we use a multi-agent collaboration mechanism during post-processing. This system works like a team of experts reviewing the raw SQL output, identifying any inconsistencies, and refining the query to improve its accuracy.&lt;/p&gt;

&lt;p&gt;The multi-agent collaboration mechanism helps ensure that even if a model misses something, other components of the system step in to catch those issues and make necessary adjustments. This added layer of refinement significantly enhances the reliability of the SQL queries produced by Chat2Query.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Why it matters&lt;/strong&gt;: This post-processing mechanism, along with the multi-agent system, increases the overall accuracy of SQL queries by 2-4%. It helps reduce errors and ensure that the output is stable, consistent, and ready for actionable insights.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdwhnjqxizlub725k6vby.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdwhnjqxizlub725k6vby.png" alt="Image description" width="800" height="819"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Real-World Use Cases: How Chat2Query Powers Smarter Decisions
&lt;/h2&gt;

&lt;p&gt;Now, let’s talk about how Chat2Query is making a real difference for businesses:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Sales Performance&lt;/strong&gt;: Ask “How much did our sales increase this month compared to last month?” and instantly get the data you need to adjust your sales strategy. No more waiting on reports or pulling data manually.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Customer Insights&lt;/strong&gt;: Quickly discover what your customers are saying. Ask “What were the most common customer complaints this month?” to identify areas that need attention and improve your service.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Supply Chain Optimization&lt;/strong&gt;: Stay on top of your inventory by asking “Which products are below the safety stock level?” or “Why did we experience delays last week?” to adjust your supply chain strategy on the fly.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Financial Reporting&lt;/strong&gt;: Need to know what caused fluctuations in the market? Simply ask, “What were the main factors driving market changes this week?” and get detailed insights to stay ahead of the competition.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Looking Ahead: The Future of Chat2Query
&lt;/h2&gt;

&lt;p&gt;Chat2Query is still evolving, and we’re continuously working to improve it. We’re exploring new techniques and optimizations to make Text2SQL even more accurate and powerful. Our goal is to keep simplifying the way businesses interact with their data, making complex analysis accessible to anyone, regardless of their technical background.&lt;/p&gt;

&lt;h2&gt;
  
  
  Get Started with Chat2Query Today
&lt;/h2&gt;

&lt;p&gt;Ready to see the magic of Chat2Query for yourself? It’s time to make your data work harder for you.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;a href="https://auth.tidbcloud.com/login?state=hKFo2SA2VlhpQm1sLWVTbm8yVm9Gem00NHJRNUxVWWZ3bzFwRKFupWxvZ2luo3RpZNkgZ1N2YUxVR3diWnBCbWY5UHp4TlhkN19LVmN0QldFZ3GjY2lk2SA2SVp0aENmbVJLSVBFblFTVDhhRGJ0TTdTR2RNbmlSbA&amp;amp;client=6IZthCfmRKIPEnQST8aDbtM7SGdMniRl&amp;amp;protocol=oauth2&amp;amp;response_type=token%20id_token&amp;amp;redirect_uri=https%3A%2F%2Ftidbcloud.com%2Fauth_redirect%3Fprev%3D%2F%3F__hstc%3D86493575.154e04c1757264ebd3e2cfaa1f6f56f1.1744713902415.1744713902415.1744713902415.1%26__hssc%3D86493575.10.1744711174273%26__hsfp%3D1159537931&amp;amp;scope=openid%20email&amp;amp;nonce=gpJ~QEp8~D1APQrcfB7mM5jVTfic~C2L&amp;amp;auth0Client=eyJuYW1lIjoiYXV0aDAuanMiLCJ2ZXJzaW9uIjoiOS4xOS4xIn0%3D" rel="noopener noreferrer"&gt;Try TiDB Cloud for Free&lt;/a&gt;&lt;/strong&gt;: Experience the power of Chat2Query with TiDB Cloud and see how simple data analysis can be.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Schedule a Demo&lt;/strong&gt;: Want to learn more? &lt;a href="https://www.pingcap.com/contact-us/" rel="noopener noreferrer"&gt;Book a session&lt;/a&gt; with one of our experts to see how Chat2Query can transform your business.&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>ai</category>
      <category>database</category>
      <category>rag</category>
      <category>sql</category>
    </item>
    <item>
      <title>Migrating Vector Data from Milvus to TiDB</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Tue, 17 Dec 2024 08:35:37 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/migrating-vector-data-from-milvus-to-tidb-og0</link>
      <guid>https://dev.to/tidbcommunity/migrating-vector-data-from-milvus-to-tidb-og0</guid>
      <description>&lt;p&gt;&lt;em&gt;This article was written by caiyfc, a dedicated TiDB Cloud Serverless user and TiDB Community Moderator.&lt;/em&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;Recently, I’ve been exploring the use of vector databases to build Retrieval-Augmented Generation (RAG) applications, successfully implementing a setup with Milvus, Llama 3, Ollama, and LangChain. After obtaining a TiDB Cloud Serverless credit through an event, I decided to migrate the vector data from Milvus to TiDB Cloud Serverless.&lt;/p&gt;

&lt;p&gt;Upon researching, I discovered that existing migration tools currently do not support transferring data from Milvus to TiDB. However, this doesn’t mean migration is impossible. While existing tools do not facilitate this process, a manual migration is feasible. This article outlines my approach to achieving this.&lt;/p&gt;

&lt;p&gt;For more information about obtaining free TiDB Cloud Serverless credit, visit the &lt;a href="https://ossinsight.io/open-source-heroes/" rel="noopener noreferrer"&gt;event page&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Migration Plan
&lt;/h2&gt;

&lt;p&gt;To perform data migration, the first step is to determine the migration plan. The simplest migration consists of two steps: exporting data from the source database and importing it into the target database, thus completing the data migration.&lt;/p&gt;

&lt;p&gt;However, this case is different. The RAG application utilizes LangChain, and based on research, the structure created by LangChain in Milvus differs from that in TiDB.&lt;/p&gt;

&lt;p&gt;In Milvus, the collection name is: LangChainCollection, with the structure being:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F7fhro47tqah3dt4301w6.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F7fhro47tqah3dt4301w6.png" alt="Image description" width="625" height="777"&gt;&lt;/a&gt;&lt;br&gt;
However, in TiDB, the table name is &lt;strong&gt;langchain_vector&lt;/strong&gt;, and the structure is as follows:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbldkz7uxm87kg8q7txhg.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fbldkz7uxm87kg8q7txhg.png" alt="Image description" width="780" height="220"&gt;&lt;/a&gt;&lt;br&gt;
The documentation for LangChain also provides details:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmfd2mhyllnuampxtygth.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmfd2mhyllnuampxtygth.png" alt="Image description" width="800" height="382"&gt;&lt;/a&gt;&lt;br&gt;
Therefore, the data migration will require two additional steps: data preparation and table structure adjustment. Since these are heterogeneous databases, the exported data format chosen is the more universal CSV.&lt;/p&gt;

&lt;p&gt;The overall plan is as follows:&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdt1ro9tr1389b7fn0g5q.PNG" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdt1ro9tr1389b7fn0g5q.PNG" alt="Image description" width="800" height="83"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Exporting Data from Milvus
&lt;/h2&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import csv
from pymilvus import connections, Collection

# Connect to Milvus
connections.connect("default", host="10.3.xx.xx", port="19530")

# Get the Collection
collection = Collection("LangChainCollection")

# Paginate through all the data
limit = 1000
offset = 0
all_results = []

while True:
    # Pass expr parameter, using a simple condition to query all data
    results = collection.query(expr="", output_fields=["pk", "source", "page", "text", "vector"], limit=limit, offset=offset)
    if not results:
        break
    all_results.extend(results)
    offset += limit

# Open the CSV file, prepare to write data
with open("milvus_data.csv", "w", newline="", encoding='utf-8') as csvfile:
    # Define the CSV column names
    fieldnames = ["pk", "source", "page", "text", "vector"]
    writer = csv.DictWriter(csvfile, fieldnames=fieldnames)

    # Write the header
    writer.writeheader()

    # Write each record
    for result in all_results:
        # Parse JSON data and extract fields
        vector_str = ','.join(map(str, result.get("vector", [])))  # Convert the vector array to a string
        writer.writerow({
            "pk": result.get("pk"),          # Get the primary key
            "source": result.get("source"),  # Get the source file
            "page": result.get("page"),      # Get the page number
            "text": result.get("text"),      # Get the text
            "vector": vector_str             # Write the vector data
        })

print(f"Total records written to CSV: {len(all_results)}")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;The format of the exported CSV file data is as follows:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdzmkttndakc81zgeygjr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fdzmkttndakc81zgeygjr.png" alt="Image description" width="800" height="123"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Data Preparation and Table Structure Adjustment
&lt;/h2&gt;

&lt;p&gt;I converted a small amount of test data into vectors and used LangChain to load it into TiDB Cloud Serverless. This process facilitated obtaining the data structure and format within TiDB Cloud Serverless.&lt;/p&gt;

&lt;p&gt;The table structure is as follows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;CREATE TABLE `langchain_vector` (
`id` varchar(36) NOT NULL,
`embedding` vector(512) NOT NULL COMMENT 'hnsw(distance=cosine)',
`document` text DEFAULT NULL,
`meta` json DEFAULT NULL,
`create_time` datetime DEFAULT CURRENT_TIMESTAMP,
`update_time` datetime DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
PRIMARY KEY (`id`) /*T![clustered_index] CLUSTERED */
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The exported data format in CSV is as follows (partial content omitted):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;"id","embedding","document","meta","create_time","update_time"
"081574ec-b3e4-481b-b0c7-9a789080d160","[-0.4020949,-0.6850993,******,0.16776393,-0.049104385]","forecasting and disaster mitigation. The organization is committed to advancing scienti\0c\nknowledge and improving public safety and well-being through its work.\nFor further information, please contact:","{\"page\": 5, \"source\": \"./WMO report highlights growing shortfalls and stress in global water resources.pdf\"}","2024-10-22 02:41:49","2024-10-22 02:41:49"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Given the CSV file exported from Milvus, the relationship is clear: "embedding" corresponds to "vector," "document" corresponds to "text," and "meta" corresponds to "page" and "source." This logic clarifies the mapping. A data preparation script based on this relationship is as follows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import pandas as pd
import json
from uuid import uuid4
from datetime import datetime

# Read the CSV file
input_csv = 'milvus_data.csv'  # Replace with your CSV file name
df = pd.read_csv(input_csv)

# Create a new DataFrame
output_data = []

for _, row in df.iterrows():
    # Extract required fields
    id_value = str(uuid4())  # Generate a unique ID
    embedding = f"[{','.join(row['vector'].split(','))}]"  # Convert vector to embedding format
    document = row['text']

    # Generate meta information
    meta_dict = {"page": row['page'], "source": row['source']}
    meta = json.dumps(meta_dict, ensure_ascii=False)  # First generate standard JSON
    # meta = meta.replace('"', '\\"')  # Escape double quotes if needed

    create_time = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
    update_time = create_time  # Same time for update

    # Add to output data
    output_data.append({
        "id": id_value,
        "embedding": embedding,
        "document": document,
        "meta": meta,
        "create_time": create_time,
        "update_time": update_time
    })

# Convert to DataFrame
output_df = pd.DataFrame(output_data)

# Save as CSV file
output_csv = 'output.csv'  # Output file name
output_df.to_csv(output_csv, index=False, quoting=1)  # quoting=1 ensures strings are quoted

print(f"Conversion completed, saved as {output_csv}")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Once the data preparation is complete, the data can be imported into TiDB Cloud Serverless.&lt;/p&gt;

&lt;h2&gt;
  
  
  Importing Data to TiDB Cloud Serverless
&lt;/h2&gt;

&lt;p&gt;TiDB Cloud Serverless provides three import methods:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fhilwtsfjcudj06em4rg9.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fhilwtsfjcudj06em4rg9.png" alt="Image description" width="800" height="76"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In this case, we will use the "Upload a local file" method.&lt;br&gt;
CSV files smaller than 50 MiB can be uploaded using the first option for uploading local files. If the file exceeds 50 MiB, a script can be used to split the file into smaller chunks before uploading:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fj9hu7te7qd1t41sofwhn.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fj9hu7te7qd1t41sofwhn.png" alt="Image description" width="753" height="486"&gt;&lt;/a&gt;&lt;br&gt;
After uploading the file, select the previously created database and table, and click &lt;code&gt;define table&lt;/code&gt;:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frlhku5xprmdi6ygrhqtv.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frlhku5xprmdi6ygrhqtv.png" alt="Image description" width="732" height="507"&gt;&lt;/a&gt;&lt;br&gt;
Adjust the mappings as needed, then click &lt;code&gt;start import&lt;/code&gt;:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ffkdx2tshm3vh2b86od0y.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ffkdx2tshm3vh2b86od0y.png" alt="Image description" width="800" height="84"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;For more import methods, you can refer to the documentation: &lt;a href="https://docs.pingcap.com/tidbcloud/tidb-cloud-migration-overview" rel="noopener noreferrer"&gt;Migration and Import Overview&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;
  
  
  Validation of Results
&lt;/h2&gt;

&lt;p&gt;After successfully importing the data, the next step is to validate it. I modified the code for the RAG application to read vector data from both Milvus and TiDB. Using the same question, I queried the large model to return answers and checked whether the answers were similar.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;from langchain_community.llms import Ollama
from langchain.callbacks.manager import CallbackManager
from langchain.callbacks.streaming_stdout import StreamingStdOutCallbackHandler
from langchain import hub
from langchain.chains import RetrievalQA
from langchain.vectorstores.milvus import Milvus
from langchain_community.embeddings.jina import JinaEmbeddings
from langchain_community.vectorstores import TiDBVectorStore
import os

llm = Ollama(
model="llama3",
callback_manager=CallbackManager([StreamingStdOutCallbackHandler()]
),
stop=["&amp;lt;|eot_id|&amp;gt;"],
)


embeddings = JinaEmbeddings(jina_api_key="xxxx", model_name="jina-embeddings-v2-small-en")

vector_store_milvus = Milvus(
    embedding_function=embeddings,
    connection_args={"uri": "http://10.3.xx.xx:19530"},
)


TIDB_CONN_STR="mysql+pymysql://xxxx.root:password@host:4000/test?ssl_ca=/Downloads/isrgrootx1.pem&amp;amp;ssl_verify_cert=true&amp;amp;ssl_verify_identity=true"
vector_store_tidb = TiDBVectorStore(
    connection_string=TIDB_CONN_STR,
    embedding_function=embeddings,
    table_name="langchain_vector",
)


os.environ["LANGCHAIN_API_KEY"] = "xxxx"
query = input("\nQuery: ")
prompt = hub.pull("rlm/rag-prompt")   

qa_chain = RetrievalQA.from_chain_type(
    llm, retriever=vector_store_milvus.as_retriever(), chain_type_kwargs={"prompt": prompt}
)
print("milvus")
result = qa_chain({"query": query})

print("\n--------------------------------------")
print("tidb")
qa_chain = RetrievalQA.from_chain_type(
    llm, retriever=vector_store_tidb.as_retriever(), chain_type_kwargs={"prompt": prompt}
)
result = qa_chain({"query": query})
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The connection string for TiDB can be obtained directly from TiDB Cloud Serverless:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F13zk38io7e97f0s701yr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F13zk38io7e97f0s701yr.png" alt="Image description" width="733" height="667"&gt;&lt;/a&gt;&lt;br&gt;
After posing the question to the RAG application and reviewing the responses, I found that the answers from Milvus and TiDB were essentially consistent, indicating that the vector migration was successful. It is also advisable to compare the number of data entries in Milvus and TiDB tables; if they match, the migration should be considered successful.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Faz6wqeuhuz6jyj8snlwe.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Faz6wqeuhuz6jyj8snlwe.png" alt="Image description" width="800" height="142"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Summary
&lt;/h2&gt;

&lt;p&gt;Data migration between different databases is fundamentally about converting the data into a universal format that all databases can recognize, including vector data. This migration from Milvus to TiDB Cloud Serverless differs from traditional relational database migrations. Although the RAG application utilizes LangChain, the table structures and data formats created by LangChain vary across different databases. Therefore, additional organization of the data and table structures is required to successfully migrate to the target database. Fortunately, TiDB Cloud Serverless offers various convenient data import methods, making the migration process relatively straightforward.&lt;/p&gt;

</description>
      <category>database</category>
      <category>vectordatabase</category>
      <category>tutorial</category>
      <category>opensource</category>
    </item>
    <item>
      <title>TiDB Future App Hackathon 2024</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Fri, 19 Jul 2024 08:49:32 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/tidb-future-app-hackathon-2024-3pab</link>
      <guid>https://dev.to/tidbcommunity/tidb-future-app-hackathon-2024-3pab</guid>
      <description>&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fghof9f6t071u8zhmbyvf.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fghof9f6t071u8zhmbyvf.png" alt="banner" width="800" height="266"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;We’re excited to announce another edition of &lt;a href="https://tidbhackathon2024.devpost.com/?utm_source=devto&amp;amp;utm_medium=social&amp;amp;utm_campaign=blog_hackathon" rel="noopener noreferrer"&gt;TiDB Future App Hackathon&lt;/a&gt;!  Our first Hackathon last year was an amazing success with almost 1,500 participants from 87 countries (see the &lt;a href="https://www.pingcap.com/blog/celebrating-the-successful-tidb-future-app-hackathon-2023" rel="noopener noreferrer"&gt;recap blog&lt;/a&gt; for more details) and we’re looking forward to an even bigger event this year.&lt;/p&gt;

&lt;p&gt;Similar to last year, we will have over $US 30k in prizes, and beyond prizes, we want the Hackathon to provide opportunities for participants to expand your network and work with like-minded developers while working with the latest technologies. &lt;/p&gt;

&lt;h2&gt;
  
  
  What’s New This Year
&lt;/h2&gt;

&lt;p&gt;During this year’s Hackathon, participants will have an opportunity to develop new applications leveraging the new &lt;a href="https://www.pingcap.com/ai/?utm_source=owned_event&amp;amp;utm_medium=virtual_event&amp;amp;utm_campaign=hackathon24_05_cm_p1_devto" rel="noopener noreferrer"&gt;Vector Search feature on TiDB Serverless&lt;/a&gt;.  We have seen amazing growth in AI and Machine Learning applications over the past few years, and we’re excited to see what TiDB community members will build to leverage our new Vector Search feature. &lt;/p&gt;

&lt;h2&gt;
  
  
  What to Create
&lt;/h2&gt;

&lt;p&gt;With TiDB Serverless, the possibilities are endless for creating an innovative AI Application. To help you kickstart AI your project, we've identified a few categories you might consider.&lt;br&gt;
Remember, these are just a few ideas to spark your imagination – the sky's the limit!&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://ask.pingcap.com/t/sample-applications-built-with-tidb-serverless-tidb-hackathon-2024/938" rel="noopener noreferrer"&gt;Sample applications&lt;/a&gt; built with TiDB Serverless&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fx0n2p27mzgj0ll4knnkz.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fx0n2p27mzgj0ll4knnkz.jpg" alt="Hackathon Idea" width="800" height="596"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If you have any questions during the Hackathon, you can drop in on our HACKATHON 2024 channels on our &lt;a href="https://discord.gg/A3Ue27s7rD" rel="noopener noreferrer"&gt;Discord&lt;/a&gt;. Join us today by registering on our &lt;a href="https://tidbhackathon2024.devpost.com/?utm_source=devto&amp;amp;utm_medium=social&amp;amp;utm_campaign=blog_hackathon" rel="noopener noreferrer"&gt;Hackathon site&lt;/a&gt; for a chance to be one of the winners of more than $30k in prizes! &lt;/p&gt;

</description>
      <category>hackathon</category>
      <category>ai</category>
      <category>vectorsearch</category>
      <category>rag</category>
    </item>
    <item>
      <title>Easy Local Development with TiDB</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Mon, 25 Sep 2023 06:42:32 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/easy-local-development-with-tidb-41h6</link>
      <guid>https://dev.to/tidbcommunity/easy-local-development-with-tidb-41h6</guid>
      <description>&lt;p&gt;This article is written by Daniël Van Eeden.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Here’s how TiDB can help you develop your application locally using the same type of distributed database platform used in production.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;When you develop an application, you begin by coding and testing in your local environment. Many applications interface with a database, so in this early stage, you might use SQLite rather than the database brand used in production. This is an issue, however, because ideally, you want to develop the application with the production database in mind.&lt;/p&gt;

&lt;p&gt;When using a distributed system setting up and starting/stopping the components needed for this can become error-prone and time-consuming.&lt;/p&gt;

&lt;p&gt;In this article, I’ll explain how you can develop your application locally and use the type of database used in production. In this case, &lt;a href="https://docs.pingcap.com/tidb/stable" rel="noopener noreferrer"&gt;TiDB&lt;/a&gt;, a distributed SQL database platform that features horizontal scalability, strong consistency, and high availability, is an excellent choice.&lt;/p&gt;

&lt;h2&gt;
  
  
  A Quick Overview Of TiDB
&lt;/h2&gt;

&lt;p&gt;TiDB is a relational database that is compatible with the MySQL protocol and syntax and can easily scale beyond a single machine by dividing the data over multiple machines. This also makes it resilient to machine failures.&lt;/p&gt;

&lt;p&gt;If you have seen pictures of the &lt;a href="https://docs.pingcap.com/tidb/stable/tidb-architecture" rel="noopener noreferrer"&gt;TiDB architecture&lt;/a&gt;, you know that it consists of many components, including the TiDB server, TiKV, a transaction, key-value database, and the Placement Driver (PD), which manages metadata. For a production setup, you’ll need multiple instances of each component.&lt;/p&gt;

&lt;p&gt;A scalable, highly available distributed system like TiDB runs multiple components on multiple hosts. For production setups, this is not a problem as there are good tools to manage this: TiDB Operator for Kubernetes and &lt;a href="https://docs.pingcap.com/tidb/stable/tiup-component-cluster" rel="noopener noreferrer"&gt;TiUP Cluster&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;When you develop and test your work, you may have a cluster that has a similar setup as production. However, if you want to test against new versions of TiDB or if your development interferes with what other developers are doing, this may not work. Also, if you are traveling you may not have an internet connection or have an unreliable connection.&lt;/p&gt;

&lt;p&gt;Setting up a local copy of a distributed system can be a complex task because there are multiple components and there also might be OS settings to manage. Also, running multiple instances of a component can easily result in conflicts on TCP ports or filesystem paths.&lt;/p&gt;

&lt;p&gt;Another good use of a local cluster is to test certain operations before doing them in production. This includes learning basic tasks like upgrading your application and backing and restoring the database.&lt;/p&gt;

&lt;p&gt;So let’s look into some of the options for local development. Some of these can also be used for CI jobs where you need a database.&lt;/p&gt;

&lt;h2&gt;
  
  
  Install TiUP and Start a TiDB Playground
&lt;/h2&gt;

&lt;p&gt;TiUP is the tool to use to manage TiDB installations, both in production and for local development. One of the things TiUP can do is to set up a playground, with this TiUP will download the components that you need and configure and start them so that you get a local environment. This works on macOS, Linux, and Windows with WSL.&lt;/p&gt;

&lt;p&gt;The playground gives you a TiDB installation to work with including the TiDB Dashboard and a set of Grafana dashboards.&lt;/p&gt;

&lt;p&gt;To install TiUP run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;curl --proto '=https' --tlsv1.2 -sSf https://tiup-mirrors.pingcap.com/install.sh | sh
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Once TiUP is installed you can start a playground:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;tiup playground
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These steps are available on &lt;a href="https://tiup.io" rel="noopener noreferrer"&gt;https://tiup.io&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;In the output of the &lt;code&gt;tiup playground&lt;/code&gt; command, shown above, you can see the information about how to connect to the playground with a MySQL client and also the URLs for the TiDB Dashboard and Grafana.&lt;/p&gt;

&lt;p&gt;Additional tips for working with playgrounds:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;You can specify the version you want to run with &lt;code&gt;tiup playground v4.0.14&lt;/code&gt; for example.&lt;/li&gt;
&lt;li&gt;With &lt;code&gt;tiup -T myapp playground&lt;/code&gt; you can put a nametag on the playground. This is useful when you use multiple playgrounds. This also allows you to more easily find the data directory of the playground to inspect the logs etc. For example, with the “myapp” tag you can find the datadir on &lt;code&gt;~/.tiup/data/myapp&lt;/code&gt;with subdirectories for the various components. Setting a tag also lets you keep the data after stopping the playground.&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;tiup playground&lt;/code&gt; command has options to set the number of instances per component. This can be used to set the number of TiFlash instances to 0 in case you for example don’t intend to use the HTAP functionality.&lt;/li&gt;
&lt;li&gt;You can add &lt;code&gt;--monitor=false&lt;/code&gt; if you don’t want to use monitoring tools like Grafana and Prometheus. This is useful if you want to save resources on your local machine.
## TiDE: A Visual Studio Code Extension for TiDB
If you use Visual Studio Code, the &lt;a href="https://marketplace.visualstudio.com/items?itemName=dragonly.ticode" rel="noopener noreferrer"&gt;TiDE&lt;/a&gt; extension lets you work with TiUP Playground, TiUP clusters, and Kubernetes clusters right from your IDE.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This extension gives you a Ti icon on the sidebar of VS Code. If you click this icon you get presented with options for starting a playground and an overview of any running playgrounds. TiDE also supports clusters deployed with TiUP, vagrant, and TiDB Operator for Kubernetes. Besides starting and stopping playgrounds you can also use this to inspect the logs, change the configuration of components, and open a MySQL client session right in the terminal pane of VS Code.&lt;/p&gt;

&lt;h2&gt;
  
  
  Set Up Your Containers With Docker Compose
&lt;/h2&gt;

&lt;p&gt;Use &lt;a href="https://github.com/pingcap/tidb-docker-compose" rel="noopener noreferrer"&gt;TiDB Docker Compose&lt;/a&gt; to set up your containers. This is a useful tool if you already use Docker Compose to manage the containers of the application you are developing.&lt;/p&gt;

&lt;p&gt;To set up a set of containers with this tool run the following:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fj3tf1pnf0hdbvc5qh8j4.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fj3tf1pnf0hdbvc5qh8j4.png" alt="Image description" width="690" height="137"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Now you can connect with a MySQL client:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwd27em3qz2aloxdmxr3p.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwd27em3qz2aloxdmxr3p.png" alt="Image description" width="690" height="94"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Use TiDB Operator With Minikube or Kind
&lt;/h2&gt;

&lt;p&gt;If you run TiDB on Kubernetes in production, a good option is to use minikube or kind for local development. This approach teaches you how to work with TiDB Operator. For detailed information on setting up TiDB Operator, see &lt;a href="https://docs.pingcap.com/tidb-in-kubernetes/stable/get-started" rel="noopener noreferrer"&gt;Getting Started with TiDB Operator on Kubernetes.&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  A Simple Option: Run a Single TiDB Instance
&lt;/h2&gt;

&lt;p&gt;You can run one instance of TiDB server without TiKV, Placement Driver, TiFlash, or any of the other components. In this case, TiDB uses unistore, a local storage engine, as a backend instead of TiKV. By default, TiDB stores data in /tmp/tidb. For TiDB server you only need a single binary, so this makes deployment easy. However, this approach is quite limited: you won’t have access to TiDB Dashboard, Grafana, or TiFlash.&lt;/p&gt;

&lt;p&gt;To download, extract, and start TiDB server, enter:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;wget -q -O - https://download.pingcap.org/tidb-v5.1.1-linux-amd64.tar.gz | tar --strip-components 2 -zxf - tidb-v5.1.1-linux-amd64/bin/tidb-server
./tidb-server`
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;Having a complex distributed system doesn’t need to prevent you from doing local development in the way that fits your needs. There are multiple methods to set up local development environments.&lt;/p&gt;

&lt;p&gt;Ready to supercharge your data integration with TiDB? Join our Discord community now! Connect with fellow data enthusiasts, developers, and experts too: Stay Informed: Get the latest updates, tips, and tricks for optimizing your data integration. Ask Questions: Seek assistance and share your knowledge with our supportive community. Collaborate: Exchange experiences and insights with like-minded professionals. Access Resources: Unlock exclusive guides and tutorials to turbocharge your data projects. &lt;a href="https://discord.com/invite/ukhXbn69Nx?utm_source=article" rel="noopener noreferrer"&gt;Join us&lt;/a&gt; today and take your data integration to the next level with TiDB!&lt;/p&gt;

</description>
    </item>
    <item>
      <title>How to load data from Slack to TiDB</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Mon, 11 Sep 2023 10:06:00 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/how-to-load-data-from-slack-to-tidb-1e8c</link>
      <guid>https://dev.to/tidbcommunity/how-to-load-data-from-slack-to-tidb-1e8c</guid>
      <description>&lt;h2&gt;
  
  
  TL;DR
&lt;/h2&gt;

&lt;p&gt;This can be done by building a data pipeline manually, usually a Python script (you can leverage a tool as Apache Airflow for this). This process can take more than a full week of development. Or it can be done in minutes on Airbyte in three easy steps:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;set up Slack as a source connector (using Auth, or usually an API key)&lt;/li&gt;
&lt;li&gt;set up TiDB as a destination connector&lt;/li&gt;
&lt;li&gt;define which data you want to transfer and how frequently&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;You can choose to self-host the pipeline using Airbyte Open Source or have it managed for you with Airbyte Cloud.&lt;/p&gt;

&lt;p&gt;This tutorial’s purpose is to show you how.&lt;/p&gt;

&lt;h2&gt;
  
  
  What is Slack
&lt;/h2&gt;

&lt;p&gt;Slack is an enterprise software platform that facilitates global communication between all sizes of businesses and teams. Slack enables collaborative work to be more efficient and more productive, making it possible for businesses to connect with immediacy from half a world apart. It allows teams to work together in concert, almost as if they were in the same room. Slack transforms the process of communication, bringing it into the 21st century with powerful style.&lt;/p&gt;

&lt;h2&gt;
  
  
  What is TiDB
&lt;/h2&gt;

&lt;p&gt;TiDB is a distributed SQL database that is designed to handle large-scale online transaction processing (OLTP) and online analytical processing (OLAP) workloads. It is an open-source, cloud-native database that is built to be highly available, scalable, and fault-tolerant. TiDB uses a distributed architecture that allows it to scale horizontally across multiple nodes, while also providing strong consistency guarantees. It supports SQL and offers compatibility with MySQL, which makes it easy for developers to migrate their existing applications to TiDB. TiDB is used by companies such as Didi Chuxing, Mobike, and Meituan-Dianping to power their mission-critical applications.&lt;/p&gt;

&lt;h2&gt;
  
  
  Prerequisites
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;A Slack account to transfer your customer data automatically from.&lt;/li&gt;
&lt;li&gt;A TiDB account.&lt;/li&gt;
&lt;li&gt;An active Airbyte Cloud account, or you can also choose to use Airbyte Open Source locally. You can follow the instructions to set up Airbyte on your system using docker-compose.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Airbyte is an open-source data integration platform that consolidates and streamlines the process of extracting and loading data from multiple data sources to data warehouses. It offers pre-built connectors, including Slack and TiDB, for seamless data migration.&lt;/p&gt;

&lt;p&gt;When using Airbyte to move data from Slack to TiDB, it extracts data from Slack using the source connector, converts it into a format TiDB can ingest using the provided schema, and then loads it into TiDB via the destination connector. This allows businesses to leverage their Slack data for advanced analytics and insights within TiDB, simplifying the ETL process and saving significant time and resources.&lt;/p&gt;

&lt;h2&gt;
  
  
  Step 1: Set up Slack as a source connector
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;First, navigate to the Slack source connector page on Airbyte.com.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Click on the "Add Source" button to begin the process of adding your Slack credentials.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;In the "Connection Configuration" section, enter a name for your Slack connection.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Next, enter your Slack workspace's API token in the "API Token" field. You can generate an API token by following the instructions in the Airbyte documentation.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;In the "Channels" field, enter the names of the Slack channels you want to sync data from. You can enter multiple channels by separating them with commas.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;If you want to filter the data that is synced from Slack, you can enter a date range in the "Start Date" and "End Date" fields.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Once you have entered all the necessary information, click on the "Test" button to ensure that your credentials are valid and that Airbyte can connect to your Slack workspace.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;If the test is successful, click on the "Save &amp;amp; Continue" button to save your Slack connection.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;You can now use your Slack source connector to sync data from your Slack workspace to your destination of choice.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Step 2: Set up TiDB as a destination connector
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;First, navigate to the Airbyte website and log in to your account.&lt;/li&gt;
&lt;li&gt;Once you are logged in, click on the "Destinations" tab on the left-hand side of the screen.&lt;/li&gt;
&lt;li&gt;Scroll down until you find the TiDB destination connector and click on it.&lt;/li&gt;
&lt;li&gt;You will be prompted to enter your TiDB database credentials, including the host, port, username, and password.&lt;/li&gt;
&lt;li&gt;Once you have entered your credentials, click on the "Test" button to ensure that the connection is successful.&lt;/li&gt;
&lt;li&gt;If the test is successful, click on the "Save" button to save your TiDB destination connector settings.&lt;/li&gt;
&lt;li&gt;You can now use the TiDB destination connector to transfer data from your source connectors to your TiDB database.&lt;/li&gt;
&lt;li&gt;To set up a data integration pipeline, navigate to the "Connections" tab on the left-hand side of the screen and create a new connection.&lt;/li&gt;
&lt;li&gt;Select your TiDB destination connector as the destination and choose your source connector as the source.&lt;/li&gt;
&lt;li&gt;Configure the settings for your data integration pipeline, including the frequency of data transfers and any data transformations that you want to apply.&lt;/li&gt;
&lt;li&gt;Once you have configured your data integration pipeline, click on the "Save" button to save your settings.&lt;/li&gt;
&lt;li&gt;Your data integration pipeline will now run automatically, transferring data from your source connectors to your TiDB database on a regular basis.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Step 3: Set up a connection to sync your Slack data to TiDB
&lt;/h2&gt;

&lt;p&gt;Once you've successfully connected Slack as a data source and TiDB as a destination in Airbyte, you can set up a data pipeline between them with the following steps:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Create a new connection: On the Airbyte dashboard, navigate to the 'Connections' tab and click the '+ New Connection' button.&lt;/li&gt;
&lt;li&gt;Choose your source: Select Slack from the dropdown list of your configured sources.&lt;/li&gt;
&lt;li&gt;Select your destination: Choose TiDB from the dropdown list of your configured destinations.&lt;/li&gt;
&lt;li&gt;Configure your sync: Define the frequency of your data syncs based on your business needs. Airbyte allows both manual and automatic scheduling for your data refreshes.&lt;/li&gt;
&lt;li&gt;Select the data to sync: Choose the specific Slack objects you want to import data from towards TiDB. You can sync all data or select specific tables and fields.&lt;/li&gt;
&lt;li&gt;Select the sync mode for your streams: Choose between full refreshes or incremental syncs (with deduplication if you want), and this for all streams or at the stream level. Incremental is only available for streams that have a primary cursor.&lt;/li&gt;
&lt;li&gt;Test your connection: Click the 'Test Connection' button to make sure that your setup works. If the connection test is successful, save your configuration.&lt;/li&gt;
&lt;li&gt;Start the sync: If the test passes, click 'Set Up Connection'. Airbyte will start moving data from Slack to TiDB according to your settings.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Remember, Airbyte keeps your data in sync at the frequency you determine, ensuring your TiDB data warehouse is always up-to-date with your Slack data.&lt;/p&gt;

&lt;h2&gt;
  
  
  Use Cases to transfer your Slack data to TiDB
&lt;/h2&gt;

&lt;p&gt;Integrating data from Slack to TiDB provides several benefits. Here are a few use cases:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Advanced Analytics&lt;/strong&gt;: TiDB’s powerful data processing capabilities enable you to perform complex queries and data analysis on your Slack data, extracting insights that wouldn't be possible within Slack alone.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Data Consolidation&lt;/strong&gt;: If you're using multiple other sources along with Slack, syncing to TiDB allows you to centralize your data for a holistic view of your operations&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Historical Data Analysis&lt;/strong&gt;: Slack has limits on historical data. Syncing data to TiDB allows for long-term data retention and analysis of historical trends over time.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Data Security and Compliance&lt;/strong&gt;: TiDB provides robust data security features. Syncing Slack data to TiDB ensures your data is secured and allows for advanced data governance and compliance management.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Scalability&lt;/strong&gt;: TiDB can handle large volumes of data without affecting performance, providing an ideal solution for growing businesses with expanding Slack data.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Data Science and Machine Learning&lt;/strong&gt;: By having Slack data in TiDB, you can apply machine learning models to your data for predictive analytics, customer segmentation, and more.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Reporting and Visualization&lt;/strong&gt;: While Slack provides reporting tools, data visualization tools like Tableau, PowerBI, Looker (Google Data Studio) can connect to TiDB, providing more advanced business intelligence options.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Wrapping Up
&lt;/h2&gt;

&lt;p&gt;To summarize, this tutorial has shown you how to:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Configure a Slack account as an Airbyte data source connector.&lt;/li&gt;
&lt;li&gt;Configure TiDB as a data destination connector.&lt;/li&gt;
&lt;li&gt;Create an Airbyte data pipeline that will automatically be moving data directly from Slack to TiDB after you set a schedule&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Ready to supercharge your data integration with TiDB? Join our Discord community now! Connect with fellow data enthusiasts, developers, and experts too: Stay Informed: Get the latest updates, tips, and tricks for optimizing your data integration. Ask Questions: Seek assistance and share your knowledge with our supportive community. Collaborate: Exchange experiences and insights with like-minded professionals. Access Resources: Unlock exclusive guides and tutorials to turbocharge your data projects. &lt;a href="https://discord.com/invite/ukhXbn69Nx?utm_source=article" rel="noopener noreferrer"&gt;Join us&lt;/a&gt; today and take your data integration to the next level with TiDB!&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Building AI Applications: Real-World Stories and Insights for Finding an Ideal Tech Stack</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Fri, 08 Sep 2023 03:55:30 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/building-ai-applications-real-world-stories-and-insights-for-finding-an-ideal-tech-stack-4f60</link>
      <guid>https://dev.to/tidbcommunity/building-ai-applications-real-world-stories-and-insights-for-finding-an-ideal-tech-stack-4f60</guid>
      <description>&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fiap320yghi1y9sowaw00.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fiap320yghi1y9sowaw00.png" alt="Image description" width="800" height="400"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fn6c8dyp26f6bt8cyqsda.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fn6c8dyp26f6bt8cyqsda.png" alt="Image description" width="800" height="266"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Have you ever marveled at the far-reaching impact of AI in various domains? Now, it’s your turn to turn your AI ideas into reality. The champions of TiDB Future App Hackathon 2023, true pioneers in the AI landscape, are eager to share their remarkable journey, the hurdles they conquered, and the profound insights they’ve gained while crafting AI-native applications. Their story of humble beginnings and relentless innovation is sure to inspire and guide you on your own AI journey.&lt;/p&gt;

&lt;p&gt;📅 Date: September 27th&lt;/p&gt;

&lt;p&gt;⏰ Time: 11:00-12:00 AM SGT&lt;/p&gt;

&lt;p&gt;📍 Location: Virtual Meetup on Zoom&lt;/p&gt;

&lt;h2&gt;
  
  
  What to Expect:
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Winning Insights (15 mins)&lt;/strong&gt;: Uncover the secrets behind crafting award-winning AI applications from industry leaders.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;AI Innovation and Challenges (20 mins)&lt;/strong&gt;: Explore how AI is reshaping application development, offering inspiration for startups and individual developers.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Future AI Trends (20 mins)&lt;/strong&gt;: Dive into the future of AI applications and discover the next-gen data infrastructure for AI-driven innovation.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Exclusive Benefits Await (5 mins)&lt;/strong&gt;: Learn about our special offers, starting free and staying that way until your business achieves success. Stick around till the end for surprises!
## Meet Our Esteemed Speakers:&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F6j0p5q2dbbld9eyzo11a.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F6j0p5q2dbbld9eyzo11a.jpeg" alt="Image description" width="724" height="1000"&gt;&lt;/a&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>developer</category>
      <category>programming</category>
      <category>techtalks</category>
    </item>
    <item>
      <title>Announcing the Winners of the TiDB Future App Hackathon 2023!</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Thu, 31 Aug 2023 09:03:51 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/announcing-the-winners-of-the-tidb-future-app-hackathon-2023-27b7</link>
      <guid>https://dev.to/tidbcommunity/announcing-the-winners-of-the-tidb-future-app-hackathon-2023-27b7</guid>
      <description>&lt;p&gt;Drumroll, please! We are absolutely ecstatic to unveil the winners of the TiDB Future App Hackathon 2023! This extraordinary event brought together 1492 participants hailing from 88 countries, who unleashed their creativity and showcased their ingenuity in 100 projects.&lt;/p&gt;

&lt;p&gt;Throughout the hackathon, participants used the opportunity to harness the power of TiDB Serverless. With $36,000 of the prize pool at stake, the competition was fierce and we were impressed with the number of innovative projects that were submitted. Without further ado, we’re excited to unveil the Hackathon prize winners&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fgxyy5gerwnpw5huj486t.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fgxyy5gerwnpw5huj486t.jpeg" alt="Image description" width="800" height="450"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  1st Place:$13,500 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;a href="https://tidbhackathon2023.devpost.com/submissions/423558-convex-ai" rel="noopener noreferrer"&gt;Convex AI &lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Less Coding, More Thinking. Generate Productivity App, not beautiful junk.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  2nd Place:$7,500 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;a href="https://tidbhackathon2023.devpost.com/submissions/419840-quizmefy" rel="noopener noreferrer"&gt;Quizmefy &lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: An AI powered multiplayer trivia game. Our platform is revolutionizing the quiz and trivia experience by harnessing the immense potential of artificial intelligence&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  3rd Place: $3,500 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;a href="https://tidbhackathon2023.devpost.com/submissions/422256-heuristic-ai" rel="noopener noreferrer"&gt;Heuristic AI&lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Heuristic AI is a search management system that creates search pages for products. The tool allows companies to have fast and efficient direct insights into their consumers’ issues thanks to TiFlash.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  4th - 7th Place: $1,500 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  4th Place: &lt;a href="https://tidbhackathon2023.devpost.com/submissions/420616-ai-mon-artificial-intelligence-activity-observability" rel="noopener noreferrer"&gt;AI-Mon: Artificial Intelligence Activity Observability&lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: AI-Mon(aka. AI Monitoring) is an advanced successor to Ira (Now a browser extension OSS to record cut/copy/paste events on websites) especially to monitor data with the popularity of AI-driven chatbots&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  5th Place: &lt;a href="https://tidbhackathon2023.devpost.com/submissions/421394-moyubie" rel="noopener noreferrer"&gt;moyubie&lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Talk to AI and your friends in private, and get ads free news feeds!&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  6th Place: &lt;a href="https://tidbhackathon2023.devpost.com/submissions/420701-briefly" rel="noopener noreferrer"&gt;Briefly &lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Never miss a beat in Slack&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  7th Place: &lt;a href="https://tidbhackathon2023.devpost.com/submissions/423739-comant" rel="noopener noreferrer"&gt;Comant &lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Comant is a digital physical disability and speech difficulties assistant, which allows users to effectively communicate with anyone using eye tracking with advanced AI technologies powered by TiDB.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Vercel | Best User Experience Award:$1500 in usage credit to the Vercel platform.
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;a href="https://tidbhackathon2023.devpost.com/submissions/419840-quizmefy" rel="noopener noreferrer"&gt;Quizmefy &lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: An AI powered multiplayer trivia game. Our platform is revolutionizing the quiz and trivia experience by harnessing the immense potential of artificial intelligence.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Best AI Application Award: $1,500 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;a href="https://tidbhackathon2023.devpost.com/submissions/423882-hacker-jobs" rel="noopener noreferrer"&gt;Hacker Jobs &lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Hacker Jobs: Your one-stop platform for tech job seekers. Leverage TiDB analytics on Hacker News data, making job search fast and efficient!&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Prize for Social Good:$1,500 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;a href="https://tidbhackathon2023.devpost.com/submissions/423739-comant" rel="noopener noreferrer"&gt;Comant&lt;/a&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Project Description: Comant is a digital physical disability and speech difficulties assistant, which allows users to effectively communicate with anyone using eye tracking with advanced AI technologies powered by TiDB.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Finalist Prize (60): Each of the 60 finalists will receive a TiDB Hackathon Swag.
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fo7ttwnsclywjkoh4era2.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fo7ttwnsclywjkoh4era2.png" alt="Image description" width="800" height="328"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Incentive Awards: Top 5 Idea-makers with the most votes:$100 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  TOP 1 : &lt;a href="https://discord.com/channels/1083300679386406923/1130984878561820672" rel="noopener noreferrer"&gt;Bit size learning platform, use GPT to generate and explain complex modules and topics.&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Winner: LyonKvalid&lt;/p&gt;

&lt;p&gt;Votes: 20&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 2: &lt;a href="https://discord.com/channels/1083300679386406923/1123271883131990056" rel="noopener noreferrer"&gt;bebrah - for modern creators&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Winner: mzir0&lt;br&gt;
Votes: 19&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 3: &lt;a href="https://discord.com/channels/1083300679386406923/1126111239785947136" rel="noopener noreferrer"&gt;UFO/UAP Sightings Database and Reporting System 1&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Winner: Mike&lt;br&gt;
Votes:17&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 4： &lt;a href="https://discord.com/channels/1083300679386406923/1127084503811248159" rel="noopener noreferrer"&gt;Spam-Jam&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Winner: Deepak_09&lt;br&gt;
Votes:17&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 5： &lt;a href="https://discord.com/channels/1083300679386406923/1125514147749175346" rel="noopener noreferrer"&gt;AI-Powered Cybersecurity and Translation Bot&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Winner: ChickenMcSwag&lt;br&gt;
Votes:15&lt;/p&gt;

&lt;h2&gt;
  
  
  Incentive Awards: Top 5 Story-tellers with the most votes:$100 USD
&lt;/h2&gt;

&lt;h3&gt;
  
  
  TOP 1: &lt;a href="https://discord.com/channels/1083300679386406923/1134636250490482889" rel="noopener noreferrer"&gt;Once upon a time, there are three engineers…&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Votes:21&lt;br&gt;
Winner: Alez&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 2: &lt;a href="https://discord.com/channels/1083300679386406923/1126025776802844712" rel="noopener noreferrer"&gt;In my first hackathon, my family thought I was working with terrorists.&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Votes:18&lt;/p&gt;

&lt;p&gt;Winner: Deepak_09&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 3: &lt;a href="https://discord.com/channels/1083300679386406923/1138482090195812393" rel="noopener noreferrer"&gt;Mad teenager designing sth at 4 AM…?&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Votes:15&lt;/p&gt;

&lt;p&gt;Winner: mzir0&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 4: &lt;a href="https://discord.com/channels/1083300679386406923/1135012466573713449" rel="noopener noreferrer"&gt;How I went through fire but didn’t get burnt during TiDB Hackathon&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Votes: 11&lt;/p&gt;

&lt;p&gt;Winner: Lucky Victory&lt;/p&gt;

&lt;h3&gt;
  
  
  TOP 5: &lt;a href="https://discord.com/channels/1083300679386406923/1130460122787872798" rel="noopener noreferrer"&gt;First Hackathon I really put a lot of effort in&lt;/a&gt;
&lt;/h3&gt;

&lt;p&gt;Votes: 11&lt;/p&gt;

&lt;p&gt;Winner: Nifemi&lt;/p&gt;

&lt;p&gt;&lt;a href="https://tidbhackathon2023.devpost.com/project-gallery" rel="noopener noreferrer"&gt;More project&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Once again, a tremendous thank you to all the participants for your enthusiasm and for making this hackathon a great success. The level of talent and innovation showcased throughout the competition was truly impressive. Your commitment to excellence and passion for technology is inspiring.&lt;/p&gt;

&lt;p&gt;We hold hackathon competitions every year, and we would be thrilled to have you participate next year and beyond. Be on the look out for announcements including on our &lt;a href="https://discord.com/invite/vYU9h56kAX" rel="noopener noreferrer"&gt;Discord&lt;/a&gt;) that we used during the recent Hackathon. It’s also a wonderful platform for exchanging thoughts, ideas, and knowledge with like-minded individuals who share a passion for technology and innovation.&lt;/p&gt;

</description>
      <category>hackathon</category>
      <category>tidb</category>
      <category>developer</category>
      <category>ai</category>
    </item>
    <item>
      <title>Some Attempts to Optimize the Accuracy of TiDB Bot Responses</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Wed, 02 Aug 2023 22:58:39 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/some-attempts-to-optimize-the-accuracy-of-tidb-bot-responses-3ghp</link>
      <guid>https://dev.to/tidbcommunity/some-attempts-to-optimize-the-accuracy-of-tidb-bot-responses-3ghp</guid>
      <description>&lt;p&gt;About the Author: Li Li, Product Manager at PingCAP.&lt;/p&gt;

&lt;h2&gt;
  
  
  TL;DR
&lt;/h2&gt;

&lt;p&gt;This article introduces how to optimize the accuracy of the enterprise-exclusive knowledge base user assistant robot, TiDB Bot, solving problems such as “incorrect toxicity detection”, “misunderstanding of context”, “erroneous semantic search results”, and “insufficient or outdated documentation”. In addition, an internal operation platform was established to continuously iterate the TiDB Bot. Ultimately, the continuous operation method optimized over 50% of the dislike rate to less than 5%.&lt;/p&gt;

&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;Based on the method of &lt;a href="https://ask.pingcap.com/t/building-a-company-specific-user-assistance-robot-with-generative-ai/633" rel="noopener noreferrer"&gt;Building a Company-specific User Assistance Robot&lt;/a&gt; with Generative AI, I have constructed TiDB Bot, a robot that answers customer questions based on TiDB and TiDB Cloud's official documentation, and is capable of refusing to answer questions outside of its scope of business. &lt;br&gt;
However, upon its initial launch, the response was less than satisfactory, with over 50% of users providing dislike feedback.&lt;/p&gt;

&lt;h2&gt;
  
  
  Issues During Internal Testing
&lt;/h2&gt;

&lt;p&gt;In order to investigate the existing problems, I conducted tests and discovered the following categories in dialogues where issues arise:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Incorrect toxicity detection: Some questions related to the company's business are refused, for instance, 'dumpling' is a data export tool for TiDB, but when directly asking 'what is dumpling?', the robot refuses to answer and advises you to consult a food expert instead. &lt;/li&gt;
&lt;li&gt;Incorrect understanding of context: When multi-round dialogues occur, users usually ask questions about the previous content. At this point, a simple description like 'what is the default value for this parameter?' is provided. When searching for semantically related content from the vector database, simply using the user's original text for search usually yields no meaningful results. This causes the problem that when it is passed to GPT, it is unable to provide the correct answer based on the official documentation.&lt;/li&gt;
&lt;li&gt;Incorrect semantic search results: Sometimes, the user's question is very clear, but the ranking of the content searched from the vector database is problematic. The correct document content to answer the question cannot be found in the Top N.&lt;/li&gt;
&lt;li&gt;Insufficient or outdated documentation: Although the customer's question is very clear, the official documentation is either not comprehensive enough or not up-to-date, so it doesn't contain these contents. As a result, GPT will improvisationally provide an answer, which often turns out to be incorrect.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Missed Targets of Toxicity Detection
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Problem Analysis
&lt;/h3&gt;

&lt;p&gt;While I have employed the Few-Shot method to assist GPT in determining whether a user's question falls within the TiDB business scope (detailed in the section on Limiting the Response Field) there are always limited examples compared to the breadth of user's questions and perspectives. The bot cannot make accurate judgments based solely on the examples written in the system prompts, leading to missed targets.&lt;/p&gt;

&lt;h3&gt;
  
  
  Solution
&lt;/h3&gt;

&lt;p&gt;Fortunately, the application scenarios in enterprises are always limited. Therefore, theoretically, the user's questioning perspectives are also limited. If I were to provide all the questions asked by users and feed them to GPT, it should be able to accurately identify whether any question belongs to the TiDB business category.&lt;br&gt;
So, how can we feed all the questions to GPT? This scenario is not isolated. In the initial design of the bot, it relied on official documentation to answer user's questions. However, it is unrealistic to stuff all the official documentation into GPT at once. Therefore, I have designed to search for relevant documents from the vector database according to semantic similarity. In this case, the feature of semantic search can also be used to solve the problem.&lt;br&gt;
To implement this solution, the following steps need to be accomplished:&lt;/p&gt;

&lt;h4&gt;
  
  
  Data Preparation
&lt;/h4&gt;

&lt;p&gt;Step one: Collect all relevant questions online and during testing, mark them for toxicity, and clean them into a format similar to the examples in the current system prompts.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;instruction: {user's querstion} &lt;br&gt;
question: is the instruction out of scope (not related with TiDB)?&lt;br&gt;
answer: YES or NO&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Importing data into a vector database, supporting the search for semantically similar results&lt;br&gt;
Step Two: Referencing the method of Correct Answering in Sub-Domains Knowledge, the cleaned data is placed into a vector database, and it supports searching in the vector database when the user asks questions, finding the most semantically similar examples, and providing them together to the GPT model.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fcwq5fx4mv1iq6s8spdxa.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fcwq5fx4mv1iq6s8spdxa.png" alt="Image description" width="800" height="406"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Thus, when the GPT model is assessing toxicity, it will reference the most relevant examples to provide the most accurate response possible.&lt;/p&gt;

&lt;h2&gt;
  
  
  Discussion: The Similarities and Differences between Example and Domain Document Search
&lt;/h2&gt;

&lt;p&gt;Although the search for examples and domain documents both involve finding content with high semantic similarity in a vector database, and both use the same vector database, the same Embedding model, the same vector length, and the same similarity calculation function.&lt;br&gt;
However, there are still certain differences in their practical execution.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;In terms of Embedding content

&lt;ul&gt;
&lt;li&gt;When conducting a domain knowledge document search, all content within the document needs to be searched. Therefore, the document content will be split and all content needs to go through embedding, and then stored in the vector database.&lt;/li&gt;
&lt;li&gt;However, when conducting an example search, since only the instruction part is related or similar to the user's question, the instruction part of the example needs to undergo Embedding, while the answer part does not.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;In terms of split

&lt;ul&gt;
&lt;li&gt;Domain knowledge documents are longer and need to be split before undergoing Embedding.&lt;/li&gt;
&lt;li&gt;Examples requiring embedding are all questions, each of which is not too lengthy, so there’s no need for split. They can be treated as an independent chunk; this way, the final search results will be individual question and answer examples.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;h2&gt;
  
  
  Difficulties in Contextual Understanding
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Problem Analysis
&lt;/h3&gt;

&lt;p&gt;Thanks to the contextual understanding capabilities of the GPT model, applications can provide continuous dialogue features. However, if the robot needs to provide relevant domain knowledge dynamically based on context, several problems usually arise.&lt;br&gt;
When users engage in multi-turn dialogue, they would ask follow-up questions about the previous dialogue content, such as, "What is the default value of this parameter?". At this point, the system directly uses the text of "What is the default value of this parameter?" to search for domain knowledge in the vector database. The quality of the search results is quite poor.&lt;/p&gt;

&lt;h3&gt;
  
  
  Solution
&lt;/h3&gt;

&lt;p&gt;The root cause of this problem is the subjective contextual semantics in human conversations, which the system fails to understand. Fortunately, as mentioned earlier, "The GPT model has the capability of contextual understanding". Therefore, a simple solution is to let GPT rewrite the user's original question before the system searches for domain knowledge. The aim is to describe the user's intent as clearly as possible in one sentence. This act is known as "question revision".&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2ohqu5d1avhr58z730ng.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2ohqu5d1avhr58z730ng.png" alt="Image description" width="800" height="200"&gt;&lt;/a&gt;&lt;br&gt;
To ensure consistency in the user questions that the entire robot system faces and avoid errors due to inconsistencies, I placed the question revision feature at the very forefront of the system information flow. This way, user questions are revised as soon as they enter the robot.&lt;br&gt;
During the revision, the robot asks the GPT model to describe the user's question intent in one sentence based on the overall dialogue context, adding as much detailed information as possible. This way, whether in toxicity detection or domain knowledge search, the system can execute based on a more specific intent.&lt;br&gt;
What if there are obvious errors found in the question revision? In fact, we can use a combination of few shot + semantic search to specifically optimize these errors.&lt;/p&gt;

&lt;h2&gt;
  
  
  Limitations of Semantic Search
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Discussion: The Process and Optimization Methods of Semantic Search
&lt;/h3&gt;

&lt;p&gt;The method of using vectors for semantic search is the cornerstone of TiDB Bot. Without this method, relying solely on the capacity of the GPT model, it would be impossible to simply build a robot to answer specific knowledge in a niche field.&lt;br&gt;
However, the more foundational the content, the more necessary it is to understand its potential issues, in order to find some methods for positive optimization.&lt;br&gt;
Overall, in the process of preparing domain knowledge data, splitting, vectorizing, and searching, there are many ways to optimize. Here are a few examples that the author has tried:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;During the data preparation stage: Clean the documents, remove images, links, and other meaningless symbols and document structures.&lt;/li&gt;
&lt;li&gt;During the splitting stage: Use different methods to split the document (like splitting by token, splitting by natural paragraphs, splitting by symbol, etc.). After splitting, consider whether some overlap is needed and determine an appropriate amount for this overlap.&lt;/li&gt;
&lt;li&gt;During the vectorization stage: Whether to use a proprietary or open-source embedding model, how long the vector should be, and whether it supports multi-language vectorization. If using an open-source model, how to fine-tune it, how to prepare the fine-tuning corpus, and how to handle epochs and rounds to allow the model to converge with high quality.&lt;/li&gt;
&lt;li&gt;During the semantic search stage: Decide which similarity algorithm is best, how much document content to search to satisfy the intent, and whether the split content needs to be aggregated again after being searched.
The advantages of the above methods:&lt;/li&gt;
&lt;li&gt;Each method is a systematic solution, effective for all domain knowledge documents, without prejudice.&lt;/li&gt;
&lt;li&gt;The methods used in the data preparation and splitting stages can generally achieve stable positive optimization, allowing for higher quality data material.
Disadvantages:&lt;/li&gt;
&lt;li&gt;Key optimization methods during the vectorization and semantic search stages cannot achieve stable positive optimization. The direction of optimization is random, and improving one aspect of the model's ability may weaken another.&lt;/li&gt;
&lt;li&gt;Each optimization requires a deep understanding of the relationship between the business and the optimization method. It requires repeated fine-tuning under the business test set, continual experimentation, and deepening the understanding of the adaptability between technology and business, to have the chance to achieve relatively good results.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Problem Analysis
&lt;/h3&gt;

&lt;p&gt;In the beta testing phase, a common problem encountered is: the user's question is clear, but the corresponding document content cannot be found in the Top N results from the vector database search. This implies that related documents to the question do exist within the system, but they just aren't being retrieved. This could be due to several possibilities:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The document is not well-written or too obscure, making it challenging to find based on semantic similarity.&lt;/li&gt;
&lt;li&gt;The embedding model needs to be improved, as the vector distance between user's query and the directly relevant domain knowledge is not the shortest.&lt;/li&gt;
&lt;li&gt;The similarity algorithm is not optimal, and other similarity algorithms could potentially be utilized to address this.
To solve these possible issues, it could take several months. Even though some improvements might be achieved, the effectiveness of these improvements cannot be guaranteed. Therefore, in order to stably improve the output quality of semantic search, there are two direct, effective, and rapidly implementable methods:&lt;/li&gt;
&lt;li&gt;First, adjust the vector distance between the domain content and the query directly.&lt;/li&gt;
&lt;li&gt;Second, recall specific content examples in addition to recalling domain knowledge content.
Both methods can provide correct information in system prompts, but they have different pros and cons:&lt;/li&gt;
&lt;li&gt;Method One:

&lt;ul&gt;
&lt;li&gt;Cons:&lt;/li&gt;
&lt;li&gt;Direct adjustment of vector distance involves moving and rotating existing vectors, which could affect other user queries and disrupt the overall distribution of the domain knowledge vectors.&lt;/li&gt;
&lt;li&gt;Direct adjustment of vector distance might also mean using an additional metric or function to express the new vector distance. However, creating a new similarity function may not necessarily solve the problem.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Method Two:

&lt;ul&gt;
&lt;li&gt;Pros:&lt;/li&gt;
&lt;li&gt;Introducing new content (examples) into the system prompts does not impact the existing domain knowledge vector space, thus providing relative decoupling.&lt;/li&gt;
&lt;li&gt;It also offers higher flexibility, allowing for rapid additions and deletions in the future.&lt;/li&gt;
&lt;li&gt;Cons:&lt;/li&gt;
&lt;li&gt;When domain knowledge is updated, the examples also need to be updated, requiring an additional process.
Considering the simplicity of system maintenance and the real-time nature of optimization, the author eventually chose Method Two.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;h3&gt;
  
  
  Solution
&lt;/h3&gt;

&lt;p&gt;The primary method I use is a combination of examples and training the Embedding model.&lt;br&gt;
In the first step, a method similar to 'The Missed Targets of Toxicity Detection' is used to supplement examples that specifically target common mistakes. These examples are then provided to the GPT model along with the system prompt words, in order to improve accuracy.&lt;br&gt;
In the second step, once a sufficient number of examples have been accumulated, these examples are used as training data to train the Embedding model. This enables the Embedding model to better understand the relationship between questions and domain knowledge, thereby producing more appropriate vector data results.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fn0cn33zjc111om51z3lj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fn0cn33zjc111om51z3lj.png" alt="Image description" width="800" height="503"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In practical work, the cyclical use of the first and second steps helps to maintain the number of examples at a manageable level, and continuously promotes the improvement of the Embedding model.&lt;/p&gt;

&lt;h2&gt;
  
  
  Garbage In, Garbage Out
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Problem Analysis
&lt;/h3&gt;

&lt;p&gt;In machine learning, one of the most famous phrases is "Garbage In, Garbage Out", which means if incorrect or meaningless data is input into the model, the model will inevitably output incorrect or meaningless results. Therefore, if the quality of the domain document content is poor, or its timeliness has passed, the quality of the answer given by the GPT model is likely to be poor as well.&lt;/p&gt;

&lt;h3&gt;
  
  
  Solution
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fugj7xd1kiigqq8m0kig2.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fugj7xd1kiigqq8m0kig2.png" alt="Image description" width="800" height="213"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I have established the ability to regularly update domain knowledge documents, and when users report errors, I submit the corresponding documents to the appropriate team to encourage the update and enrichment of domain documents.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Only Rule to Product Usability: Continuous Operation
&lt;/h2&gt;

&lt;p&gt;The aforementioned strategies are some of the attempts I made while optimizing the TiDB Bot. These methods can to a certain extent enhance the accuracy of the bot's responses. However, to reduce the dislike rate from over 50% to less than 5%, we need to progress step by step to achieve our long-term goal.&lt;br&gt;
To ensure the continuous optimization of TiDB Bot, I built an internal operation platform. This platform can conveniently implement the optimization methods introduced in this article. The core capabilities of this platform include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Feedback Information Display: It presents the upvotes or downvotes from users on the replies. For downvoted information, it displays the handling logs of each node in the information flow, which is convenient for troubleshooting. &lt;/li&gt;
&lt;li&gt;Quick Addition of Examples: For each node interacting with GPT, it supports the capability to provide examples, including revising questions, toxicity detection, domain knowledge, and more. All stages can quickly supplement examples.&lt;/li&gt;
&lt;li&gt;Automatic Update of Domain Knowledge: For domain knowledge with a fixed source, such as official documents, it supports regular automatic updates of the document content in the vector database to keep the domain knowledge up to date.&lt;/li&gt;
&lt;li&gt;Data Organization for Model Iteration: It automatically organizes the training data needed for tweaking the Embedding model, including users' upvote information and example information supplemented during operation, etc.
Finally, by using this operation platform, I gradually improved the accuracy over 103 days. Eventually, with the help of community test users, it was successfully launched.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Discussion: The Choice Between Model Fine-Tuning and Continuous Operation
&lt;/h2&gt;

&lt;p&gt;The term "model fine-tuning" here refers to the method of using more domain-specific data to train models, including Embedding and GPT models, directly through fine-tuning. By contrast, "continuous operation" refers to practices similar to those described in this article, which involve leveraging more high-quality domain knowledge and examples, as well as engaging in multiple interactions with GPT to enhance the accuracy of the application.&lt;br&gt;
Many people may ask, why does this article emphasize the method of continuous operation and not accentuate the method of model fine-tuning? To answer this question, we first need to look at the pros and cons of both methods:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Model Fine-Tuning Method:

&lt;ul&gt;
&lt;li&gt;Pros:&lt;/li&gt;
&lt;li&gt;The opportunity to comprehensively improve the quality of responses in a specific domain.&lt;/li&gt;
&lt;li&gt;Once trained successfully, the demands for domain knowledge in answering questions will decrease, thus saving on the cost of collecting domain knowledge in the later stage.&lt;/li&gt;
&lt;li&gt;The training cost is acceptable. As seen from the open-source community, using the Low-Rank Adaptation of Large Language Models (LoRA) approach to fine-tune a model only takes about 8 hours on a V100 graphics card to converge.&lt;/li&gt;
&lt;li&gt;Cons:&lt;/li&gt;
&lt;li&gt;It requires collecting and preprocessing a vast amount of high-quality domain data. If Full Fine-Tuning (FFT) is needed, more than 100,000 corpora are required, and even if the Parameter-Efficient Fine-Tuning (PEFT) method is used, over 50,000 corpora are still needed.&lt;/li&gt;
&lt;li&gt;The training effect is uncertain. After training, although the capacity to respond to domain knowledge has improved, the abilities in other general knowledge and reasoning may decline. When facing real user questions, it may result in inadequate reasoning and a decrease in the ability to answer questions. As the fine-tuning method is based on an existing model for training, whether it improves or deteriorates depends on the existing model. If a good existing model can be found, it will enable the fine-tuned model to start from a higher point.&lt;/li&gt;
&lt;li&gt;The quality of open-source models cannot rival that of OpenAI. Although there is a chance to reduce training costs, there are currently no academic or industrial reports that can produce an open-source model with capabilities similar to OpenAI.&lt;/li&gt;
&lt;li&gt;Each iteration takes a relatively long time. Each iteration (measured in months) requires undergoing one or several cycles of data preparation, training, and testing to possibly obtain a usable model. Especially in terms of data preparation, high-quality training datasets may not be prepared until after undergoing several rounds of actual training.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;Continuous Operation Method:

&lt;ul&gt;
&lt;li&gt;Pros:&lt;/li&gt;
&lt;li&gt;Relatively stable positive optimization. This article adopts a systematic method to optimize accuracy without depending on the randomness produced by model training.&lt;/li&gt;
&lt;li&gt;Fast. The optimization of the example part can achieve minute-level iteration speed, which allows for rapid troubleshooting if users encounter problems.&lt;/li&gt;
&lt;li&gt;Economical. It only requires the reuse of existing semantic search capabilities, with no need for additional components or extra costs.&lt;/li&gt;
&lt;li&gt;Low migration cost. The method in this article can be used in any chat-type GPT model, allowing for quick migration to other models. Should there be a better model in open-source or commercial models, it can be integrated swiftly.&lt;/li&gt;
&lt;li&gt;Friendly to cold start. Problems can be solved as they arise, without the need for a large amount of training data in advance.&lt;/li&gt;
&lt;li&gt;Cons:&lt;/li&gt;
&lt;li&gt;More frequent human intervention is required. Because the example-based method requires more human verification and supplementation processes, it demands more frequent human intervention than model fine-tuning during product operation.&lt;/li&gt;
&lt;li&gt;Excessive content. After a period of operation, the supplemented content may become too much to handle, leading to difficulties in maintenance and a decline in search accuracy.
From the above, we can see that both methods have their advantages and disadvantages. They are not mutually exclusive but complementary. For example, the author has fine-tuned the Embedding model. 
In the early stages of the TiDB Bot, the author leans more towards the continuous operation method, applying a systematic approach for stable, economical, and rapid positive optimization, making sure that the entire team focuses on business issues. Perhaps in the middle and later stages of TiDB Bot's development, the method of model fine-tuning could be considered for further optimization.&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Holistic Logical Architecture Including Optimization Methods
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fvto2wx5qa0er6h4zgnih.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fvto2wx5qa0er6h4zgnih.png" alt="Image description" width="800" height="443"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;So far, we have obtained the ability to continuously optimize the TiDB Bot.&lt;/p&gt;

&lt;h2&gt;
  
  
  Following up
&lt;/h2&gt;

&lt;p&gt;The TiDB Bot has been launched on &lt;a href="https://tidbcloud.com/" rel="noopener noreferrer"&gt;TiDB Cloud&lt;/a&gt;, &lt;a href="https://join.slack.com/t/tidbcommunity/shared_invite/zt-1zx8bvrqp-tfelBm_J8e1gkZ_CyOarbQ" rel="noopener noreferrer"&gt;Slack&lt;/a&gt;, and &lt;a href="https://discord.gg/wUWMTW5CV8" rel="noopener noreferrer"&gt;Discord channels&lt;/a&gt;. Everyone is welcomed to use it.&lt;br&gt;
In the future, we will provide open-source tools for building applications similar to TiDB Bot, enabling everyone to quickly build their own GPT applications.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>database</category>
      <category>tidb</category>
      <category>chatgpt</category>
    </item>
    <item>
      <title>Building a Company-specific User Assistance Robot with Generative AI</title>
      <dc:creator>TiDB Community</dc:creator>
      <pubDate>Thu, 20 Jul 2023 03:21:34 +0000</pubDate>
      <link>https://dev.to/tidbcommunity/building-a-company-specific-user-assistance-robot-with-generative-ai-14d4</link>
      <guid>https://dev.to/tidbcommunity/building-a-company-specific-user-assistance-robot-with-generative-ai-14d4</guid>
      <description>&lt;p&gt;About the Author: Li Li, Product Manager at PingCAP.&lt;/p&gt;

&lt;h3&gt;
  
  
  TL:DR
&lt;/h3&gt;

&lt;p&gt;This article introduces how to use Generative AI to build a user assistance robot that uses a corporate-specific knowledge base. In addition to the industry’s commonly used knowledge base response method, it also attempts to judge toxicity under the few-shot method. Eventually, the robot has been applied to various channels facing global customers of the company, with a dislike ratio of less than 5% after user usage.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Magic of Generative AI Unveiled
&lt;/h3&gt;

&lt;p&gt;Since 2022, Generative AI (hereafter referred to as GenAI) has spearheaded a global revolution. From the buzz created by &lt;a href="https://www.midjourney.com/" rel="noopener noreferrer"&gt;MidJourney&lt;/a&gt; and &lt;a href="https://openai.com/dall-e-2" rel="noopener noreferrer"&gt;DALL-E&lt;/a&gt; in generating imagery from text, to the phenomenal attention garnered by &lt;a href="https://openai.com/chatgpt" rel="noopener noreferrer"&gt;ChatGPT&lt;/a&gt; through its natural and fluent conversations, GenAI has become an unavoidable topic. Whether AI can support better living and work in more general scenarios became one of the core topics in 2023.&lt;/p&gt;

&lt;p&gt;The rise of development tools such as &lt;a href="https://www.langchain.com/" rel="noopener noreferrer"&gt;LangChain&lt;/a&gt; signifies that engineers have begun to mass-produce applications based on GenAI. PingCAP has also conducted some experiments and accomplished some works, such as:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://ossinsight.io/" rel="noopener noreferrer"&gt;Ossingisht&lt;/a&gt;’s &lt;a href="https://ossinsight.io/explore/" rel="noopener noreferrer"&gt;Data Explore&lt;/a&gt;r: A project that generates SQL to explore Github open-source software projects using natural language&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://tidbcloud.com/" rel="noopener noreferrer"&gt;TiDB Cloud&lt;/a&gt;’s &lt;a href="https://docs.pingcap.com/tidbcloud/explore-data-with-chat2query" rel="noopener noreferrer"&gt;Chat2Query&lt;/a&gt;: A project that uses the in-cloud database to generate SQL using natural language&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;After building these applications, the author began to contemplate whether the capabilities of GenAI can be used to construct more universal applications, providing bigger value for the users.&lt;/p&gt;

&lt;h3&gt;
  
  
  Considering the Demand
&lt;/h3&gt;

&lt;p&gt;With the global growth of TiDB and TiDB Cloud, providing support for global users has become increasingly important. As the number of users grows exponentially, the number of support staff will not increase rapidly. Hence, how to handle the large volume of users becomes an urgent matter to consider.&lt;/p&gt;

&lt;p&gt;Based on the actual experience of supporting users, according to our research on the user queries in the global community and the internal ticket system, over 50% of the user issues could actually be addressed by referring to the official documentation. It’s just that the vast volume of content makes it difficult to find. Therefore, if we can provide a robot armed with all the necessary knowledge from the official TiDB documentation, perhaps it could help users utilize TiDB more effectively.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Gap between Generative AI and Demand Fulfillment
&lt;/h3&gt;

&lt;p&gt;After identifying the demand, it’s also necessary to understand the characteristics and limitations of GenAI to determine whether it can be applied to this particular demand. Based on the work completed so far, the author is able to summarize some features of GenAI. Here, GenAI primarily refers to GPT (Generative Pre-trained Transformer) type models, with text dialogue as the main focus, and GPT will be used to describe in the following context of this article.&lt;/p&gt;

&lt;h3&gt;
  
  
  Capabilities of GPT
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Ability to understand semantics. GPT possesses a strong capability in comprehending semantics, essentially able to understand any given text without obstacles. Regardless of the language (human or computer languages), the level of textual expression — even in a multilingual mixture, or texts with grammatical or vocabulary errors, it can interpret user queries.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Logical reasoning ability. GPT has a certain degree of logical reasoning power. Without the need for additional special prompt words, GPT can perform simple inference and uncover deeper contents of a question. With certain prompt words supplemented, GPT can demonstrate stronger inferential capabilities. The methods to provide these prompt words include Few-shot, Chain-of-Thought (COT), Self-Consistency, Tree of thought (TOT), and so on.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Attempting to answer all questions. GPT, especially the Chat type, like GPT 3.5, GPT 4, will always try to respond to all user questions in a conversational form, as long as it aligns with the preset value perception, even if the answer is “I cannot provide that information.”&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;General knowledge capability. GPT itself possesses a vast amount of general knowledge, which is highly accurate and covers a broad range.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Multi-turn dialogue capability. GPT is set up to understand the meanings of multiple dialogues between different roles, meaning it can utilize the method of further questioning in a conversation without having to repeat all the historical key information in every dialogue. This behavior aligns very well with human thinking and conversational logic.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  Limitations of GPT
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Passive triggering. GPT requires an input from the user to generate a response. This implies that GPT would not initiate interaction on its own.&lt;/li&gt;
&lt;li&gt;Knowledge expiration. This specifically refers to GPT 3.5 and GPT 4. The training data for both cease in September 2021, which means any knowledge or events post this date are unknown to GPT. It is unrealistic to expect GPT to provide new knowledge itself.&lt;/li&gt;
&lt;li&gt;Illusion of specialized fields. Although GPT possesses excellent abilities in general knowledge, in a specific knowledge domain, such as the author’s field of database industry, most of GPT’s answers are more or less erroneous and cannot be trusted directly.&lt;/li&gt;
&lt;li&gt;Dialogue length. GPT has a character limit for each dialogue round. Therefore, if the content provided to GPT exceeds this character limit, the dialogue will fail.&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  Gap in Implementation of Requirements
&lt;/h3&gt;

&lt;p&gt;The author intends to use GPT to realize an "enterprise-specific user assistant robot," which means the following requirements:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Requirement 1: Multiturn dialogues, understanding the user's queries, and providing answers.&lt;/li&gt;
&lt;li&gt;Requirement 2: The content of the answers regarding TiDB and TiDB Cloud must be accurate.&lt;/li&gt;
&lt;li&gt;Requirement 3: Can't answer content unrelated to TiDB and TiDB Cloud, especially political-related content.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Analyzing these requirements:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Requirement 1: can basically be met, based on GPT's "ability to understand semantics," "logical reasoning ability," "try to answer questions ability," and "context understanding ability."&lt;/li&gt;
&lt;li&gt;Requirement 2: can't be met. Due to GPT's "knowledge obsolescence" and "illusion of segmented fields" limitations.&lt;/li&gt;
&lt;li&gt;Requirement 3: can't be met. Because of GPT’s "ability to try to answer all questions," any question will be answered, and GPT itself does not restrict answering political questions.
Therefore, in the construction of this assistant robot, it is mainly about solving problems with requirement two and requirement three.
### Correct Answering in Sub-Domains Knowledge&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Here, we are to address the second requirement.&lt;br&gt;
The task of enabling GPT to answer user's queries based on specific domain knowledge is not a new field. My previous optimization for Ossinsight - Data Explorer uses such specific domain knowledge, helping boost the execution rate of natural language generated SQL (i.e., the SQL generated can successfully run and produce results in TiDB) by over 25% (as seen in the performance upon &lt;a href="https://pingcap.feishu.cn/wiki/wikcnqan475PLagIpWq8mDTZ4Rf" rel="noopener noreferrer"&gt;OssInsight's launch&lt;/a&gt;).&lt;br&gt;
What needs to be employed here is the spatial similarity search capability of vector databases. This typically involves three steps:&lt;/p&gt;

&lt;h4&gt;
  
  
  Storing Domain Knowledge in a Vector Database
&lt;/h4&gt;

&lt;p&gt;The first step is to put the official documents of TiDB and TiDB Cloud into the vector database.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fa5yh3crxz4lz6vlef4gb.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fa5yh3crxz4lz6vlef4gb.png" alt="Image description" width="800" height="262"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Once the documents have been retrieved, the text content is put into the Embedding model to generate the corresponding vector of the textual content, and these vectors are placed into a specific vector database.&lt;br&gt;
In this step, two points need to be checked: &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;If the quality of the document is poor, or the format of the document does not meet the expectations, a round of preprocessing will be carried out on the document in advance to convert it into a relatively clean text format that can be easily understood by LLM.&lt;/li&gt;
&lt;li&gt;If the document is long and exceeds the single conversation length of GPT, the document must be trimmed to meet the length requirement. There are many methods of trimming, such as trimming by specific characters (e.g., commas, periods, semicolons), trimming by text length, and so on.&lt;/li&gt;
&lt;/ul&gt;

&lt;h4&gt;
  
  
  Searching for Relevant Content from the Vector Database
&lt;/h4&gt;

&lt;p&gt;The second step is to search for relevant text content from the vector database when the user poses a question.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fypl5st3viqqb531y9khi.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fypl5st3viqqb531y9khi.png" alt="Image description" width="800" height="1154"&gt;&lt;/a&gt;&lt;br&gt;
When a user initiates a conversation, the system will convert the user's conversation into a vector through the Embedding model and put this vector into the vector database to perform a search with the existing data. During the search, we use similarity algorithms (such as cosine similarity, dot-product, etc.) to calculate the most similar domain knowledge vectors and extract the text content corresponding to these vectors.&lt;br&gt;
A user's specific question may require multiple documents to answer, hence during the search, we retrieve the top N (currently N equals 5) documents with the highest similarity. These top N documents can satisfy the need for spanning multiple documents, all of which will contribute to the content provided to GPT in the next step.&lt;/p&gt;

&lt;h4&gt;
  
  
  Relevant content and user queries are presented to GPT together.
&lt;/h4&gt;

&lt;p&gt;The third step is assembling all the pertinent information and submitting it to GPT.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F7qpwfzsgg8r63qlupjpq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F7qpwfzsgg8r63qlupjpq.png" alt="Image description" width="800" height="168"&gt;&lt;/a&gt;&lt;br&gt;
The task objective and relevant domain knowledge are incorporated into the system prompts and the chat history is assembled based on past dialogues. Providing all the content to GPT allows for a domain-specific response based on this acquired knowledge. &lt;br&gt;
Upon completing the above steps, basically, we can meet the second requirement - answering questions based upon specific domain knowledge. The correctness of the answers is greatly improved compared to directly querying GPT.&lt;/p&gt;

&lt;h3&gt;
  
  
  Limiting the Response Field
&lt;/h3&gt;

&lt;p&gt;Here we aim to address the issue raised in Demand Three. &lt;br&gt;
As this robot is intended to serve as a business support capability for users, we expect it to only answer questions related to the company itself, such as those about TiDB, TiDB Cloud, SQL issues, application construction problems, etc. If inquiries go beyond these scopes, we hope the robot will decline to respond, for instance to questions about the weather, cities, arts, politics, etc. &lt;br&gt;
Given that we previously mentioned GPT's aptitude to "attempt to answer all questions", it is within GPT's own setting that it should respond to any question in a manner that aligns with human values. Therefore, this restriction cannot be built with the help of GPT, and must be attempted on the application side. &lt;br&gt;
Only by accomplishing this requirement can a service actually go live to serve its users. Regrettably, at present, there isn't any satisfactory industrial solution for this. Indeed, the majority of application designs do not even address this aspect.&lt;/p&gt;

&lt;h4&gt;
  
  
  Concept: Toxicity
&lt;/h4&gt;

&lt;p&gt;As mentioned earlier, GPT attempts to tailor its responses to align with human values, a step referred to as "Alignment" in model training. It prompts GPT to deny answering questions related to hate and violence. If GPT doesn't comply with the condition and ends up answering hate or violence-related questions, it is deemed as having displayed toxicity.&lt;br&gt;
Therefore, with regard to the robot that I'm about to create, the scope of toxicity has effectively expanded. Namely, any responses not pertaining to the company's business can be considered as being laced with toxicity. Under this definition, we can draw upon the previous work done in the field of detoxification. &lt;a href="https://aclanthology.org/2021.findings-emnlp.210.pdf" rel="noopener noreferrer"&gt;Johannes Welbl&lt;/a&gt; from DeepMind (2021), among others, advises utilizing language models for toxicity detection. Now, with the considerable advancements in GPT's capabilities, it has become possible to use GPT itself to judge whether a user's question falls within the company's business scope.&lt;br&gt;
To limit the answer domain, two steps are necessary.&lt;/p&gt;

&lt;h4&gt;
  
  
  Determination within a limited domain
&lt;/h4&gt;

&lt;p&gt;The first step is to evaluate the user's initial inquiry.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg8vlja0jw4ayht9zklgr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg8vlja0jw4ayht9zklgr.png" alt="Image description" width="800" height="190"&gt;&lt;/a&gt;&lt;br&gt;
Here, it's necessary to use the few-shot method to construct prompts for toxicity detection, enabling GPT to determine if the user's inquiry falls within the scope of enterprise services when multiple examples are at hand. &lt;br&gt;
For instance, some examples are:&lt;br&gt;
``&amp;lt;&amp;lt; EXAMPLES &amp;gt;&amp;gt;&lt;/p&gt;

&lt;p&gt;instruction: who is Lady Gaga?&lt;br&gt;
question: is the instruction out of scope (not related with TiDB)?&lt;br&gt;
answer: YES&lt;/p&gt;

&lt;p&gt;instruction: how to deploy a TiDB cluster?&lt;br&gt;
question: is the instruction out of scope (not related with TiDB)?&lt;br&gt;
answer: NO&lt;/p&gt;

&lt;p&gt;instruction: how to use TiDB Cloud?&lt;br&gt;
question: is the instruction out of scope (not related with TiDB)?&lt;br&gt;
answer: NO``&lt;/p&gt;

&lt;p&gt;After the judgment is completed, GPT will input 'Yes' or 'No' for subsequent proceedings. Note, here 'Yes' signifies 'toxic' (not relevant to the business), and 'No' means 'non-toxic' (relevant to the business).&lt;/p&gt;

&lt;h3&gt;
  
  
  Post-Judgment Processing
&lt;/h3&gt;

&lt;p&gt;In the second step, after obtaining whether the result is toxic or not, we branch the processes into two: toxic and non-toxic, for the handling of abnormal and normal processes respectively.&lt;br&gt;
The normal process is the Correct Answering in Sub-Domains Knowledge, as mentioned above. The focus here is on the explanation of the abnormal process flow.&lt;br&gt;
When the system discovers that the generated content is "Yes", it will guide the process into the toxic content reply process. At this time, a system prompt word that refuses to answer the user's question and the corresponding question from the user will be submitted to GPT, and finally, the user will receive a reply that refuses to answer.&lt;br&gt;
Upon completing these two steps, Requirement Three is essentially completed.&lt;/p&gt;

&lt;h3&gt;
  
  
  Overall Logical Framework
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ftz4uopm8c2gc66xnnh63.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Ftz4uopm8c2gc66xnnh63.png" alt="Image description" width="800" height="396"&gt;&lt;/a&gt;&lt;br&gt;
Thus, we have developed a basic assistant robot, which we named TiDB Bot, that can be provided to users and has specific enterprise domain knowledge.&lt;/p&gt;

&lt;h3&gt;
  
  
  TiDB Bot Test Stage Results
&lt;/h3&gt;

&lt;p&gt;Starting from March 30, TiDB Bot began internal testing, and officially opened to Cloud users on July 11. &lt;br&gt;
During the 103 days of TiDB Bot’s incubation, countless communities and developers provided valuable feedback on the test product, gradully making TiDB Bot usable. During the test phase, a total of 249 users accessed the bot, sending 4570 messages. By the end of the test stage, 83 users had given 266 pieces of feedback, with negative feedbacks accounting for 3.4% of the total amount of information conveyed and positive feedbacks accounting for 2.1%.&lt;br&gt;
In addition to the direct users, there were also communities who suggested ideas and proposed more solutions. Thank you to all the communities and developers, without you, the product launch of TiDB Bot would not have been possible.&lt;/p&gt;

&lt;h3&gt;
  
  
  Further Plans
&lt;/h3&gt;

&lt;p&gt;As the number of users steadily increases, there still remain significant challenges whether in terms of the accuracy of recall content or toxicity judgment. Therefore, the author has been optimizing the accuracy of TiDB Bot in actual service provision, to gradually enhance the effectiveness of its answers. These matters will be introduced in future articles.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>tidb</category>
    </item>
  </channel>
</rss>
