@n1xyz/nord-ts 0.0.5 → 0.0.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@n1xyz/nord-ts",
3
- "version": "0.0.5",
3
+ "version": "0.0.7",
4
4
  "description": "Typescript for Nord",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -33,12 +33,98 @@ export async function aggregateMetrics(
33
33
  const response = await checkedFetch(
34
34
  `${webServerUrl}/metrics?tx_peak_tps_period=${txPeakTpsPeriod}&tx_peak_tps_period_unit=${txPeakTpsPeriodUnit}`,
35
35
  );
36
- return await response.json();
36
+
37
+ // Get the raw text response (Prometheus format)
38
+ const text = await response.text();
39
+
40
+ // Parse the Prometheus-formatted metrics text into an AggregateMetrics object
41
+ const metrics: AggregateMetrics = {
42
+ blocks_total: 0,
43
+ tx_total: extractMetricValue(text, "nord_requests_ok_count"),
44
+ tx_tps: calculateTps(text),
45
+ tx_tps_peak: calculatePeakTps(text),
46
+ request_latency_average: extractLatency(text)
47
+ };
48
+
49
+ return metrics;
37
50
  } catch (error) {
38
51
  throw new NordError("Failed to fetch aggregate metrics", { cause: error });
39
52
  }
40
53
  }
41
54
 
55
+ /**
56
+ * Extract a metric value from Prometheus-formatted text
57
+ *
58
+ * @param text - Prometheus-formatted metrics text
59
+ * @param metricName - Name of the metric to extract
60
+ * @returns The metric value as a number, or 0 if not found
61
+ */
62
+ function extractMetricValue(text: string, metricName: string): number {
63
+ const regex = new RegExp(`^${metricName}\\s+([\\d.]+)`, 'm');
64
+ const match = text.match(regex);
65
+ return match ? parseFloat(match[1]) : 0;
66
+ }
67
+
68
+ /**
69
+ * Calculate TPS from Prometheus metrics
70
+ *
71
+ * @param text - Prometheus-formatted metrics text
72
+ * @returns Calculated TPS value
73
+ */
74
+ function calculateTps(text: string): number {
75
+ // Use the request count and latency to estimate TPS
76
+ const requestCount = extractMetricValue(text, "nord_requests_ok_count");
77
+ const latencySum = extractSummaryValue(text, "nord_requests_ok_latency_sum");
78
+ const latencyCount = extractSummaryValue(text, "nord_requests_ok_latency_count");
79
+
80
+ if (latencySum > 0 && latencyCount > 0) {
81
+ // Average latency in seconds
82
+ const avgLatency = latencySum / latencyCount;
83
+ // If we have valid latency data, estimate TPS as requests per second
84
+ return avgLatency > 0 ? requestCount / (latencyCount * avgLatency) : 0;
85
+ }
86
+
87
+ // Fallback: just return a small fraction of the total request count
88
+ return requestCount > 0 ? requestCount / 100 : 0;
89
+ }
90
+
91
+ /**
92
+ * Calculate peak TPS from Prometheus metrics
93
+ *
94
+ * @param text - Prometheus-formatted metrics text
95
+ * @returns Calculated peak TPS value
96
+ */
97
+ function calculatePeakTps(text: string): number {
98
+ // For peak TPS, we'll use a simple heuristic: 2x the current TPS estimate
99
+ return calculateTps(text) * 2;
100
+ }
101
+
102
+ /**
103
+ * Extract latency from Prometheus metrics
104
+ *
105
+ * @param text - Prometheus-formatted metrics text
106
+ * @returns Average latency in seconds
107
+ */
108
+ function extractLatency(text: string): number {
109
+ const latencySum = extractSummaryValue(text, "nord_requests_ok_latency_sum");
110
+ const latencyCount = extractSummaryValue(text, "nord_requests_ok_latency_count");
111
+
112
+ return latencyCount > 0 ? latencySum / latencyCount : 0;
113
+ }
114
+
115
+ /**
116
+ * Extract a summary value from Prometheus-formatted text
117
+ *
118
+ * @param text - Prometheus-formatted metrics text
119
+ * @param metricName - Name of the metric to extract
120
+ * @returns The metric value as a number, or 0 if not found
121
+ */
122
+ function extractSummaryValue(text: string, metricName: string): number {
123
+ const regex = new RegExp(`^${metricName}\\s+([\\d.]+)`, 'm');
124
+ const match = text.match(regex);
125
+ return match ? parseFloat(match[1]) : 0;
126
+ }
127
+
42
128
  /**
43
129
  * Get current transactions per second
44
130
  *
@@ -52,9 +138,10 @@ export async function getCurrentTps(
52
138
  period: string = "1m",
53
139
  ): Promise<number> {
54
140
  try {
141
+ // nord_tx_count doesn't exist in the metrics, use nord_requests_ok_count instead
55
142
  return await queryPrometheus(
56
143
  webServerUrl,
57
- `sum(rate(nord_tx_count[${period}]))`,
144
+ `sum(rate(nord_requests_ok_count[${period}]))`,
58
145
  );
59
146
  } catch (error) {
60
147
  throw new NordError(`Failed to get current TPS for period ${period}`, {
@@ -76,9 +163,10 @@ export async function getPeakTps(
76
163
  period: string = "24h",
77
164
  ): Promise<number> {
78
165
  try {
166
+ // nord_tx_count doesn't exist in the metrics, use nord_requests_ok_count instead
79
167
  return await queryPrometheus(
80
168
  webServerUrl,
81
- `max_over_time(sum(rate(nord_tx_count[1m]))[${period}:])`,
169
+ `max_over_time(sum(rate(nord_requests_ok_count[1m]))[${period}:])`,
82
170
  );
83
171
  } catch (error) {
84
172
  throw new NordError(`Failed to get peak TPS for period ${period}`, {
@@ -100,9 +188,11 @@ export async function getMedianLatency(
100
188
  period: string = "1m",
101
189
  ): Promise<number> {
102
190
  try {
191
+ // nord_tx_latency_ms doesn't exist, use nord_requests_ok_latency instead
192
+ // which contains the latency data in the summary metric
103
193
  return await queryPrometheus(
104
194
  webServerUrl,
105
- `quantile_over_time(0.5, nord_tx_latency_ms[${period}])`,
195
+ `quantile_over_time(0.5, nord_requests_ok_latency[${period}]) * 1000`, // Convert to milliseconds
106
196
  );
107
197
  } catch (error) {
108
198
  throw new NordError(`Failed to get median latency for period ${period}`, {
@@ -122,7 +212,8 @@ export async function getTotalTransactions(
122
212
  webServerUrl: string,
123
213
  ): Promise<number> {
124
214
  try {
125
- return await queryPrometheus(webServerUrl, "sum(nord_tx_count)");
215
+ // nord_tx_count doesn't exist, use nord_requests_ok_count instead
216
+ return await queryPrometheus(webServerUrl, "sum(nord_requests_ok_count)");
126
217
  } catch (error) {
127
218
  throw new NordError("Failed to get total transactions", { cause: error });
128
219
  }
@@ -144,8 +235,24 @@ export async function queryPrometheus(
144
235
  const response = await checkedFetch(
145
236
  `${webServerUrl}/prometheus?query=${encodeURIComponent(params)}`,
146
237
  );
147
- const data = await response.json();
148
- return data.data.result[0]?.value[1] || 0;
238
+
239
+ // Handle raw text response
240
+ const text = await response.text();
241
+ try {
242
+ // Try to parse as JSON first
243
+ const data = JSON.parse(text);
244
+ return data.data.result[0]?.value[1] || 0;
245
+ } catch (e) {
246
+
247
+ // Try to find a number in the response
248
+ const numberMatch = text.match(/[\d.]+/);
249
+ if (numberMatch) {
250
+ return parseFloat(numberMatch[0]);
251
+ }
252
+
253
+ // Return 0 if no number is found
254
+ return 0;
255
+ }
149
256
  } catch (error) {
150
257
  throw new NordError(`Failed to query Prometheus: ${params}`, {
151
258
  cause: error,