Soumik555 commited on
Commit
0f480e0
·
1 Parent(s): 8783d4a

added upstash

Browse files
pinecone_keep_alive_service.py CHANGED
@@ -3,6 +3,8 @@ import logging
3
  from datetime import datetime
4
  from dotenv import load_dotenv
5
  from pinecone import Pinecone
 
 
6
 
7
  # Configure logging
8
  logging.basicConfig(
@@ -17,8 +19,23 @@ load_dotenv()
17
  keys = os.getenv("PINECONE_API_KEYS", "").split(",")
18
 
19
 
20
- def ping_all_pinecone_indexes():
21
- results = []
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
22
 
23
  for key in filter(None, (k.strip() for k in keys)):
24
  pc = Pinecone(api_key=key)
@@ -28,39 +45,47 @@ def ping_all_pinecone_indexes():
28
  indexes = pc.list_indexes()
29
  except Exception as e:
30
  logger.error(f"[{short_key}] failed to list indexes: {e}")
31
- results.append({
32
- "service_name": "pinecone",
33
- "success": False,
34
- "error": str(e),
35
- "time": datetime.utcnow().isoformat(),
36
- "api_key": short_key,
37
- "index": None,
38
- })
 
39
  continue
40
 
41
  for index in indexes:
42
  try:
43
  stats = pc.Index(index.name).describe_index_stats()
44
- logger.info(f"[{short_key}] ping {index.name} ✓")
45
 
46
- results.append({
47
- "service_name": f"pinecone-{index.name}",
48
- "success": True,
49
- "error": None,
50
- "time": datetime.utcnow().isoformat(),
51
- "api_key": short_key,
52
- "index": index.name,
53
- "stats": stats,
54
- })
 
 
 
 
 
 
55
  except Exception as e:
56
  logger.error(f"[{short_key}] ping {index.name} ✗: {e}")
57
- results.append({
58
- "service_name": f"pinecone-{index.name}",
59
- "success": False,
60
- "error": str(e),
61
- "time": datetime.utcnow().isoformat(),
62
- "api_key": short_key,
63
- "index": index.name,
64
- })
65
-
66
- return results
 
 
 
3
  from datetime import datetime
4
  from dotenv import load_dotenv
5
  from pinecone import Pinecone
6
+ from pydantic import BaseModel
7
+ from typing import Any
8
 
9
  # Configure logging
10
  logging.basicConfig(
 
19
  keys = os.getenv("PINECONE_API_KEYS", "").split(",")
20
 
21
 
22
+
23
+ class PineconePingResponse(BaseModel):
24
+ service_name: str
25
+ success: bool
26
+ error: str | None = None
27
+ time: str
28
+ api_key: str
29
+ index: str | None = None
30
+ stats: dict[str, Any] | None = None
31
+
32
+
33
+ class PineconePingAllResponse(BaseModel):
34
+ services: list[PineconePingResponse]
35
+
36
+
37
+ def ping_all_pinecone_indexes() -> PineconePingAllResponse:
38
+ results: list[PineconePingResponse] = []
39
 
40
  for key in filter(None, (k.strip() for k in keys)):
41
  pc = Pinecone(api_key=key)
 
45
  indexes = pc.list_indexes()
46
  except Exception as e:
47
  logger.error(f"[{short_key}] failed to list indexes: {e}")
48
+ results.append(
49
+ PineconePingResponse(
50
+ service_name="pinecone",
51
+ success=False,
52
+ error=str(e),
53
+ time=datetime.utcnow().isoformat(),
54
+ api_key=short_key,
55
+ )
56
+ )
57
  continue
58
 
59
  for index in indexes:
60
  try:
61
  stats = pc.Index(index.name).describe_index_stats()
 
62
 
63
+ # 🔑 Make sure it's plain dict
64
+ stats = dict(stats) if not isinstance(stats, dict) else stats
65
+
66
+ logger.info(f"[{short_key}] ping {index.name} ✓")
67
+ results.append(
68
+ PineconePingResponse(
69
+ service_name=f"pinecone-{index.name}",
70
+ success=True,
71
+ error=None,
72
+ time=datetime.utcnow().isoformat(),
73
+ api_key=short_key,
74
+ index=index.name,
75
+ stats=stats,
76
+ )
77
+ )
78
  except Exception as e:
79
  logger.error(f"[{short_key}] ping {index.name} ✗: {e}")
80
+ results.append(
81
+ PineconePingResponse(
82
+ service_name=f"pinecone-{index.name}",
83
+ success=False,
84
+ error=str(e),
85
+ time=datetime.utcnow().isoformat(),
86
+ api_key=short_key,
87
+ index=index.name,
88
+ )
89
+ )
90
+
91
+ return PineconePingAllResponse(services=results)
redis_keep_alive_service.py CHANGED
@@ -10,8 +10,8 @@ from pydantic import BaseModel
10
  # Logging (console only)
11
  logging.basicConfig(
12
  level=logging.INFO,
13
- format='%(asctime)s - %(levelname)s - %(message)s',
14
- handlers=[logging.StreamHandler()]
15
  )
16
  logger = logging.getLogger(__name__)
17
 
@@ -29,7 +29,6 @@ REDIS_SERVICES = {
29
  "port": os.getenv("REDIS_DEVELOPMENT_PORT"),
30
  "password": os.getenv("REDIS_DEVELOPMENT_PASSWORD"),
31
  },
32
-
33
  # Upstash Redis (REST API)
34
  "upstash_dev": {
35
  "rest_url": os.getenv("UPSTASH_REDIS_DEV_REST_URL"),
@@ -42,7 +41,7 @@ REDIS_SERVICES = {
42
  }
43
 
44
 
45
- # ---------- Pydantic Response ----------
46
  class RedisPingResponse(BaseModel):
47
  service_name: str
48
  success: bool
@@ -50,6 +49,13 @@ class RedisPingResponse(BaseModel):
50
  time: str
51
  latency_ms: float | None = None
52
  type: str # "self-managed" or "upstash"
 
 
 
 
 
 
 
53
 
54
 
55
  # ---------- Self-managed Redis ----------
@@ -72,15 +78,17 @@ def ping_redis(service_name: str, redis_config: dict) -> RedisPingResponse:
72
  key = f"healthcheck:{uuid.uuid4()}"
73
  r.set(key, "ok")
74
  got = r.get(key)
 
75
 
76
- logger.info(f"{service_name} PING OK, latency {latency:.2f}ms, value={got.decode()}")
77
  return RedisPingResponse(
78
  service_name=service_name,
79
  success=True,
80
  error=None,
81
  time=now,
82
  latency_ms=latency,
83
- type="self-managed"
 
84
  )
85
  except Exception as e:
86
  error_msg = str(e)
@@ -91,13 +99,13 @@ def ping_redis(service_name: str, redis_config: dict) -> RedisPingResponse:
91
  error=error_msg,
92
  time=now,
93
  latency_ms=None,
94
- type="self-managed"
95
  )
96
 
97
 
98
  # ---------- Upstash Redis ----------
99
- def ping_upstash(redis_config):
100
- """Ping and benchmark Upstash Redis REST API."""
101
  try:
102
  headers = {"Authorization": f"Bearer {redis_config['rest_token']}"}
103
 
@@ -107,38 +115,32 @@ def ping_upstash(redis_config):
107
  resp = requests.get(url, headers=headers)
108
  latency = (datetime.now() - start_time).total_seconds() * 1000
109
 
110
- if resp.status_code == 200:
111
- try:
112
- result = resp.json().get("result")
113
- except Exception:
114
- result = resp.text.strip()
115
-
116
- if result and result.upper() == "PONG":
117
- logger.info(
118
- f"PING {redis_config['rest_url']} "
119
- f"- Response: {result}, Latency: {latency:.2f}ms"
120
- )
121
- else:
122
- logger.error(f"Unexpected Upstash PING response: {resp.status_code} - {resp.text}")
123
- return {
124
- "service_name": redis_config["rest_url"],
125
- "success": False,
126
- "error": f"Unexpected response: {resp.status_code} - {resp.text}",
127
- "time": datetime.now().isoformat(),
128
- "latency_ms": None,
129
- "type": "upstash",
130
- }
131
- else:
132
- return {
133
- "service_name": redis_config["rest_url"],
134
- "success": False,
135
- "error": f"HTTP {resp.status_code}: {resp.text}",
136
- "time": datetime.now().isoformat(),
137
- "latency_ms": None,
138
- "type": "upstash",
139
- }
140
-
141
- # ✅ If ping is OK, also test SET/GET
142
  key = f"healthcheck:{uuid.uuid4()}"
143
  value = "ok"
144
 
@@ -154,44 +156,40 @@ def ping_upstash(redis_config):
154
  if get_resp.status_code == 200:
155
  got_value = get_resp.json().get("result")
156
 
157
- return {
158
- "service_name": redis_config.get("name", "upstash"),
159
- "success": True,
160
- "error": None,
161
- "time": datetime.now().isoformat(),
162
- "latency_ms": latency,
163
- "type": "upstash",
164
- "set_latency_ms": set_latency,
165
- "get_latency_ms": get_latency,
166
- "value": got_value,
167
- }
168
-
169
  except Exception as e:
170
- logger.error(f"Failed to test Upstash: {str(e)}")
171
- return {
172
- "service_name": redis_config.get("name", "upstash"),
173
- "success": False,
174
- "error": str(e),
175
- "time": datetime.now().isoformat(),
176
- "latency_ms": None,
177
- "type": "upstash",
178
- }
179
 
180
 
181
  # ---------- Run All ----------
182
- def ping_all_redis_projects() -> list[RedisPingResponse]:
183
  logger.info("Starting Redis service health check")
184
  results: list[RedisPingResponse] = []
185
 
186
  for service_name, config in REDIS_SERVICES.items():
187
  if not config or not any(config.values()):
188
- continue # skip empty configs
189
  if "rest_url" in config: # Upstash
190
- results.append(ping_upstash(config))
191
  else: # Self-managed
192
  results.append(ping_redis(service_name, config))
193
 
194
  logger.info("Completed all Redis service checks")
195
- return results
196
-
197
-
 
10
  # Logging (console only)
11
  logging.basicConfig(
12
  level=logging.INFO,
13
+ format="%(asctime)s - %(levelname)s - %(message)s",
14
+ handlers=[logging.StreamHandler()],
15
  )
16
  logger = logging.getLogger(__name__)
17
 
 
29
  "port": os.getenv("REDIS_DEVELOPMENT_PORT"),
30
  "password": os.getenv("REDIS_DEVELOPMENT_PASSWORD"),
31
  },
 
32
  # Upstash Redis (REST API)
33
  "upstash_dev": {
34
  "rest_url": os.getenv("UPSTASH_REDIS_DEV_REST_URL"),
 
41
  }
42
 
43
 
44
+ # ---------- Pydantic Response Models ----------
45
  class RedisPingResponse(BaseModel):
46
  service_name: str
47
  success: bool
 
49
  time: str
50
  latency_ms: float | None = None
51
  type: str # "self-managed" or "upstash"
52
+ set_latency_ms: float | None = None
53
+ get_latency_ms: float | None = None
54
+ value: str | None = None
55
+
56
+
57
+ class RedisPingAllResponse(BaseModel):
58
+ services: list[RedisPingResponse]
59
 
60
 
61
  # ---------- Self-managed Redis ----------
 
78
  key = f"healthcheck:{uuid.uuid4()}"
79
  r.set(key, "ok")
80
  got = r.get(key)
81
+ got_value = got.decode() if got else None # ✅ ensure only str, not bytes or Redis object
82
 
83
+ logger.info(f"{service_name} PING OK, latency {latency:.2f}ms, value={got_value}")
84
  return RedisPingResponse(
85
  service_name=service_name,
86
  success=True,
87
  error=None,
88
  time=now,
89
  latency_ms=latency,
90
+ type="self-managed",
91
+ value=got_value,
92
  )
93
  except Exception as e:
94
  error_msg = str(e)
 
99
  error=error_msg,
100
  time=now,
101
  latency_ms=None,
102
+ type="self-managed",
103
  )
104
 
105
 
106
  # ---------- Upstash Redis ----------
107
+ def ping_upstash(service_name: str, redis_config: dict) -> RedisPingResponse:
108
+ now = datetime.utcnow().isoformat()
109
  try:
110
  headers = {"Authorization": f"Bearer {redis_config['rest_token']}"}
111
 
 
115
  resp = requests.get(url, headers=headers)
116
  latency = (datetime.now() - start_time).total_seconds() * 1000
117
 
118
+ if resp.status_code != 200:
119
+ return RedisPingResponse(
120
+ service_name=service_name,
121
+ success=False,
122
+ error=f"HTTP {resp.status_code}: {resp.text}",
123
+ time=now,
124
+ latency_ms=None,
125
+ type="upstash",
126
+ )
127
+
128
+ try:
129
+ result = resp.json().get("result")
130
+ except Exception:
131
+ result = resp.text.strip()
132
+
133
+ if not result or result.upper() != "PONG":
134
+ return RedisPingResponse(
135
+ service_name=service_name,
136
+ success=False,
137
+ error=f"Unexpected response: {resp.status_code} - {resp.text}",
138
+ time=now,
139
+ latency_ms=None,
140
+ type="upstash",
141
+ )
142
+
143
+ # SET/GET test
 
 
 
 
 
 
144
  key = f"healthcheck:{uuid.uuid4()}"
145
  value = "ok"
146
 
 
156
  if get_resp.status_code == 200:
157
  got_value = get_resp.json().get("result")
158
 
159
+ return RedisPingResponse(
160
+ service_name=service_name,
161
+ success=True,
162
+ error=None,
163
+ time=now,
164
+ latency_ms=latency,
165
+ type="upstash",
166
+ set_latency_ms=set_latency,
167
+ get_latency_ms=get_latency,
168
+ value=got_value,
169
+ )
 
170
  except Exception as e:
171
+ return RedisPingResponse(
172
+ service_name=service_name,
173
+ success=False,
174
+ error=str(e),
175
+ time=now,
176
+ latency_ms=None,
177
+ type="upstash",
178
+ )
 
179
 
180
 
181
  # ---------- Run All ----------
182
+ def ping_all_redis_projects() -> RedisPingAllResponse:
183
  logger.info("Starting Redis service health check")
184
  results: list[RedisPingResponse] = []
185
 
186
  for service_name, config in REDIS_SERVICES.items():
187
  if not config or not any(config.values()):
188
+ continue
189
  if "rest_url" in config: # Upstash
190
+ results.append(ping_upstash(service_name, config))
191
  else: # Self-managed
192
  results.append(ping_redis(service_name, config))
193
 
194
  logger.info("Completed all Redis service checks")
195
+ return RedisPingAllResponse(services=results)