{"meta":{"title":"Pre-Tool Verwendungs-Hook","intro":"Der onPreToolUse Hook wird aufgerufen , bevor ein Tool ausgeführt wird. Verwenden Sie es zu folgenden Zwecken:","product":"GitHub Copilot","breadcrumbs":[{"href":"/de/enterprise-cloud@latest/copilot","title":"GitHub Copilot"},{"href":"/de/enterprise-cloud@latest/copilot/how-tos","title":"Vorgehensweisen"},{"href":"/de/enterprise-cloud@latest/copilot/how-tos/copilot-sdk","title":"Copilot SDK"},{"href":"/de/enterprise-cloud@latest/copilot/how-tos/copilot-sdk/hooks","title":"Verwenden Sie Hooks"},{"href":"/de/enterprise-cloud@latest/copilot/how-tos/copilot-sdk/hooks/pre-tool-use","title":"Vor der Verwendung des Tools"}],"documentType":"article"},"body":"# Pre-Tool Verwendungs-Hook\n\nDer onPreToolUse Hook wird aufgerufen , bevor ein Tool ausgeführt wird. Verwenden Sie es zu folgenden Zwecken:\n\n<!-- markdownlint-disable GHD046 GHD005 -->\n\n<!-- Suppressed: GHD046 (outdated release terminology), GHD005 (hardcoded data variable) -->\n\n* Genehmigen oder Verweigern der Toolausführung\n* Ändern von Toolargumenten\n* Hinzufügen von Kontext für das Tool\n* Toolausgabe aus der Unterhaltung unterdrücken\n\n## Hook-Signatur\n\n<div class=\"ghd-codetabs\">\n<div class=\"ghd-codetab\" data-lang=\"typescript\" data-label=\"TypeScript\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">TypeScript</div>\n\n```typescript\ntype PreToolUseHandler = (\n  input: PreToolUseHookInput,\n  invocation: HookInvocation\n) => Promise<PreToolUseHookOutput | null | undefined>;\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"python\" data-label=\"Python\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">Python</div>\n\n```python\nPreToolUseHandler = Callable[\n    [PreToolUseHookInput, dict[str, str]],\n    Awaitable[PreToolUseHookOutput | None]\n]\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"go\" data-label=\"Go\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">Go</div>\n\n```golang\ntype PreToolUseHandler func(\n    input PreToolUseHookInput,\n    invocation HookInvocation,\n) (*PreToolUseHookOutput, error)\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"dotnet\" data-label=\".NET\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">.NET</div>\n\n```csharp\npublic delegate Task<PreToolUseHookOutput?> PreToolUseHandler(\n    PreToolUseHookInput input,\n    HookInvocation invocation);\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"java\" data-label=\"Java\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">Java</div>\n\n```java\n@FunctionalInterface\npublic interface PreToolUseHandler {\n    CompletableFuture<PreToolUseHookOutput> handle(\n        PreToolUseHookInput input,\n        HookInvocation invocation);\n}\n```\n\n</div>\n\n</div>\n\n## Eingabe\n\n| Feld        | Typ    | Description                                       |\n| ----------- | ------ | ------------------------------------------------- |\n| `timestamp` | Zahl   | Unix-Zeitstempel, zu dem der Hook ausgelöst wurde |\n| `cwd`       | string | Aktuelles Arbeitsverzeichnis                      |\n| `toolName`  | string | Name des aufgerufenen Tools                       |\n| `toolArgs`  | Objekt | An das Tool übergebene Argumente                  |\n\n## Output\n\nGeben Sie `null` oder `undefined` zurück, um das Tool ohne Änderungen auszuführen. Geben Sie andernfalls ein Objekt mit einem der folgenden Felder zurück:\n\n| Feld                                               | Typ     | Description                                                        |\n| -------------------------------------------------- | ------- | ------------------------------------------------------------------ |\n| `permissionDecision`                               |         |                                                                    |\n| `\"allow\"`                                          |         |                                                                    |\n| \\|                                                 |         |                                                                    |\n| `\"deny\"`                                           |         |                                                                    |\n| \\|                                                 |         |                                                                    |\n| `\"ask\"`                                            |         |                                                                    |\n| Gibt an, ob der Toolaufruf zugelassen werden soll. |         |                                                                    |\n| `permissionDecisionReason`                         | string  | Erläuterung, die dem Benutzer angezeigt wird (zur Ablehnung/Frage) |\n| `modifiedArgs`                                     | Objekt  | Geänderte Argumente, die an das Tool übergeben werden sollen       |\n| `additionalContext`                                | string  | Zusätzlicher Kontext, der in die Unterhaltung eingefügt wurde      |\n| `suppressOutput`                                   | boolean | Wenn wahr, wird die Toolausgabe nicht in Unterhaltungen angezeigt. |\n\n### Berechtigungsentscheidungen\n\n| Entscheidung | Behavior                                                                           |\n| ------------ | ---------------------------------------------------------------------------------- |\n| `\"allow\"`    | Das Tool wird normal ausgeführt                                                    |\n| `\"deny\"`     | Tool ist blockiert, Grund, der dem Benutzer angezeigt wird                         |\n| `\"ask\"`      | Der Benutzer wird aufgefordert, den Zugriff (im interaktiven Modus) zu genehmigen. |\n\n### Überspringen von Berechtigungsaufforderungen für vertrauenswürdige benutzerdefinierte Tools\n\nWenn Sie ein benutzerdefiniertes Tool definieren, das sicher ohne Rückfrage ausgeführt werden kann, setzen Sie `skipPermission: true` in der Tooldefinition. Verwenden Sie dies für vertrauenswürdige, anwendungseigene Tools, deren Eingaben bereits durch Ihre Anwendung eingeschränkt sind; verwenden Sie `onPreToolUse`, wenn Sie Richtlinienprüfungen oder eine Argumentvalidierung pro Aufruf benötigen.\n\n```typescript\nconst getWeather = defineTool(\"get_weather\", {\n  description: \"Get weather for a location.\",\n  parameters: {\n    type: \"object\",\n    properties: { location: { type: \"string\" } },\n    required: [\"location\"],\n  },\n  skipPermission: true,\n  handler: async ({ location }) => ({ forecast: `Sunny in ${location}` }),\n});\n```\n\n## Examples\n\n### Alle Tools zulassen (nur Protokollierung)\n\n<div class=\"ghd-codetabs\">\n<div class=\"ghd-codetab\" data-lang=\"typescript\" data-label=\"TypeScript\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">TypeScript</div>\n\n```typescript\nconst session = await client.createSession({\n  hooks: {\n    onPreToolUse: async (input, invocation) => {\n      console.log(`[${invocation.sessionId}] Calling ${input.toolName}`);\n      console.log(`  Args: ${JSON.stringify(input.toolArgs)}`);\n      return { permissionDecision: \"allow\" };\n    },\n  },\n});\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"python\" data-label=\"Python\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">Python</div>\n\n```python\nfrom copilot.session import PermissionHandler\n\nasync def on_pre_tool_use(input_data, invocation):\n    print(f\"[{invocation['session_id']}] Calling {input_data['toolName']}\")\n    print(f\"  Args: {input_data['toolArgs']}\")\n    return {\"permissionDecision\": \"allow\"}\n\nsession = await client.create_session(on_permission_request=PermissionHandler.approve_all, hooks={\"on_pre_tool_use\": on_pre_tool_use})\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"go\" data-label=\"Go\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">Go</div>\n\n```golang\nsession, _ := client.CreateSession(context.Background(), &copilot.SessionConfig{\n    Hooks: &copilot.SessionHooks{\n        OnPreToolUse: func(input copilot.PreToolUseHookInput, inv copilot.HookInvocation) (*copilot.PreToolUseHookOutput, error) {\n            fmt.Printf(\"[%s] Calling %s\\n\", inv.SessionID, input.ToolName)\n            fmt.Printf(\"  Args: %v\\n\", input.ToolArgs)\n            return &copilot.PreToolUseHookOutput{\n                PermissionDecision: \"allow\",\n            }, nil\n        },\n    },\n})\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"dotnet\" data-label=\".NET\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">.NET</div>\n\n```csharp\nvar session = await client.CreateSessionAsync(new SessionConfig\n{\n    Hooks = new SessionHooks\n    {\n        OnPreToolUse = (input, invocation) =>\n        {\n            Console.WriteLine($\"[{invocation.SessionId}] Calling {input.ToolName}\");\n            Console.WriteLine($\"  Args: {input.ToolArgs}\");\n            return Task.FromResult<PreToolUseHookOutput?>(\n                new PreToolUseHookOutput { PermissionDecision = \"allow\" }\n            );\n        },\n    },\n});\n```\n\n</div>\n\n<div class=\"ghd-codetab\" data-lang=\"java\" data-label=\"Java\"><div class=\"ghd-codetab-fallback-label\" role=\"heading\" aria-level=\"3\">Java</div>\n\n<!-- docs-validate: skip -->\n\n```java\nimport com.github.copilot.*;\nimport com.github.copilot.rpc.*;\nimport java.util.concurrent.CompletableFuture;\n\nvar hooks = new SessionHooks()\n    .setOnPreToolUse((input, invocation) -> {\n        System.out.println(\"[\" + invocation.getSessionId() + \"] Calling \" + input.getToolName());\n        System.out.println(\"  Args: \" + input.getToolArgs());\n        return CompletableFuture.completedFuture(PreToolUseHookOutput.allow());\n    });\n\nvar session = client.createSession(\n    new SessionConfig()\n        .setOnPermissionRequest(PermissionHandler.APPROVE_ALL)\n        .setHooks(hooks)\n).get();\n```\n\n</div>\n\n</div>\n\n### Blockieren bestimmter Tools\n\n```typescript\nconst BLOCKED_TOOLS = [\"shell\", \"bash\", \"write_file\", \"delete_file\"];\n\nconst session = await client.createSession({\n  hooks: {\n    onPreToolUse: async (input) => {\n      if (BLOCKED_TOOLS.includes(input.toolName)) {\n        return {\n          permissionDecision: \"deny\",\n          permissionDecisionReason: `Tool '${input.toolName}' is not permitted in this environment`,\n        };\n      }\n      return { permissionDecision: \"allow\" };\n    },\n  },\n});\n```\n\n### Ändern von Toolargumenten\n\n```typescript\nconst session = await client.createSession({\n  hooks: {\n    onPreToolUse: async (input) => {\n      // Add a default timeout to all shell commands\n      if (input.toolName === \"shell\" && input.toolArgs) {\n        const args = input.toolArgs as { command: string; timeout?: number };\n        return {\n          permissionDecision: \"allow\",\n          modifiedArgs: {\n            ...args,\n            timeout: args.timeout ?? 30000, // Default 30s timeout\n          },\n        };\n      }\n      return { permissionDecision: \"allow\" };\n    },\n  },\n});\n```\n\n### Einschränken des Dateizugriffs auf bestimmte Verzeichnisse\n\n```typescript\nconst ALLOWED_DIRECTORIES = [\"/home/user/projects\", \"/tmp\"];\n\nconst session = await client.createSession({\n  hooks: {\n    onPreToolUse: async (input) => {\n      if (input.toolName === \"read_file\" || input.toolName === \"write_file\") {\n        const args = input.toolArgs as { path: string };\n        const isAllowed = ALLOWED_DIRECTORIES.some(dir => \n          args.path.startsWith(dir)\n        );\n        \n        if (!isAllowed) {\n          return {\n            permissionDecision: \"deny\",\n            permissionDecisionReason: `Access to '${args.path}' is not permitted. Allowed directories: ${ALLOWED_DIRECTORIES.join(\", \")}`,\n          };\n        }\n      }\n      return { permissionDecision: \"allow\" };\n    },\n  },\n});\n```\n\n### Ausführliche Toolausgabe unterdrücken\n\n```typescript\nconst VERBOSE_TOOLS = [\"list_directory\", \"search_files\"];\n\nconst session = await client.createSession({\n  hooks: {\n    onPreToolUse: async (input) => {\n      return {\n        permissionDecision: \"allow\",\n        suppressOutput: VERBOSE_TOOLS.includes(input.toolName),\n      };\n    },\n  },\n});\n```\n\n### Hinzufügen von Kontext basierend auf dem Tool\n\n```typescript\nconst session = await client.createSession({\n  hooks: {\n    onPreToolUse: async (input) => {\n      if (input.toolName === \"query_database\") {\n        return {\n          permissionDecision: \"allow\",\n          additionalContext: \"Remember: This database uses PostgreSQL syntax. Always use parameterized queries.\",\n        };\n      }\n      return { permissionDecision: \"allow\" };\n    },\n  },\n});\n```\n\n## Bewährte Methoden\n\n1. **Geben Sie immer eine Entscheidung zurück** – Die Rückgabe von `null` erlaubt das Tool, aber die explizite Verwendung von `{ permissionDecision: \"allow\" }` ist klarer.\n\n2. **Geben Sie hilfreiche Ablehnungsgründe an** – Erläutern Sie bei einer Ablehnung, warum, damit Nutzer dies verstehen:\n\n   ```typescript\n   return {\n     permissionDecision: \"deny\",\n     permissionDecisionReason: \"Shell commands require approval. Please describe what you want to accomplish.\",\n   };\n   ```\n\n3. **Achten Sie bei der Argumentänderung darauf** , dass geänderte Argen das erwartete Schema für das Tool beibehalten.\n\n4. **Performance berücksichtigen** – Pre-Tool-Hooks werden vor jedem Tool-Aufruf synchron ausgeführt. Halten Sie sie schnell.\n\n5. **Verwenden Sie `suppressOutput` mit Bedacht** – Das Unterdrücken der Ausgabe bedeutet, dass das Modell das Ergebnis nicht sieht, was sich auf die Gesprächsqualität auswirken kann.\n\n## Siehe auch\n\n* [Verwenden Sie Hooks](/de/enterprise-cloud@latest/copilot/how-tos/copilot-sdk/hooks)\n* [Hook für die Verwendung des Tools nach der Sitzung](/de/enterprise-cloud@latest/copilot/how-tos/copilot-sdk/hooks/post-tool-use)\n* [Debughandbuch](/de/enterprise-cloud@latest/copilot/how-tos/copilot-sdk/troubleshooting/debugging)"}