Skip to main content
Glama
scvcoder

korean-privacy-law-mcp

by scvcoder

get_law_system_tree

Display the hierarchical tree structure of Korean privacy law, from statutes down to administrative rules. Understand legal relationships and dependencies at a glance.

Instructions

법령 체계도 — 트리 시각화 (법제처 lawService · target=lsStmd). 법률 → 시행령 → 시행규칙 → 행정규칙(고시·훈령·예규) 계층을 들여쓰기 트리로 표시. get_related_laws와 endpoint 공유하지만 출력 형태가 트리(체계 이해용) vs 평탄 list(검색·발견용). 다음: get_law_text(mst·lawId)로 특정 노드 본문, get_delegated_laws(lawId)로 위임조문 매핑.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
mstNo법령일련번호 (search_law 결과의 mst)
lawIdNo법령ID (search_law 결과의 lawId)

Implementation Reference

  • Main handler that fetches law system tree data via lawService.do (lsStmd), parses the response, formats it into a hierarchical indented tree (상하위법/관련법령), and returns the result with suggestions.
    async handler(args, client) {
      try {
        if (!args.mst && !args.lawId) {
          throw new ValidationError("mst 또는 lawId 필수");
        }
    
        const extraParams: Record<string, string> = {};
        if (args.mst) extraParams.MST = args.mst;
        else if (args.lawId) extraParams.ID = args.lawId;
    
        const jsonText = await client.fetchApi({
          endpoint: "lawService.do",
          target: "lsStmd",
          type: "JSON",
          extraParams,
        });
    
        let parsed: SystemTreeResponse;
        try {
          parsed = JSON.parse(jsonText);
        } catch {
          return notFoundResponse(
            `법령 체계도 응답 파싱 실패 (mst=${args.mst ?? "-"}, lawId=${args.lawId ?? "-"})`,
            [`search_law(query="...") — 유효한 mst·lawId 확인`]
          );
        }
    
        const tree = parsed.법령체계도;
        if (!tree) {
          return notFoundResponse(
            `법령 체계도 데이터 없음 (mst=${args.mst ?? "-"}, lawId=${args.lawId ?? "-"})`,
            [`search_law(query="...") — 유효한 식별자 확인`]
          );
        }
    
        const baseInfo = tree.기본정보 ?? {};
        const baseName = baseInfo.법령명 ?? "(법령명 없음)";
        const baseDate = baseInfo.시행일자 ?? "";
    
        let text = `=== ${baseName} 법령 체계도 ===\n`;
        if (baseInfo.법령ID) text += `lawId: ${baseInfo.법령ID}`;
        if (baseInfo.법령일련번호) text += ` / mst: ${baseInfo.법령일련번호}`;
        text += "\n";
        if (baseDate) text += `시행: ${baseDate}\n`;
        text += "\n";
    
        const out = { text: "", truncated: false };
    
        // 상하위법 트리
        if (tree.상하위법 && Object.keys(tree.상하위법 as object).length > 0) {
          out.text += "[상하위법]\n";
          formatTree(tree.상하위법, 1, out);
        }
    
        // 관련법령 트리
        if (
          tree.관련법령 &&
          typeof tree.관련법령 === "object" &&
          Object.keys(tree.관련법령 as object).length > 0
        ) {
          out.text += "\n[관련법령]\n";
          formatTree(tree.관련법령, 1, out);
        }
    
        if (out.text.trim() === "") {
          text += "(상하위법·관련법령 데이터 없음)\n";
        } else {
          text += out.text;
        }
    
        const suggestions: Array<{
          tool: string;
          args: Record<string, unknown>;
          reason: string;
        }> = [
          {
            tool: "get_related_laws",
            args: args.mst ? { mst: args.mst } : { lawId: args.lawId ?? "" },
            reason: `${baseName} 평탄 list 형태 (검색·발견용)`,
          },
        ];
        if (baseInfo.법령ID) {
          suggestions.push({
            tool: "get_delegated_laws",
            args: { lawId: baseInfo.법령ID },
            reason: "위임조문 매핑 (조문 수준 세부)",
          });
        }
        text = appendSuggestions(text, suggestions);
        text += `\n${formatLawAttribution(baseName)}`;
    
        return { content: [{ type: "text", text }] };
      } catch (err) {
        return formatToolError(err, "get_law_system_tree");
      }
    },
  • Input schema using Zod: accepts optional mst or lawId, requiring at least one.
    const inputSchema = z
      .object({
        mst: z.string().optional().describe("법령일련번호 (search_law 결과의 mst)"),
        lawId: z.string().optional().describe("법령ID (search_law 결과의 lawId)"),
      })
      .refine((d) => d.mst || d.lawId, {
        message: "mst 또는 lawId 중 하나는 필수입니다",
      });
  • Registration of getLawSystemTree in the ALL_TOOLS array in registry.ts
    getLawSystemTree,
  • Import statement for getLawSystemTree in the registry
    import { getLawSystemTree } from "./primitives/get-law-system-tree.js";
  • Recursive helper function that formats the nested law system tree object into an indented text representation, handling 기본정보 items and sub-category keys.
    function formatTree(
      node: unknown,
      indent: number,
      out: { text: string; truncated: boolean }
    ): void {
      if (out.truncated) return;
      if (out.text.length > MAX_BODY_CHARS) {
        out.text += `\n⋯ 이하 생략 (12,000자 한도) ⋯\n`;
        out.truncated = true;
        return;
      }
      if (!node || typeof node !== "object") return;
    
      // 배열은 각 요소를 동일 들여쓰기로
      if (Array.isArray(node)) {
        for (const item of node) formatTree(item, indent, out);
        return;
      }
    
      const obj = node as Record<string, unknown>;
      const prefix = "  ".repeat(indent);
    
      // 이 노드 자체에 기본정보 → 항목 출력
      if (obj.기본정보 && typeof obj.기본정보 === "object") {
        const info = obj.기본정보 as BasicInfo;
        const name = getName(info);
        const id = getId(info);
        const date = getDate(info);
        out.text += `${prefix}- ${name}`;
        if (id) out.text += ` (id=${id})`;
        if (date) out.text += ` · ${date}`;
        out.text += "\n";
      }
    
      // 자식 노드 walk (기본정보 외)
      for (const [key, value] of Object.entries(obj)) {
        if (key === "기본정보") continue;
        if (!value || typeof value !== "object") continue;
    
        // type 헤더 출력 (법률·시행령·시행규칙·행정규칙·고시·훈령·예규 등)
        out.text += `${prefix}[${key}]\n`;
        formatTree(value, indent + 1, out);
      }
    }
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description must disclose behavioral traits. It mentions sharing an endpoint with get_related_laws and that output is a tree, but does not explicitly state read-only nature, idempotency, or lack of side effects. This is adequate but not fully transparent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Description is concise and front-loaded with the main purpose. It includes useful differentiation and next steps. Minor redundancy with Korean terms but overall efficient.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 2 parameters and no output schema, the description covers purpose, usage differentiation, and next steps. Lacks details on the tree structure (e.g., fields returned), but sufficiently complete for an AI agent to understand when and why to use it.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Input schema has 100% coverage (both mst and lawId described). The description does not add extra details beyond the schema, so baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states this tool provides a hierarchical tree visualization of law hierarchy (법률→시행령→시행규칙→행정규칙) and explicitly contrasts with get_related_laws, which outputs a flat list for discovery.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Describes when to use this tool (for understanding hierarchy) vs get_related_laws (for search/discovery) and suggests follow-up tools (get_law_text, get_delegated_laws), providing excellent usage guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Install Server

Other Tools

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/scvcoder/korean-privacy-law-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server