import { UserInputError } from "./errors-D_R568zP.js";
import { defineTool } from "./define-2Lj8Lm1t.js";
import { apiServiceFromContext } from "./api-CkLTFexT.js";
import { ParamOrganizationSlug, ParamProjectSlug, ParamRegionUrl } from "./schema-rwexXWFL.js";
import { RECOMMENDED_FIELDS } from "./config-DlhHLHjD.js";
import { searchEventsAgent } from "./agent-FoPk5psd.js";
import { formatErrorResults, formatLogResults, formatSpanResults } from "./formatters-B9XiCNZ_.js";
import { setTag } from "@sentry/core";
import { z } from "zod";

//#region src/tools/search-events/handler.ts
var handler_default = defineTool({
	name: "search_events",
	requiredScopes: ["event:read"],
	description: [
		"Search for events AND perform counts/aggregations - the ONLY tool for statistics and counts.",
		"",
		"Supports TWO query types:",
		"1. AGGREGATIONS (counts, sums, averages): 'how many errors', 'count of issues', 'total tokens'",
		"2. Individual events with timestamps: 'show me error logs from last hour'",
		"",
		"🔢 USE THIS FOR ALL COUNTS/STATISTICS:",
		"- 'how many errors today' → returns count",
		"- 'count of database failures' → returns count",
		"- 'total number of issues' → returns count",
		"- 'average response time' → returns avg()",
		"- 'sum of tokens used' → returns sum()",
		"",
		"📋 ALSO USE FOR INDIVIDUAL EVENTS:",
		"- 'error logs from last hour' → returns event list",
		"- 'database errors with timestamps' → returns event list",
		"- 'trace spans for slow API calls' → returns span list",
		"",
		"Dataset Selection (AI automatically chooses):",
		"- errors: Exception/crash events",
		"- logs: Log entries",
		"- spans: Performance data, AI/LLM calls, token usage",
		"",
		"❌ DO NOT USE for grouped issue lists → use search_issues",
		"",
		"<examples>",
		"search_events(organizationSlug='my-org', naturalLanguageQuery='how many errors today')",
		"search_events(organizationSlug='my-org', naturalLanguageQuery='count of database failures this week')",
		"search_events(organizationSlug='my-org', naturalLanguageQuery='total tokens used by model')",
		"search_events(organizationSlug='my-org', naturalLanguageQuery='error logs from the last hour')",
		"</examples>",
		"",
		"<hints>",
		"- If the user passes a parameter in the form of name/otherName, it's likely in the format of <organizationSlug>/<projectSlug>.",
		"- Parse org/project notation directly without calling find_organizations or find_projects.",
		"</hints>"
	].join("\n"),
	inputSchema: {
		organizationSlug: ParamOrganizationSlug,
		naturalLanguageQuery: z.string().trim().min(1).describe("Natural language description of what you want to search for"),
		projectSlug: ParamProjectSlug.optional(),
		regionUrl: ParamRegionUrl.optional(),
		limit: z.number().min(1).max(100).optional().default(10).describe("Maximum number of results to return"),
		includeExplanation: z.boolean().optional().default(false).describe("Include explanation of how the query was translated")
	},
	annotations: {
		readOnlyHint: true,
		openWorldHint: true
	},
	async handler(params, context) {
		const apiService = apiServiceFromContext(context, { regionUrl: params.regionUrl });
		const organizationSlug = params.organizationSlug;
		setTag("organization.slug", organizationSlug);
		if (params.projectSlug) setTag("project.slug", params.projectSlug);
		let projectId;
		if (params.projectSlug) {
			const project = await apiService.getProject({
				organizationSlug,
				projectSlugOrId: params.projectSlug
			});
			projectId = String(project.id);
		}
		const agentResult = await searchEventsAgent({
			query: params.naturalLanguageQuery,
			organizationSlug,
			apiService,
			projectId
		});
		const parsed = agentResult.result;
		const dataset = parsed.dataset;
		const recommendedFields = RECOMMENDED_FIELDS[dataset];
		if (!parsed.sort) throw new UserInputError(`Search Events Agent response missing required 'sort' parameter. Received: ${JSON.stringify(parsed, null, 2)}. The agent must specify how to sort results (e.g., '-timestamp' for newest first, '-count()' for highest count).`);
		const sentryQuery = parsed.query || "";
		const requestedFields = parsed.fields || [];
		const isAggregateQuery = requestedFields.some((field) => field.includes("(") && field.includes(")"));
		let fields;
		if (isAggregateQuery) {
			if (!requestedFields || requestedFields.length === 0) throw new UserInputError(`AI response missing required 'fields' for aggregate query. The AI must specify which fields to return. For aggregate queries, include only the aggregate functions (like count(), avg()) and groupBy fields.`);
			fields = requestedFields;
		} else fields = requestedFields && requestedFields.length > 0 ? requestedFields : recommendedFields.basic;
		const sortParam = parsed.sort;
		const timeParams = {};
		if (parsed.timeRange) {
			if ("statsPeriod" in parsed.timeRange) timeParams.statsPeriod = parsed.timeRange.statsPeriod;
			else if ("start" in parsed.timeRange && "end" in parsed.timeRange) {
				timeParams.start = parsed.timeRange.start;
				timeParams.end = parsed.timeRange.end;
			}
		} else timeParams.statsPeriod = "14d";
		const eventsResponse = await apiService.searchEvents({
			organizationSlug,
			query: sentryQuery,
			fields,
			limit: params.limit,
			projectId,
			dataset: dataset === "logs" ? "ourlogs" : dataset,
			sort: sortParam,
			...timeParams
		});
		const aggregateFunctions = fields.filter((field) => field.includes("(") && field.includes(")"));
		const groupByFields = fields.filter((field) => !field.includes("(") && !field.includes(")"));
		const explorerUrl = apiService.getEventsExplorerUrl(organizationSlug, sentryQuery, projectId, dataset, fields, sortParam, aggregateFunctions, groupByFields, timeParams.statsPeriod, timeParams.start, timeParams.end);
		function isValidResponse(response) {
			return typeof response === "object" && response !== null;
		}
		function isValidEventArray(data) {
			return Array.isArray(data) && data.every((item) => typeof item === "object" && item !== null);
		}
		if (!isValidResponse(eventsResponse)) throw new Error("Invalid response format from Sentry API");
		const eventData = eventsResponse.data;
		if (!isValidEventArray(eventData)) throw new Error("Invalid event data format from Sentry API");
		const formatParams = {
			eventData,
			naturalLanguageQuery: params.naturalLanguageQuery,
			includeExplanation: params.includeExplanation,
			apiService,
			organizationSlug,
			explorerUrl,
			sentryQuery,
			fields,
			explanation: parsed.explanation
		};
		switch (dataset) {
			case "errors": return formatErrorResults(formatParams);
			case "logs": return formatLogResults(formatParams);
			case "spans": return formatSpanResults(formatParams);
		}
	}
});

//#endregion
export { handler_default };
//# sourceMappingURL=handler-B3-dKrMX.js.map