From 9377cf2118798d9c126c46caab339e5e9ad28c67 Mon Sep 17 00:00:00 2001 From: Santhosh S Date: Tue, 14 Oct 2025 13:19:37 +0530 Subject: [PATCH] Added tools - Refund analytics and filter orders by amount --- .../voice/automatic/tools/juspay/analytics.py | 120 ++++++++++++++++++ 1 file changed, 120 insertions(+) diff --git a/app/agents/voice/automatic/tools/juspay/analytics.py b/app/agents/voice/automatic/tools/juspay/analytics.py index 2eddcbe0..ee5d2a98 100644 --- a/app/agents/voice/automatic/tools/juspay/analytics.py +++ b/app/agents/voice/automatic/tools/juspay/analytics.py @@ -476,6 +476,85 @@ def get_average_ticket_payment_wise_by_time( return _make_genius_api_request(params, payload_details) +async def get_refund_analytics_by_time(params: FunctionCallParams): + """ + Get comprehensive refund analytics from the dedicated refund domain including + total refund volume, successful refunds, manual review counts, and breakdown + by payment gateway and method. + """ + try: + input_dimension = params.arguments.get("dimension") + + actual_dimensions = [] + if input_dimension: + actual_dimensions = [input_dimension] + + logger.info( + f"Fetching refund analytics with params: {params.arguments} and dimension: {actual_dimensions}" + ) + + # Main refund analytics by gateway + analytics_payload = { + "domain": "kvrefundtxns", + "metric": [ + "total_volume", + "success_rate", + "manual_review_rate", + "manual_review_count", + "pending_rate", + "refund_pending_5days", + "total_amount", + "mean_turn_around_time", + ], + "dimensions": actual_dimensions, + "sortedOn": {"sortDimension": "total_volume", "ordering": "Desc"}, + } + + analytics_result = await _make_genius_api_request(params, analytics_payload) + if isinstance(analytics_result, ApiFailure): + await params.result_callback(analytics_result.error) + return + + await params.result_callback({"data": analytics_result.data}) + + except Exception as e: + logger.error( + f"Unexpected error in get_refund_analytics_by_time: {e}", exc_info=True + ) + await params.result_callback({"error": f"An unexpected error occurred: {e}"}) + + +async def get_orders_by_amount(params: FunctionCallParams) -> GeniusApiResponse: + """ + Retrieves orders filtered by transaction amount using flexible comparison operators. Allows filtering orders above, below, or at specific amount thresholds within a specified time range. Results are grouped by payment method type showing order counts and success volumes. Useful for analyzing high-value transactions, small purchases, or specific spending patterns. + """ + logger.info(f"Fetching orders filtered by amount with params: {params.arguments}") + try: + input_amount = params.arguments.get("amount") + input_operator = params.arguments.get("operator") + + analytics_payload = { + "domain": "kvorders", + "metric": ["order_with_transactions", "success_volume"], + "dimensions": ["payment_method_type"], + "filters": { + "condition": input_operator, + "field": "ticket_size", + "val": input_amount, + }, + } + + analytics_result = await _make_genius_api_request(params, analytics_payload) + if isinstance(analytics_result, ApiFailure): + await params.result_callback(analytics_result.error) + return + + await params.result_callback({"data": analytics_result.data}) + except Exception as e: + logger.error(f"Unexpected error in get_orders_by_amount: {e}", exc_info=True) + await params.result_callback({"error": f"An unexpected error occurred: {e}"}) + + async def create_euler_offer(params: FunctionCallParams): """ Creates discount offers, cashbacks, and other promotional offers in the platform. IMPORTANT: Before calling this function, you MUST first present all the offer details to the user in a clear, formatted way and explicitly ask for their confirmation. Only proceed with calling this function after the user has explicitly confirmed they want to create the offer. Do not call this function without explicit user confirmation. To set the offer's active period, always use the get_current_time() tool for accurate start and end times in IST. @@ -1868,6 +1947,43 @@ async def update_euler_offer(params: FunctionCallParams): required=["offerCode"], ) +get_refund_analytics_function = FunctionSchema( + name="get_refund_analytics_by_time", + description="Get comprehensive refund analytics from the dedicated refund domain including total refund volume, successful refunds, manual review counts, and breakdown by payment gateway and method within a specified time range. Provides insights into refund processing efficiency and patterns.", + properties={ + **time_input_schema["properties"], + "dimension": { + "type": "string", + "description": "The dimension to group the analytics by. If provided, the results will be grouped by this dimension. Can be empty. How to slice the data: 'payment_gateway' for each gateway (Stripe, Razorpay), 'payment_method_type' for UPI, Cards, NB, etc., currency for different currencies (INR, USD) and banks for each bank (HDFC, SBI) ", + "enum": [ + "currency", + "payment_gateway", + "payment_method_type", + "bank", + ], + }, + }, + required=time_input_schema["required"], +) + +get_orders_by_amount_function = FunctionSchema( + name="get_orders_by_amount", + description="Retrieves orders filtered by transaction amount using flexible comparison operators. Allows filtering orders above, below, or at specific amount thresholds within a specified time range. Results are grouped by payment method type showing order counts and success volumes. Useful for analyzing high-value transactions, small purchases, or specific spending patterns.", + properties={ + **time_input_schema["properties"], + "operator": { + "type": "string", + "description": "The comparison operator to apply against the ticket size. 'Greater' finds orders above the amount, 'GreaterThanEqual' includes the exact amount and above, 'Less' finds orders below the amount, 'LessThanEqual' includes the exact amount and below.", + "enum": ["Greater", "GreaterThanEqual", "Less", "LessThanEqual"], + }, + "amount": { + "type": "string", + "description": "The monetary threshold value in the base currency (typically INR) to compare against order ticket sizes. This value will be used with the specified operator to filter transactions.", + }, + }, + required=["startTime", "endTime", "amount", "operator"], +) + tools = ToolsSchema( standard_tools=[ get_sr_success_rate_function, @@ -1881,6 +1997,8 @@ async def update_euler_offer(params: FunctionCallParams): list_offers_by_filter_function, delete_euler_offer_function, update_euler_offer_function, + get_refund_analytics_function, + get_orders_by_amount_function, ] ) @@ -1897,4 +2015,6 @@ async def update_euler_offer(params: FunctionCallParams): "list_offers_by_filter": list_offers_by_filter, "delete_euler_offer": delete_euler_offer, "update_euler_offer": update_euler_offer, + "get_refund_analytics_by_time": get_refund_analytics_by_time, + "get_orders_by_amount": get_orders_by_amount, }