Skip to content

Commit 8ed0447

Browse files
committed
fix: respect using custom datasource when configured in jsonData
1 parent 53d1ef7 commit 8ed0447

File tree

4 files changed

+148
-18
lines changed

4 files changed

+148
-18
lines changed

src/datasource/DataSource.test.ts

Lines changed: 113 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
1+
import { config } from '@grafana/runtime';
12
import { BASIC_CHECK_ALERTS } from 'test/fixtures/checkAlerts';
23
import { BASIC_HTTP_CHECK } from 'test/fixtures/checks';
3-
import { SM_DATASOURCE } from 'test/fixtures/datasources';
4+
import { LOGS_DATASOURCE, METRICS_DATASOURCE, SM_DATASOURCE } from 'test/fixtures/datasources';
45
import { PRIVATE_PROBE } from 'test/fixtures/probes';
56
import { apiRoute, ApiRoutes, getServerRequests } from 'test/handlers';
67
import { server } from 'test/server';
@@ -144,4 +145,115 @@ describe('SMDataSource', () => {
144145
expect(request.headers.get('X-Client-ID')).toEqual(process.env.SM_PLUGIN_ID);
145146
expect(request.headers.get('X-Client-Version')).toEqual(process.env.SM_PLUGIN_VERSION);
146147
});
148+
149+
describe('getLogsDS', () => {
150+
beforeEach(() => {
151+
config.datasources = {};
152+
});
153+
154+
it('should return the configured datasource when it exists', () => {
155+
config.datasources = {
156+
[LOGS_DATASOURCE.name]: LOGS_DATASOURCE,
157+
};
158+
159+
const smDataSource = new SMDataSource(SM_DATASOURCE);
160+
const result = smDataSource.getLogsDS();
161+
162+
expect(result).toEqual(LOGS_DATASOURCE);
163+
expect(result?.uid).toEqual('P4DC6B4C9A7FFCC6C');
164+
});
165+
166+
it('should fall back to default grafanacloud-logs UID when configured datasource does not exist', () => {
167+
const defaultLogsDS = { ...LOGS_DATASOURCE, uid: 'grafanacloud-logs' };
168+
config.datasources = {
169+
[defaultLogsDS.name]: defaultLogsDS,
170+
};
171+
172+
const smDataSourceWithMissingConfig = new SMDataSource({
173+
...SM_DATASOURCE,
174+
jsonData: {
175+
...SM_DATASOURCE.jsonData,
176+
logs: {
177+
...SM_DATASOURCE.jsonData.logs,
178+
uid: 'non-existent-uid',
179+
},
180+
},
181+
});
182+
183+
const result = smDataSourceWithMissingConfig.getLogsDS();
184+
185+
expect(result).toEqual(defaultLogsDS);
186+
expect(result?.uid).toEqual('grafanacloud-logs');
187+
});
188+
189+
it('should respect custom datasource configuration', () => {
190+
const lbacLogsDS = {
191+
...LOGS_DATASOURCE,
192+
uid: 'grafanacloud-logs-lbac',
193+
name: 'grafanacloud-ckbedwellksix-logs-lbac',
194+
};
195+
196+
config.datasources = {
197+
[lbacLogsDS.name]: lbacLogsDS,
198+
};
199+
200+
const smDataSourceWithLBAC = new SMDataSource({
201+
...SM_DATASOURCE,
202+
jsonData: {
203+
...SM_DATASOURCE.jsonData,
204+
logs: {
205+
...SM_DATASOURCE.jsonData.logs,
206+
uid: 'grafanacloud-logs-lbac',
207+
grafanaName: 'grafanacloud-ckbedwellksix-logs-lbac',
208+
},
209+
},
210+
});
211+
212+
const result = smDataSourceWithLBAC.getLogsDS();
213+
214+
expect(result).toEqual(lbacLogsDS);
215+
expect(result?.uid).toEqual('grafanacloud-logs-lbac');
216+
});
217+
});
218+
219+
describe('getMetricsDS', () => {
220+
beforeEach(() => {
221+
config.datasources = {};
222+
});
223+
224+
it('should return the configured datasource when it exists', () => {
225+
config.datasources = {
226+
[METRICS_DATASOURCE.name]: METRICS_DATASOURCE,
227+
};
228+
229+
const smDataSource = new SMDataSource(SM_DATASOURCE);
230+
const result = smDataSource.getMetricsDS();
231+
232+
expect(result).toEqual(METRICS_DATASOURCE);
233+
expect(result?.uid).toEqual('P4DCEA413A673ADCC');
234+
});
235+
236+
it('should fall back to default grafanacloud-metrics UID when configured datasource does not exist', () => {
237+
const defaultMetricsDS = { ...METRICS_DATASOURCE, uid: 'grafanacloud-metrics' };
238+
config.datasources = {
239+
[defaultMetricsDS.name]: defaultMetricsDS,
240+
};
241+
242+
const smDataSourceWithMissingConfig = new SMDataSource({
243+
...SM_DATASOURCE,
244+
jsonData: {
245+
...SM_DATASOURCE.jsonData,
246+
metrics: {
247+
...SM_DATASOURCE.jsonData.metrics,
248+
uid: 'non-existent-uid',
249+
},
250+
},
251+
});
252+
253+
const result = smDataSourceWithMissingConfig.getMetricsDS();
254+
255+
expect(result).toEqual(defaultMetricsDS);
256+
expect(result?.uid).toEqual('grafanacloud-metrics');
257+
});
258+
});
147259
});

src/datasource/DataSource.ts

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -101,20 +101,24 @@ export class SMDataSource extends DataSourceApi<SMQuery, SMOptions> {
101101
// see https://github.com/grafana/synthetic-monitoring-app/pull/911 for more details
102102
getMetricsDS() {
103103
const info = this.instanceSettings.jsonData.metrics;
104-
const ds = findLinkedDatasource({ ...info, uid: 'grafanacloud-metrics' });
105-
if (ds) {
106-
return ds;
104+
// First try to use the configured datasource (respects custom configurations)
105+
const configuredDs = findLinkedDatasource(info);
106+
if (configuredDs) {
107+
return configuredDs;
107108
}
108-
return findLinkedDatasource(info);
109+
// Fall back to the default Grafana Cloud metrics datasource if configured one doesn't exist
110+
return findLinkedDatasource({ ...info, uid: 'grafanacloud-metrics' });
109111
}
110112

111113
getLogsDS() {
112114
const info = this.instanceSettings.jsonData.logs;
113-
const ds = findLinkedDatasource({ ...info, uid: 'grafanacloud-logs' });
114-
if (ds) {
115-
return ds;
115+
// First try to use the configured datasource (respects custom configurations)
116+
const configuredDs = findLinkedDatasource(info);
117+
if (configuredDs) {
118+
return configuredDs;
116119
}
117-
return findLinkedDatasource(this.instanceSettings.jsonData.logs);
120+
// Fall back to the default Grafana Cloud logs datasource if configured one doesn't exist
121+
return findLinkedDatasource({ ...info, uid: 'grafanacloud-logs' });
118122
}
119123

120124
async query(options: DataQueryRequest<SMQuery>): Promise<DataQueryResponse> {

src/datasource/types.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ export const defaultQuery: SMQuery = {
2222
export interface ProvisioningLinkedDatasourceInfo {
2323
grafanaName: string;
2424
hostedId: number;
25+
uid?: string;
2526
}
2627

2728
export interface LinkedDatasourceInfo extends ProvisioningLinkedDatasourceInfo {

src/hooks/useAppInitializer.ts

Lines changed: 22 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -35,19 +35,28 @@ function getLogsName(provisionedName?: string) {
3535

3636
function findDatasourceByNameAndUid(
3737
provisionedName: string,
38+
configuredUid: string | undefined,
3839
type: 'loki' | 'prometheus'
3940
): {
4041
byName: DataSourceInstanceSettings<DataSourceJsonData> | undefined;
4142
byUid: DataSourceInstanceSettings<DataSourceJsonData> | undefined;
4243
} {
4344
const byName = config.datasources[provisionedName];
44-
const byUid = Object.values(config.datasources).find((ds) => {
45-
if (type === 'loki') {
46-
return ds.uid === 'grafanacloud-logs';
47-
} else {
48-
return ds.uid === 'grafanacloud-metrics';
49-
}
50-
});
45+
46+
// First try to find by the configured UID (respects custom datasources)
47+
let byUid = configuredUid ? Object.values(config.datasources).find((ds) => ds.uid === configuredUid) : undefined;
48+
49+
// Fall back to default Grafana Cloud UIDs if configured UID doesn't exist
50+
if (!byUid) {
51+
byUid = Object.values(config.datasources).find((ds) => {
52+
if (type === 'loki') {
53+
return ds.uid === 'grafanacloud-logs';
54+
} else {
55+
return ds.uid === 'grafanacloud-metrics';
56+
}
57+
});
58+
}
59+
5160
return {
5261
byName,
5362
byUid,
@@ -92,9 +101,13 @@ export const useAppInitializer = (redirectTo?: AppRoutes) => {
92101
const { jsonData, id } = useMeta();
93102

94103
const metricsName = getMetricsName(jsonData.metrics.grafanaName);
95-
const { byName: metricsByName, byUid: metricsByUid } = findDatasourceByNameAndUid(metricsName, 'prometheus');
104+
const { byName: metricsByName, byUid: metricsByUid } = findDatasourceByNameAndUid(
105+
metricsName,
106+
jsonData.metrics.uid,
107+
'prometheus'
108+
);
96109
const logsName = getLogsName(jsonData.logs.grafanaName);
97-
const { byName: logsByName, byUid: logsByUid } = findDatasourceByNameAndUid(logsName, 'loki');
110+
const { byName: logsByName, byUid: logsByUid } = findDatasourceByNameAndUid(logsName, jsonData.logs.uid, 'loki');
98111
const stackId = jsonData.stackId;
99112

100113
const handleClick = async () => {

0 commit comments

Comments
 (0)