thryve-mcp-server 0.0.1
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/Overview.csv +351 -0
- package/README.md +229 -0
- package/dist/category-mappings.d.ts +34 -0
- package/dist/category-mappings.d.ts.map +1 -0
- package/dist/category-mappings.js +146 -0
- package/dist/category-mappings.js.map +1 -0
- package/dist/data-enrichment.d.ts +19 -0
- package/dist/data-enrichment.d.ts.map +1 -0
- package/dist/data-enrichment.js +105 -0
- package/dist/data-enrichment.js.map +1 -0
- package/dist/data-types-generated.d.ts +70 -0
- package/dist/data-types-generated.d.ts.map +1 -0
- package/dist/data-types-generated.js +2597 -0
- package/dist/data-types-generated.js.map +1 -0
- package/dist/data-types.d.ts +53 -0
- package/dist/data-types.d.ts.map +1 -0
- package/dist/data-types.js +138 -0
- package/dist/data-types.js.map +1 -0
- package/dist/debug-logger.d.ts +17 -0
- package/dist/debug-logger.d.ts.map +1 -0
- package/dist/debug-logger.js +35 -0
- package/dist/debug-logger.js.map +1 -0
- package/dist/debug-middleware.d.ts +12 -0
- package/dist/debug-middleware.d.ts.map +1 -0
- package/dist/debug-middleware.js +36 -0
- package/dist/debug-middleware.js.map +1 -0
- package/dist/helpers.d.ts +19 -0
- package/dist/helpers.d.ts.map +1 -0
- package/dist/helpers.js +166 -0
- package/dist/helpers.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +754 -0
- package/dist/index.js.map +1 -0
- package/dist/schemas.d.ts +557 -0
- package/dist/schemas.d.ts.map +1 -0
- package/dist/schemas.js +338 -0
- package/dist/schemas.js.map +1 -0
- package/dist/tool-loader.d.ts +34 -0
- package/dist/tool-loader.d.ts.map +1 -0
- package/dist/tool-loader.js +108 -0
- package/dist/tool-loader.js.map +1 -0
- package/dist/tool-registry.d.ts +44 -0
- package/dist/tool-registry.d.ts.map +1 -0
- package/dist/tool-registry.js +54 -0
- package/dist/tool-registry.js.map +1 -0
- package/dist/tools/baseCategoryHandler.d.ts +28 -0
- package/dist/tools/baseCategoryHandler.d.ts.map +1 -0
- package/dist/tools/baseCategoryHandler.js +184 -0
- package/dist/tools/baseCategoryHandler.js.map +1 -0
- package/dist/tools/categories/getActivity.d.ts +10 -0
- package/dist/tools/categories/getActivity.d.ts.map +1 -0
- package/dist/tools/categories/getActivity.js +5 -0
- package/dist/tools/categories/getActivity.js.map +1 -0
- package/dist/tools/categories/getAudioAndHearing.d.ts +10 -0
- package/dist/tools/categories/getAudioAndHearing.d.ts.map +1 -0
- package/dist/tools/categories/getAudioAndHearing.js +5 -0
- package/dist/tools/categories/getAudioAndHearing.js.map +1 -0
- package/dist/tools/categories/getBloodGlucose.d.ts +10 -0
- package/dist/tools/categories/getBloodGlucose.d.ts.map +1 -0
- package/dist/tools/categories/getBloodGlucose.js +5 -0
- package/dist/tools/categories/getBloodGlucose.js.map +1 -0
- package/dist/tools/categories/getBodyComposition.d.ts +10 -0
- package/dist/tools/categories/getBodyComposition.d.ts.map +1 -0
- package/dist/tools/categories/getBodyComposition.js +5 -0
- package/dist/tools/categories/getBodyComposition.js.map +1 -0
- package/dist/tools/categories/getCardiovascular.d.ts +10 -0
- package/dist/tools/categories/getCardiovascular.d.ts.map +1 -0
- package/dist/tools/categories/getCardiovascular.js +5 -0
- package/dist/tools/categories/getCardiovascular.js.map +1 -0
- package/dist/tools/categories/getHeartRate.d.ts +10 -0
- package/dist/tools/categories/getHeartRate.d.ts.map +1 -0
- package/dist/tools/categories/getHeartRate.js +5 -0
- package/dist/tools/categories/getHeartRate.js.map +1 -0
- package/dist/tools/categories/getLocation.d.ts +10 -0
- package/dist/tools/categories/getLocation.d.ts.map +1 -0
- package/dist/tools/categories/getLocation.js +5 -0
- package/dist/tools/categories/getLocation.js.map +1 -0
- package/dist/tools/categories/getMicrobiome.d.ts +10 -0
- package/dist/tools/categories/getMicrobiome.d.ts.map +1 -0
- package/dist/tools/categories/getMicrobiome.js +5 -0
- package/dist/tools/categories/getMicrobiome.js.map +1 -0
- package/dist/tools/categories/getMovementAnalysis.d.ts +10 -0
- package/dist/tools/categories/getMovementAnalysis.d.ts.map +1 -0
- package/dist/tools/categories/getMovementAnalysis.js +5 -0
- package/dist/tools/categories/getMovementAnalysis.js.map +1 -0
- package/dist/tools/categories/getNutrition.d.ts +10 -0
- package/dist/tools/categories/getNutrition.d.ts.map +1 -0
- package/dist/tools/categories/getNutrition.js +5 -0
- package/dist/tools/categories/getNutrition.js.map +1 -0
- package/dist/tools/categories/getRespiratory.d.ts +10 -0
- package/dist/tools/categories/getRespiratory.d.ts.map +1 -0
- package/dist/tools/categories/getRespiratory.js +5 -0
- package/dist/tools/categories/getRespiratory.js.map +1 -0
- package/dist/tools/categories/getSleep.d.ts +10 -0
- package/dist/tools/categories/getSleep.d.ts.map +1 -0
- package/dist/tools/categories/getSleep.js +5 -0
- package/dist/tools/categories/getSleep.js.map +1 -0
- package/dist/tools/categories/getStressAndHRV.d.ts +10 -0
- package/dist/tools/categories/getStressAndHRV.d.ts.map +1 -0
- package/dist/tools/categories/getStressAndHRV.js +5 -0
- package/dist/tools/categories/getStressAndHRV.js.map +1 -0
- package/dist/tools/categories/getWellness.d.ts +10 -0
- package/dist/tools/categories/getWellness.d.ts.map +1 -0
- package/dist/tools/categories/getWellness.js +5 -0
- package/dist/tools/categories/getWellness.js.map +1 -0
- package/dist/tools/categories/getWomensHealth.d.ts +10 -0
- package/dist/tools/categories/getWomensHealth.d.ts.map +1 -0
- package/dist/tools/categories/getWomensHealth.js +5 -0
- package/dist/tools/categories/getWomensHealth.js.map +1 -0
- package/dist/tools/categories/getWorkouts.d.ts +10 -0
- package/dist/tools/categories/getWorkouts.d.ts.map +1 -0
- package/dist/tools/categories/getWorkouts.js +5 -0
- package/dist/tools/categories/getWorkouts.js.map +1 -0
- package/dist/tools/categoryTools.d.ts +100 -0
- package/dist/tools/categoryTools.d.ts.map +1 -0
- package/dist/tools/categoryTools.js +66 -0
- package/dist/tools/categoryTools.js.map +1 -0
- package/dist/tools/get.d.ts +39 -0
- package/dist/tools/get.d.ts.map +1 -0
- package/dist/tools/get.js +118 -0
- package/dist/tools/get.js.map +1 -0
- package/dist/tools/getAvailableDataTypes.d.ts +101 -0
- package/dist/tools/getAvailableDataTypes.d.ts.map +1 -0
- package/dist/tools/getAvailableDataTypes.js +120 -0
- package/dist/tools/getAvailableDataTypes.js.map +1 -0
- package/dist/tools/getConnectionWidgetUrl.d.ts +12 -0
- package/dist/tools/getConnectionWidgetUrl.d.ts.map +1 -0
- package/dist/tools/getConnectionWidgetUrl.js +26 -0
- package/dist/tools/getConnectionWidgetUrl.js.map +1 -0
- package/dist/tools/getDailyData.d.ts +30 -0
- package/dist/tools/getDailyData.d.ts.map +1 -0
- package/dist/tools/getDailyData.js +114 -0
- package/dist/tools/getDailyData.js.map +1 -0
- package/dist/tools/getEpochData.d.ts +30 -0
- package/dist/tools/getEpochData.d.ts.map +1 -0
- package/dist/tools/getEpochData.js +111 -0
- package/dist/tools/getEpochData.js.map +1 -0
- package/dist/tools/getHealthDataByCategory.d.ts +38 -0
- package/dist/tools/getHealthDataByCategory.d.ts.map +1 -0
- package/dist/tools/getHealthDataByCategory.js +231 -0
- package/dist/tools/getHealthDataByCategory.js.map +1 -0
- package/dist/tools/getUserInformation.d.ts +8 -0
- package/dist/tools/getUserInformation.d.ts.map +1 -0
- package/dist/tools/getUserInformation.js +24 -0
- package/dist/tools/getUserInformation.js.map +1 -0
- package/dist/tools/index.d.ts +7 -0
- package/dist/tools/index.d.ts.map +1 -0
- package/dist/tools/index.js +12 -0
- package/dist/tools/index.js.map +1 -0
- package/dist/tools/legacy.d.ts +37 -0
- package/dist/tools/legacy.d.ts.map +1 -0
- package/dist/tools/legacy.js +105 -0
- package/dist/tools/legacy.js.map +1 -0
- package/dist/tools/listConnectedSources.d.ts +11 -0
- package/dist/tools/listConnectedSources.d.ts.map +1 -0
- package/dist/tools/listConnectedSources.js +29 -0
- package/dist/tools/listConnectedSources.js.map +1 -0
- package/dist/tools/listDevices.d.ts +11 -0
- package/dist/tools/listDevices.d.ts.map +1 -0
- package/dist/tools/listDevices.js +29 -0
- package/dist/tools/listDevices.js.map +1 -0
- package/dist/tools/search-filters.d.ts +42 -0
- package/dist/tools/search-filters.d.ts.map +1 -0
- package/dist/tools/search-filters.js +210 -0
- package/dist/tools/search-filters.js.map +1 -0
- package/dist/tools/search-keyword.d.ts +32 -0
- package/dist/tools/search-keyword.d.ts.map +1 -0
- package/dist/tools/search-keyword.js +122 -0
- package/dist/tools/search-keyword.js.map +1 -0
- package/dist/tools/search-tools.d.ts +8 -0
- package/dist/tools/search-tools.d.ts.map +1 -0
- package/dist/tools/search-tools.js +273 -0
- package/dist/tools/search-tools.js.map +1 -0
- package/dist/types.d.ts +37 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +2 -0
- package/dist/types.js.map +1 -0
- package/package.json +30 -0
- package/parse-csv.py +152 -0
- package/src/category-mappings.ts +181 -0
- package/src/data-enrichment.ts +125 -0
- package/src/data-types-generated.ts +2652 -0
- package/src/helpers.ts +198 -0
- package/src/index.ts +859 -0
- package/src/schemas.ts +372 -0
- package/src/tools/baseCategoryHandler.ts +243 -0
- package/src/tools/categoryTools.ts +101 -0
- package/src/tools/get.ts +147 -0
- package/src/tools/getAvailableDataTypes.ts +148 -0
- package/src/tools/index.ts +32 -0
- package/src/tools/listConnectedSources.ts +45 -0
- package/src/tools/listDevices.ts +45 -0
- package/src/tools/search-filters.ts +253 -0
- package/src/tools/search-keyword.ts +162 -0
- package/src/types.ts +44 -0
- package/tsconfig.json +20 -0
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Category mappings for LLM-friendly health data access
|
|
3
|
+
* Maps high-level categories to Thryve data type IDs
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import { ALL_DATA_TYPES } from "./data-types-generated.js";
|
|
7
|
+
|
|
8
|
+
export type HealthCategory =
|
|
9
|
+
| "Activity"
|
|
10
|
+
| "Heart Rate"
|
|
11
|
+
| "Sleep"
|
|
12
|
+
| "Workouts"
|
|
13
|
+
| "Stress & HRV"
|
|
14
|
+
| "Respiratory"
|
|
15
|
+
| "Blood Glucose"
|
|
16
|
+
| "Body Composition"
|
|
17
|
+
| "Womens Health"
|
|
18
|
+
| "Nutrition"
|
|
19
|
+
| "Cardiovascular"
|
|
20
|
+
| "Wellness"
|
|
21
|
+
| "Audio & Hearing"
|
|
22
|
+
| "Microbiome"
|
|
23
|
+
| "Location"
|
|
24
|
+
| "Movement Analysis";
|
|
25
|
+
|
|
26
|
+
interface CategoryMapping {
|
|
27
|
+
thryveCategories: string[];
|
|
28
|
+
description: string;
|
|
29
|
+
dataTypeIds: number[];
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Build category mappings dynamically from data types
|
|
34
|
+
*/
|
|
35
|
+
function buildCategoryMappings(): Record<HealthCategory, CategoryMapping> {
|
|
36
|
+
const mappings: Record<string, CategoryMapping> = {
|
|
37
|
+
"Activity": {
|
|
38
|
+
thryveCategories: ["Activity"],
|
|
39
|
+
description: "Steps, distance, floors climbed, elevation, calories burned, and general activity metrics",
|
|
40
|
+
dataTypeIds: [],
|
|
41
|
+
},
|
|
42
|
+
"Heart Rate": {
|
|
43
|
+
thryveCategories: ["Heart Rate"],
|
|
44
|
+
description: "Heart rate measurements including resting, average, min, max, and variability",
|
|
45
|
+
dataTypeIds: [],
|
|
46
|
+
},
|
|
47
|
+
"Sleep": {
|
|
48
|
+
thryveCategories: ["Sleep"],
|
|
49
|
+
description: "Sleep duration, stages, quality, and sleep-related metrics",
|
|
50
|
+
dataTypeIds: [],
|
|
51
|
+
},
|
|
52
|
+
"Workouts": {
|
|
53
|
+
thryveCategories: ["Workouts"],
|
|
54
|
+
description: "Exercise sessions, workout types, duration, and performance metrics",
|
|
55
|
+
dataTypeIds: [],
|
|
56
|
+
},
|
|
57
|
+
"Stress & HRV": {
|
|
58
|
+
thryveCategories: ["Stress & HRV"],
|
|
59
|
+
description: "Stress levels, heart rate variability, and recovery metrics",
|
|
60
|
+
dataTypeIds: [],
|
|
61
|
+
},
|
|
62
|
+
"Respiratory": {
|
|
63
|
+
thryveCategories: ["Respiratory & Breathing"],
|
|
64
|
+
description: "Breathing rate, SpO2, respiratory patterns, and lung function",
|
|
65
|
+
dataTypeIds: [],
|
|
66
|
+
},
|
|
67
|
+
"Blood Glucose": {
|
|
68
|
+
thryveCategories: ["Blood Glucose"],
|
|
69
|
+
description: "Blood glucose levels and continuous glucose monitoring (CGM) data",
|
|
70
|
+
dataTypeIds: [],
|
|
71
|
+
},
|
|
72
|
+
"Body Composition": {
|
|
73
|
+
thryveCategories: ["Body Composition & Measurements"],
|
|
74
|
+
description: "Weight, BMI, body fat percentage, muscle mass, and body measurements",
|
|
75
|
+
dataTypeIds: [],
|
|
76
|
+
},
|
|
77
|
+
"Womens Health": {
|
|
78
|
+
thryveCategories: ["Women's Health"],
|
|
79
|
+
description: "Menstrual cycle tracking, ovulation, symptoms, and reproductive health",
|
|
80
|
+
dataTypeIds: [],
|
|
81
|
+
},
|
|
82
|
+
"Nutrition": {
|
|
83
|
+
thryveCategories: ["Detailed Nutrition"],
|
|
84
|
+
description: "Nutritional intake including calories, macros, micros, hydration, and meal data",
|
|
85
|
+
dataTypeIds: [],
|
|
86
|
+
},
|
|
87
|
+
"Cardiovascular": {
|
|
88
|
+
thryveCategories: ["Cardiovascular Health", "Advanced Cardiac Analysis"],
|
|
89
|
+
description: "Blood pressure, VO2 max, cardiac analysis, and cardiovascular health metrics",
|
|
90
|
+
dataTypeIds: [],
|
|
91
|
+
},
|
|
92
|
+
"Wellness": {
|
|
93
|
+
thryveCategories: ["Self-Reported Wellness"],
|
|
94
|
+
description: "General wellness, mood, energy levels, and self-reported health data",
|
|
95
|
+
dataTypeIds: [],
|
|
96
|
+
},
|
|
97
|
+
"Audio & Hearing": {
|
|
98
|
+
thryveCategories: ["Audio & Hearing Health"],
|
|
99
|
+
description: "Hearing health, audio exposure, and environmental sound levels",
|
|
100
|
+
dataTypeIds: [],
|
|
101
|
+
},
|
|
102
|
+
"Microbiome": {
|
|
103
|
+
thryveCategories: ["Microbiome & Gut Health"],
|
|
104
|
+
description: "Gut health, microbiome composition, and digestive metrics",
|
|
105
|
+
dataTypeIds: [],
|
|
106
|
+
},
|
|
107
|
+
"Location": {
|
|
108
|
+
thryveCategories: ["Location & GPS"],
|
|
109
|
+
description: "GPS coordinates, routes, and location tracking data",
|
|
110
|
+
dataTypeIds: [],
|
|
111
|
+
},
|
|
112
|
+
"Movement Analysis": {
|
|
113
|
+
thryveCategories: ["Movement Analysis"],
|
|
114
|
+
description: "Movement patterns, gait analysis, and biomechanics",
|
|
115
|
+
dataTypeIds: [],
|
|
116
|
+
},
|
|
117
|
+
};
|
|
118
|
+
|
|
119
|
+
// Build data type ID lists by matching categories
|
|
120
|
+
for (const dataType of ALL_DATA_TYPES) {
|
|
121
|
+
for (const [category, mapping] of Object.entries(mappings)) {
|
|
122
|
+
// Check if this data type's category matches any of the mapping's Thryve categories
|
|
123
|
+
const matches = mapping.thryveCategories.some((thryveCategory) => {
|
|
124
|
+
// Handle compound categories like "Activity,Workouts"
|
|
125
|
+
const dataTypeCategories = dataType.category.split(",").map((c) => c.trim());
|
|
126
|
+
return dataTypeCategories.includes(thryveCategory);
|
|
127
|
+
});
|
|
128
|
+
|
|
129
|
+
if (matches) {
|
|
130
|
+
mapping.dataTypeIds.push(dataType.id);
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
return mappings as Record<HealthCategory, CategoryMapping>;
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
// Build mappings once at module load time
|
|
139
|
+
export const CATEGORY_MAPPINGS = buildCategoryMappings();
|
|
140
|
+
|
|
141
|
+
/**
|
|
142
|
+
* Get all data type IDs for given categories
|
|
143
|
+
*/
|
|
144
|
+
export function getDataTypeIdsForCategories(categories: HealthCategory[]): number[] {
|
|
145
|
+
const allIds = new Set<number>();
|
|
146
|
+
|
|
147
|
+
for (const category of categories) {
|
|
148
|
+
const mapping = CATEGORY_MAPPINGS[category];
|
|
149
|
+
if (mapping) {
|
|
150
|
+
mapping.dataTypeIds.forEach((id) => allIds.add(id));
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
return Array.from(allIds);
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
/**
|
|
158
|
+
* Get category information for display
|
|
159
|
+
*/
|
|
160
|
+
export function getCategoryInfo(category: HealthCategory): CategoryMapping | undefined {
|
|
161
|
+
return CATEGORY_MAPPINGS[category];
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
/**
|
|
165
|
+
* Get all available categories
|
|
166
|
+
*/
|
|
167
|
+
export function getAllCategories(): HealthCategory[] {
|
|
168
|
+
return Object.keys(CATEGORY_MAPPINGS) as HealthCategory[];
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
/**
|
|
172
|
+
* Get category statistics
|
|
173
|
+
*/
|
|
174
|
+
export function getCategoryStats() {
|
|
175
|
+
return Object.entries(CATEGORY_MAPPINGS).map(([category, mapping]) => ({
|
|
176
|
+
category,
|
|
177
|
+
description: mapping.description,
|
|
178
|
+
dataTypeCount: mapping.dataTypeIds.length,
|
|
179
|
+
thryveCategories: mapping.thryveCategories,
|
|
180
|
+
}));
|
|
181
|
+
}
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared data enrichment utilities for health data
|
|
3
|
+
* Used by getDailyData, getEpochData, and getHealthDataByCategory
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import type { HealthDataRecord } from "./types.js";
|
|
7
|
+
import { getDataTypeById } from "./data-types-generated.js";
|
|
8
|
+
import { generateRecordId } from "./helpers.js";
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* Flatten Thryve API response structure into flat array of records
|
|
12
|
+
*/
|
|
13
|
+
export function flattenThryveResponse(data: any): HealthDataRecord[] {
|
|
14
|
+
const records: HealthDataRecord[] = [];
|
|
15
|
+
|
|
16
|
+
if (!Array.isArray(data)) {
|
|
17
|
+
return records;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
for (const item of data) {
|
|
21
|
+
if (item.dataSources && Array.isArray(item.dataSources)) {
|
|
22
|
+
for (const dataSource of item.dataSources) {
|
|
23
|
+
if (dataSource.data && Array.isArray(dataSource.data)) {
|
|
24
|
+
for (const record of dataSource.data) {
|
|
25
|
+
records.push({
|
|
26
|
+
...record,
|
|
27
|
+
dataSource: dataSource.dataSource,
|
|
28
|
+
dataSourceName: dataSource.dataSourceName,
|
|
29
|
+
_recordId: generateRecordId({ ...record, dataSource: dataSource.dataSource }),
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
return records;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* Enrich records with data type metadata (name, category, unit)
|
|
42
|
+
*/
|
|
43
|
+
export function enrichWithDataTypes(records: HealthDataRecord[]): void {
|
|
44
|
+
for (const record of records) {
|
|
45
|
+
const typeId =
|
|
46
|
+
record.dailyDynamicValueType ||
|
|
47
|
+
record.dynamicValueType ||
|
|
48
|
+
record.dynamicEpochValueType;
|
|
49
|
+
|
|
50
|
+
if (typeId) {
|
|
51
|
+
const dataType = getDataTypeById(typeId);
|
|
52
|
+
if (dataType) {
|
|
53
|
+
// Set appropriate type name based on the type ID field
|
|
54
|
+
if (record.dailyDynamicValueType) {
|
|
55
|
+
record.dailyDynamicValueTypeName = dataType.name;
|
|
56
|
+
}
|
|
57
|
+
if (record.dynamicValueType || record.dynamicEpochValueType) {
|
|
58
|
+
record.dynamicValueTypeName = dataType.name;
|
|
59
|
+
record.dynamicEpochValueTypeName = dataType.name;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
record.category = dataType.category;
|
|
63
|
+
record.unit = dataType.unit;
|
|
64
|
+
record.dataType = typeId;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* Rebuild Thryve API response structure from flattened records
|
|
72
|
+
* Groups records by dataSource
|
|
73
|
+
*/
|
|
74
|
+
export function rebuildThryveResponse(records: HealthDataRecord[]): any[] {
|
|
75
|
+
if (records.length === 0) {
|
|
76
|
+
return [];
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
// Group records by data source
|
|
80
|
+
const groupedBySource = new Map<number, HealthDataRecord[]>();
|
|
81
|
+
|
|
82
|
+
for (const record of records) {
|
|
83
|
+
const sourceId = record.dataSource || 0;
|
|
84
|
+
if (!groupedBySource.has(sourceId)) {
|
|
85
|
+
groupedBySource.set(sourceId, []);
|
|
86
|
+
}
|
|
87
|
+
groupedBySource.get(sourceId)!.push(record);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
// Rebuild structure
|
|
91
|
+
const result: any[] = [];
|
|
92
|
+
|
|
93
|
+
for (const [dataSource, sourceRecords] of groupedBySource) {
|
|
94
|
+
// Extract first record to get authToken (if present)
|
|
95
|
+
const firstRecord = sourceRecords[0];
|
|
96
|
+
const authToken = (firstRecord as any).authenticationToken;
|
|
97
|
+
|
|
98
|
+
const dataSourceObj: any = {
|
|
99
|
+
dataSource,
|
|
100
|
+
data: sourceRecords.map((record) => {
|
|
101
|
+
// Remove internal fields
|
|
102
|
+
const { dataSource: _ds, dataSourceName: _dsName, _recordId, ...cleanRecord } = record;
|
|
103
|
+
return cleanRecord;
|
|
104
|
+
}),
|
|
105
|
+
};
|
|
106
|
+
|
|
107
|
+
// Add dataSourceName if available
|
|
108
|
+
if (sourceRecords[0].dataSourceName) {
|
|
109
|
+
dataSourceObj.dataSourceName = sourceRecords[0].dataSourceName;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
const responseItem: any = {
|
|
113
|
+
dataSources: [dataSourceObj],
|
|
114
|
+
};
|
|
115
|
+
|
|
116
|
+
// Add authToken if present
|
|
117
|
+
if (authToken) {
|
|
118
|
+
responseItem.authenticationToken = authToken;
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
result.push(responseItem);
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
return result;
|
|
125
|
+
}
|