#!/usr/bin/env python3
import argparse
import asyncio
import json
import sys

try:
    from nepse import Nepse, AsyncNepse
except Exception as exc:  # pragma: no cover
    print(json.dumps({"ok": False, "error": f"ImportError: {exc}"}))
    sys.exit(1)


async def async_call(method: str, args: dict):
    client = AsyncNepse()
    try:
        client.setTLSVerification(False)
    except Exception:
        pass

    m = method
    # no-arg methods
    if m in {
        "getCompanyList",
        "getSecurityList",
        "getSectorScrips",
        "getLiveMarket",
        "getPriceVolume",
        "getSummary",
        "getTopTenTradeScrips",
        "getTopTenTransactionScrips",
        "getTopTenTurnoverScrips",
        "getSupplyDemand",
        "getTopGainers",
        "getTopLosers",
        "isNepseOpen",
        "getNepseIndex",
        "getNepseSubIndices",
        "getDailyNepseIndexGraph",
        "getDailySensitiveIndexGraph",
        "getDailyFloatIndexGraph",
        "getDailySensitiveFloatIndexGraph",
        "getDailyBankSubindexGraph",
        "getDailyDevelopmentBankSubindexGraph",
        "getDailyFinanceSubindexGraph",
        "getDailyHotelTourismSubindexGraph",
        "getDailyHydroSubindexGraph",
        "getDailyInvestmentSubindexGraph",
        "getDailyLifeInsuranceSubindexGraph",
        "getDailyManufacturingSubindexGraph",
        "getDailyMicrofinanceSubindexGraph",
        "getDailyMutualfundSubindexGraph",
        "getDailyNonLifeInsuranceSubindexGraph",
        "getDailyOthersSubindexGraph",
        "getDailyTradingSubindexGraph",
    }:
        return await getattr(client, m)()

    # with args
    if m == "getFloorSheet":
        show_progress = bool(args.get("show_progress", False))
        return await client.getFloorSheet(show_progress=show_progress)
    if m == "getFloorSheetOf":
        symbol = args.get("symbol")
        business_date = args.get("business_date")
        if not symbol:
            raise ValueError("symbol is required")
        return await client.getFloorSheetOf(symbol, business_date=business_date)
    if m == "getCompanyPriceVolumeHistory":
        symbol = args.get("symbol")
        start_date = args.get("start_date")
        end_date = args.get("end_date")
        if not symbol:
            raise ValueError("symbol is required")
        return await client.getCompanyPriceVolumeHistory(symbol, start_date, end_date)
    if m == "getDailyScripPriceGraph":
        symbol = args.get("symbol")
        if not symbol:
            raise ValueError("symbol is required")
        return await client.getDailyScripPriceGraph(symbol)
    if m == "getCompanyDetails":
        symbol = args.get("symbol")
        if not symbol:
            raise ValueError("symbol is required")
        return await client.getCompanyDetails(symbol)
    if m == "getSymbolMarketDepth":
        symbol = args.get("symbol")
        if not symbol:
            raise ValueError("symbol is required")
        return await client.getSymbolMarketDepth(symbol)

    raise ValueError(f"Unsupported method: {method}")


def sync_call(method: str, args: dict):
    client = Nepse()
    try:
        client.setTLSVerification(False)
    except Exception:
        pass

    m = method
    if m in {
        "getCompanyList",
        "getSecurityList",
        "getSectorScrips",
        "getLiveMarket",
        "getPriceVolume",
        "getSummary",
        "getTopTenTradeScrips",
        "getTopTenTransactionScrips",
        "getTopTenTurnoverScrips",
        "getSupplyDemand",
        "getTopGainers",
        "getTopLosers",
        "isNepseOpen",
        "getNepseIndex",
        "getNepseSubIndices",
        "getDailyNepseIndexGraph",
        "getDailySensitiveIndexGraph",
        "getDailyFloatIndexGraph",
        "getDailySensitiveFloatIndexGraph",
        "getDailyBankSubindexGraph",
        "getDailyDevelopmentBankSubindexGraph",
        "getDailyFinanceSubindexGraph",
        "getDailyHotelTourismSubindexGraph",
        "getDailyHydroSubindexGraph",
        "getDailyInvestmentSubindexGraph",
        "getDailyLifeInsuranceSubindexGraph",
        "getDailyManufacturingSubindexGraph",
        "getDailyMicrofinanceSubindexGraph",
        "getDailyMutualfundSubindexGraph",
        "getDailyNonLifeInsuranceSubindexGraph",
        "getDailyOthersSubindexGraph",
        "getDailyTradingSubindexGraph",
    }:
        return getattr(client, m)()

    if m == "getFloorSheet":
        show_progress = bool(args.get("show_progress", False))
        return client.getFloorSheet(show_progress=show_progress)
    if m == "getFloorSheetOf":
        symbol = args.get("symbol")
        business_date = args.get("business_date")
        if not symbol:
            raise ValueError("symbol is required")
        return client.getFloorSheetOf(symbol, business_date=business_date)
    if m == "getCompanyPriceVolumeHistory":
        symbol = args.get("symbol")
        start_date = args.get("start_date")
        end_date = args.get("end_date")
        if not symbol:
            raise ValueError("symbol is required")
        return client.getCompanyPriceVolumeHistory(symbol, start_date, end_date)
    if m == "getDailyScripPriceGraph":
        symbol = args.get("symbol")
        if not symbol:
            raise ValueError("symbol is required")
        return client.getDailyScripPriceGraph(symbol)
    if m == "getCompanyDetails":
        symbol = args.get("symbol")
        if not symbol:
            raise ValueError("symbol is required")
        return client.getCompanyDetails(symbol)
    if m == "getSymbolMarketDepth":
        symbol = args.get("symbol")
        if not symbol:
            raise ValueError("symbol is required")
        return client.getSymbolMarketDepth(symbol)

    raise ValueError(f"Unsupported method: {method}")


def main():
    parser = argparse.ArgumentParser()
    parser.add_argument("--method", required=True)
    parser.add_argument("--args", default="{}")
    parser.add_argument("--async", dest="is_async", action="store_true")
    args = parser.parse_args()

    try:
        payload = json.loads(args.args) if args.args else {}
    except Exception:
        payload = {}

    try:
        if args.is_async:
            result = asyncio.run(async_call(args.method, payload))
        else:
            result = sync_call(args.method, payload)
        print(json.dumps({"ok": True, "data": result}, default=str))
    except Exception as exc:
        print(json.dumps({"ok": False, "error": str(exc)}))
        sys.exit(2)


if __name__ == "__main__":
    main()


