import json, os, sys, time, hmac, hashlib, base64 import urllib.parse, urllib.request, urllib.error def _cfg(): return json.loads(os.environ.get("INTEGRATION_SECRETS", "{}")) def _inputs(): return json.loads(os.environ.get("INTEGRATION_INPUTS", "{}")) def request(method, api_path, cfg, body=None): # api_path MUST include the leading /api/v3/... and any ?query string. base = str(cfg.get("base_url", "")).rstrip("/") url = base + api_path timestamp = str(int(time.time())) to_sign = api_path + ":" + method.upper() + ":" + timestamp secret = str(cfg.get("api_secret_key", "")).encode("utf-8") signature = base64.b64encode(hmac.new(secret, to_sign.encode("utf-8"), hashlib.sha256).digest()).decode("utf-8") authorization = "TC " + str(cfg.get("access_id", "")) + ":" + signature data = json.dumps(body).encode("utf-8") if body is not None else None headers = {"Authorization": authorization, "Timestamp": timestamp, "Accept": "application/json"} if data is not None: headers["Content-Type"] = "application/json" req = urllib.request.Request(url, data=data, headers=headers, method=method) with urllib.request.urlopen(req, timeout=60) as r: raw = r.read() return json.loads(raw) if raw else {} def _run(fn): try: print(json.dumps(fn(_cfg(), _inputs()))) except urllib.error.HTTPError as e: print(json.dumps({"error": "HTTP " + str(e.code), "detail": e.read().decode("utf-8", "replace")})) sys.exit(1) except Exception as e: print(json.dumps({"error": str(e)})) sys.exit(1) def main(cfg, inputs): indicator_id = inputs.get("indicator_id") if not indicator_id: raise Exception("indicator_id is required") q = lambda v: urllib.parse.quote(str(v), safe="") path = "/api/v3/indicators/" + q(indicator_id) result = request("DELETE", path, cfg) if not result: return {"ok": True, "deleted": indicator_id} return result _run(main)