ragalgo-mcp-server 1.0.5 → 1.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/README.md +192 -119
- package/dist/check_sdk.d.ts +1 -0
- package/dist/check_sdk.js +11 -0
- package/dist/check_sse.d.ts +1 -0
- package/dist/check_sse.js +10 -0
- package/dist/index.d.ts +0 -7
- package/dist/index.js +490 -208
- package/dist/tools/chart.d.ts +37 -20
- package/dist/tools/chart.js +6 -7
- package/dist/tools/financials.d.ts +16 -5
- package/dist/tools/financials.js +1 -1
- package/dist/tools/news.d.ts +56 -11
- package/dist/tools/news.js +9 -22
- package/dist/tools/research.d.ts +27 -14
- package/dist/tools/research.js +9 -9
- package/dist/tools/rooms.d.ts +33 -0
- package/dist/tools/rooms.js +43 -0
- package/dist/tools/snapshots.d.ts +16 -1
- package/dist/tools/snapshots.js +16 -3
- package/dist/tools/tags.d.ts +56 -16
- package/dist/tools/tags.js +13 -2
- package/dist/tools/trends.d.ts +8 -1
- package/dist/utils/api.js +100 -26
- package/package.json +45 -39
- package/server.json +32 -0
package/dist/tools/chart.d.ts
CHANGED
|
@@ -4,30 +4,33 @@
|
|
|
4
4
|
import { z } from 'zod';
|
|
5
5
|
export declare const ChartStockParamsSchema: z.ZodObject<{
|
|
6
6
|
ticker: z.ZodOptional<z.ZodString>;
|
|
7
|
-
market: z.ZodOptional<z.ZodEnum<
|
|
8
|
-
|
|
9
|
-
KOSDAQ: "KOSDAQ";
|
|
10
|
-
}>>;
|
|
11
|
-
zone: z.ZodOptional<z.ZodEnum<{
|
|
12
|
-
STRONG_UP: "STRONG_UP";
|
|
13
|
-
UP_ZONE: "UP_ZONE";
|
|
14
|
-
NEUTRAL: "NEUTRAL";
|
|
15
|
-
DOWN_ZONE: "DOWN_ZONE";
|
|
16
|
-
STRONG_DOWN: "STRONG_DOWN";
|
|
17
|
-
}>>;
|
|
7
|
+
market: z.ZodOptional<z.ZodEnum<["KOSPI", "KOSDAQ", "US", "JP", "UK"]>>;
|
|
8
|
+
zone: z.ZodOptional<z.ZodEnum<["STRONG_UP", "UP_ZONE", "NEUTRAL", "DOWN_ZONE", "STRONG_DOWN"]>>;
|
|
18
9
|
limit: z.ZodDefault<z.ZodNumber>;
|
|
19
|
-
}, z.
|
|
10
|
+
}, "strip", z.ZodTypeAny, {
|
|
11
|
+
limit: number;
|
|
12
|
+
market?: "KOSPI" | "KOSDAQ" | "US" | "JP" | "UK" | undefined;
|
|
13
|
+
ticker?: string | undefined;
|
|
14
|
+
zone?: "STRONG_UP" | "UP_ZONE" | "NEUTRAL" | "DOWN_ZONE" | "STRONG_DOWN" | undefined;
|
|
15
|
+
}, {
|
|
16
|
+
limit?: number | undefined;
|
|
17
|
+
market?: "KOSPI" | "KOSDAQ" | "US" | "JP" | "UK" | undefined;
|
|
18
|
+
ticker?: string | undefined;
|
|
19
|
+
zone?: "STRONG_UP" | "UP_ZONE" | "NEUTRAL" | "DOWN_ZONE" | "STRONG_DOWN" | undefined;
|
|
20
|
+
}>;
|
|
20
21
|
export declare const ChartCoinParamsSchema: z.ZodObject<{
|
|
21
22
|
ticker: z.ZodOptional<z.ZodString>;
|
|
22
|
-
zone: z.ZodOptional<z.ZodEnum<
|
|
23
|
-
STRONG_UP: "STRONG_UP";
|
|
24
|
-
UP_ZONE: "UP_ZONE";
|
|
25
|
-
NEUTRAL: "NEUTRAL";
|
|
26
|
-
DOWN_ZONE: "DOWN_ZONE";
|
|
27
|
-
STRONG_DOWN: "STRONG_DOWN";
|
|
28
|
-
}>>;
|
|
23
|
+
zone: z.ZodOptional<z.ZodEnum<["STRONG_UP", "UP_ZONE", "NEUTRAL", "DOWN_ZONE", "STRONG_DOWN"]>>;
|
|
29
24
|
limit: z.ZodDefault<z.ZodNumber>;
|
|
30
|
-
}, z.
|
|
25
|
+
}, "strip", z.ZodTypeAny, {
|
|
26
|
+
limit: number;
|
|
27
|
+
ticker?: string | undefined;
|
|
28
|
+
zone?: "STRONG_UP" | "UP_ZONE" | "NEUTRAL" | "DOWN_ZONE" | "STRONG_DOWN" | undefined;
|
|
29
|
+
}, {
|
|
30
|
+
limit?: number | undefined;
|
|
31
|
+
ticker?: string | undefined;
|
|
32
|
+
zone?: "STRONG_UP" | "UP_ZONE" | "NEUTRAL" | "DOWN_ZONE" | "STRONG_DOWN" | undefined;
|
|
33
|
+
}>;
|
|
31
34
|
export type ChartStockParams = z.infer<typeof ChartStockParamsSchema>;
|
|
32
35
|
export type ChartCoinParams = z.infer<typeof ChartCoinParamsSchema>;
|
|
33
36
|
export declare function getChartStock(params: ChartStockParams): Promise<{
|
|
@@ -39,6 +42,13 @@ export declare function getChartStock(params: ChartStockParams): Promise<{
|
|
|
39
42
|
scores: number[];
|
|
40
43
|
zone: string;
|
|
41
44
|
oscillator_state: string;
|
|
45
|
+
analysis?: {
|
|
46
|
+
weekly_zone: string;
|
|
47
|
+
daily_momentum: string;
|
|
48
|
+
daily_signal: string;
|
|
49
|
+
};
|
|
50
|
+
outlook?: string;
|
|
51
|
+
chart_history?: any;
|
|
42
52
|
last_price: number;
|
|
43
53
|
updated_at: string;
|
|
44
54
|
} | Array<{
|
|
@@ -57,6 +67,13 @@ export declare function getChartCoin(params: ChartCoinParams): Promise<{
|
|
|
57
67
|
scores: number[];
|
|
58
68
|
zone: string;
|
|
59
69
|
oscillator_state: string;
|
|
70
|
+
analysis?: {
|
|
71
|
+
weekly_zone: string;
|
|
72
|
+
daily_momentum: string;
|
|
73
|
+
daily_signal: string;
|
|
74
|
+
};
|
|
75
|
+
outlook?: string;
|
|
76
|
+
chart_history?: any;
|
|
60
77
|
last_price: number;
|
|
61
78
|
updated_at: string;
|
|
62
79
|
} | Array<{
|
package/dist/tools/chart.js
CHANGED
|
@@ -6,7 +6,7 @@ import { callApi } from '../utils/api.js';
|
|
|
6
6
|
// 주식 차트 파라미터 스키마
|
|
7
7
|
export const ChartStockParamsSchema = z.object({
|
|
8
8
|
ticker: z.string().optional().describe('종목 코드 (예: 005930)'),
|
|
9
|
-
market: z.enum(['KOSPI', 'KOSDAQ']).optional().describe('시장 구분'),
|
|
9
|
+
market: z.enum(['KOSPI', 'KOSDAQ', 'US', 'JP', 'UK']).optional().describe('시장 구분 (KOSPI/KOSDAQ/US/JP/UK)'),
|
|
10
10
|
zone: z.enum(['STRONG_UP', 'UP_ZONE', 'NEUTRAL', 'DOWN_ZONE', 'STRONG_DOWN']).optional().describe('차트 구간'),
|
|
11
11
|
limit: z.number().min(1).max(100).default(20).describe('결과 수'),
|
|
12
12
|
});
|
|
@@ -18,15 +18,14 @@ export const ChartCoinParamsSchema = z.object({
|
|
|
18
18
|
});
|
|
19
19
|
// 주식 차트 조회
|
|
20
20
|
export async function getChartStock(params) {
|
|
21
|
-
const endpoint =
|
|
22
|
-
|
|
23
|
-
const result = await callApi(endpoint,
|
|
21
|
+
const endpoint = 'chart-stock';
|
|
22
|
+
// params passes through directly as query params
|
|
23
|
+
const result = await callApi(endpoint, params);
|
|
24
24
|
return result;
|
|
25
25
|
}
|
|
26
26
|
// 코인 차트 조회
|
|
27
27
|
export async function getChartCoin(params) {
|
|
28
|
-
const endpoint =
|
|
29
|
-
const
|
|
30
|
-
const result = await callApi(endpoint, queryParams);
|
|
28
|
+
const endpoint = 'chart-coin';
|
|
29
|
+
const result = await callApi(endpoint, params);
|
|
31
30
|
return result;
|
|
32
31
|
}
|
|
@@ -5,14 +5,25 @@ import { z } from 'zod';
|
|
|
5
5
|
export declare const FinancialsParamsSchema: z.ZodObject<{
|
|
6
6
|
ticker: z.ZodOptional<z.ZodString>;
|
|
7
7
|
period: z.ZodOptional<z.ZodString>;
|
|
8
|
-
market: z.ZodOptional<z.ZodEnum<
|
|
9
|
-
KOSPI: "KOSPI";
|
|
10
|
-
KOSDAQ: "KOSDAQ";
|
|
11
|
-
}>>;
|
|
8
|
+
market: z.ZodOptional<z.ZodEnum<["KOSPI", "KOSDAQ", "US", "JP", "UK"]>>;
|
|
12
9
|
periods: z.ZodDefault<z.ZodNumber>;
|
|
13
10
|
limit: z.ZodDefault<z.ZodNumber>;
|
|
14
11
|
offset: z.ZodDefault<z.ZodNumber>;
|
|
15
|
-
}, z.
|
|
12
|
+
}, "strip", z.ZodTypeAny, {
|
|
13
|
+
limit: number;
|
|
14
|
+
offset: number;
|
|
15
|
+
periods: number;
|
|
16
|
+
market?: "KOSPI" | "KOSDAQ" | "US" | "JP" | "UK" | undefined;
|
|
17
|
+
ticker?: string | undefined;
|
|
18
|
+
period?: string | undefined;
|
|
19
|
+
}, {
|
|
20
|
+
limit?: number | undefined;
|
|
21
|
+
offset?: number | undefined;
|
|
22
|
+
market?: "KOSPI" | "KOSDAQ" | "US" | "JP" | "UK" | undefined;
|
|
23
|
+
ticker?: string | undefined;
|
|
24
|
+
period?: string | undefined;
|
|
25
|
+
periods?: number | undefined;
|
|
26
|
+
}>;
|
|
16
27
|
export type FinancialsParams = z.infer<typeof FinancialsParamsSchema>;
|
|
17
28
|
export declare function getFinancials(params: FinancialsParams): Promise<{
|
|
18
29
|
success: boolean;
|
package/dist/tools/financials.js
CHANGED
|
@@ -7,7 +7,7 @@ import { callApi } from '../utils/api.js';
|
|
|
7
7
|
export const FinancialsParamsSchema = z.object({
|
|
8
8
|
ticker: z.string().optional().describe('종목 코드 (예: 005930)'),
|
|
9
9
|
period: z.string().optional().describe('분기 (예: 2024Q3)'),
|
|
10
|
-
market: z.enum(['KOSPI', 'KOSDAQ']).optional().describe('시장 구분'),
|
|
10
|
+
market: z.enum(['KOSPI', 'KOSDAQ', 'US', 'JP', 'UK']).optional().describe('시장 구분 (KOSPI/KOSDAQ/US/JP/UK)'),
|
|
11
11
|
periods: z.number().min(1).max(8).default(4).describe('최근 N분기 (기본: 4)'),
|
|
12
12
|
limit: z.number().min(1).max(200).default(50).describe('결과 수'),
|
|
13
13
|
offset: z.number().min(0).default(0).describe('페이지네이션 오프셋'),
|
package/dist/tools/news.d.ts
CHANGED
|
@@ -8,30 +8,75 @@ export declare const NewsParamsSchema: z.ZodObject<{
|
|
|
8
8
|
search: z.ZodOptional<z.ZodString>;
|
|
9
9
|
from_date: z.ZodOptional<z.ZodString>;
|
|
10
10
|
to_date: z.ZodOptional<z.ZodString>;
|
|
11
|
-
limit: z.ZodDefault<z.ZodNumber>;
|
|
12
|
-
offset: z.ZodDefault<z.ZodNumber>;
|
|
13
11
|
start_date: z.ZodOptional<z.ZodString>;
|
|
14
12
|
end_date: z.ZodOptional<z.ZodString>;
|
|
15
|
-
|
|
13
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
14
|
+
offset: z.ZodDefault<z.ZodNumber>;
|
|
15
|
+
}, "strip", z.ZodTypeAny, {
|
|
16
|
+
limit: number;
|
|
17
|
+
offset: number;
|
|
18
|
+
tag_code?: string | undefined;
|
|
19
|
+
source?: string | undefined;
|
|
20
|
+
search?: string | undefined;
|
|
21
|
+
from_date?: string | undefined;
|
|
22
|
+
to_date?: string | undefined;
|
|
23
|
+
start_date?: string | undefined;
|
|
24
|
+
end_date?: string | undefined;
|
|
25
|
+
}, {
|
|
26
|
+
tag_code?: string | undefined;
|
|
27
|
+
source?: string | undefined;
|
|
28
|
+
search?: string | undefined;
|
|
29
|
+
from_date?: string | undefined;
|
|
30
|
+
to_date?: string | undefined;
|
|
31
|
+
start_date?: string | undefined;
|
|
32
|
+
end_date?: string | undefined;
|
|
33
|
+
limit?: number | undefined;
|
|
34
|
+
offset?: number | undefined;
|
|
35
|
+
}>;
|
|
16
36
|
export declare const NewsScoredParamsSchema: z.ZodObject<{
|
|
17
37
|
tag_code: z.ZodOptional<z.ZodString>;
|
|
18
38
|
source: z.ZodOptional<z.ZodString>;
|
|
19
39
|
search: z.ZodOptional<z.ZodString>;
|
|
20
40
|
from_date: z.ZodOptional<z.ZodString>;
|
|
21
41
|
to_date: z.ZodOptional<z.ZodString>;
|
|
22
|
-
limit: z.ZodDefault<z.ZodNumber>;
|
|
23
|
-
offset: z.ZodDefault<z.ZodNumber>;
|
|
24
42
|
start_date: z.ZodOptional<z.ZodString>;
|
|
25
43
|
end_date: z.ZodOptional<z.ZodString>;
|
|
44
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
45
|
+
offset: z.ZodDefault<z.ZodNumber>;
|
|
46
|
+
} & {
|
|
26
47
|
min_score: z.ZodOptional<z.ZodNumber>;
|
|
27
48
|
max_score: z.ZodOptional<z.ZodNumber>;
|
|
28
|
-
verdict: z.ZodOptional<z.ZodEnum<
|
|
29
|
-
bullish: "bullish";
|
|
30
|
-
bearish: "bearish";
|
|
31
|
-
neutral: "neutral";
|
|
32
|
-
}>>;
|
|
49
|
+
verdict: z.ZodOptional<z.ZodEnum<["bullish", "bearish", "neutral"]>>;
|
|
33
50
|
market: z.ZodOptional<z.ZodString>;
|
|
34
|
-
}, z.
|
|
51
|
+
}, "strip", z.ZodTypeAny, {
|
|
52
|
+
limit: number;
|
|
53
|
+
offset: number;
|
|
54
|
+
tag_code?: string | undefined;
|
|
55
|
+
source?: string | undefined;
|
|
56
|
+
search?: string | undefined;
|
|
57
|
+
from_date?: string | undefined;
|
|
58
|
+
to_date?: string | undefined;
|
|
59
|
+
start_date?: string | undefined;
|
|
60
|
+
end_date?: string | undefined;
|
|
61
|
+
min_score?: number | undefined;
|
|
62
|
+
max_score?: number | undefined;
|
|
63
|
+
verdict?: "bullish" | "bearish" | "neutral" | undefined;
|
|
64
|
+
market?: string | undefined;
|
|
65
|
+
}, {
|
|
66
|
+
tag_code?: string | undefined;
|
|
67
|
+
source?: string | undefined;
|
|
68
|
+
search?: string | undefined;
|
|
69
|
+
from_date?: string | undefined;
|
|
70
|
+
to_date?: string | undefined;
|
|
71
|
+
start_date?: string | undefined;
|
|
72
|
+
end_date?: string | undefined;
|
|
73
|
+
limit?: number | undefined;
|
|
74
|
+
offset?: number | undefined;
|
|
75
|
+
min_score?: number | undefined;
|
|
76
|
+
max_score?: number | undefined;
|
|
77
|
+
verdict?: "bullish" | "bearish" | "neutral" | undefined;
|
|
78
|
+
market?: string | undefined;
|
|
79
|
+
}>;
|
|
35
80
|
export type NewsParams = z.infer<typeof NewsParamsSchema>;
|
|
36
81
|
export type NewsScoredParams = z.infer<typeof NewsScoredParamsSchema>;
|
|
37
82
|
export declare function getNews(params: NewsParams): Promise<{
|
package/dist/tools/news.js
CHANGED
|
@@ -6,25 +6,27 @@ import { callApi } from '../utils/api.js';
|
|
|
6
6
|
// 뉴스 파라미터 스키마
|
|
7
7
|
export const NewsParamsSchema = z.object({
|
|
8
8
|
tag_code: z.string().optional().describe('태그 코드 (search_tags 결과값, 예: STK005930, THM001)'),
|
|
9
|
-
source: z.string().optional().describe('소스 필터 (예: 한경,
|
|
9
|
+
source: z.string().optional().describe('소스 필터 (예: 한경, 매경, WSJ, Bloomberg)'),
|
|
10
10
|
search: z.string().optional().describe('제목 검색어'),
|
|
11
11
|
from_date: z.string().optional().describe('시작일 (YYYY-MM-DD)'),
|
|
12
12
|
to_date: z.string().optional().describe('종료일 (YYYY-MM-DD)'),
|
|
13
|
+
start_date: z.string().optional().describe('시작일 (from_date의 별칭)'), // [FIX] LLM Alias support
|
|
14
|
+
end_date: z.string().optional().describe('종료일 (to_date의 별칭)'), // [FIX] LLM Alias support
|
|
13
15
|
limit: z.number().min(1).max(100).default(20).describe('결과 수 (기본: 20, 최대: 100)'),
|
|
14
16
|
offset: z.number().min(0).default(0).describe('페이지네이션 오프셋'),
|
|
15
|
-
start_date: z.string().optional().describe('시작일 alias'),
|
|
16
|
-
end_date: z.string().optional().describe('종료일 alias'),
|
|
17
17
|
}); // [MOD] Removed .strict()
|
|
18
18
|
// 점수 포함 뉴스 파라미터 스키마
|
|
19
19
|
export const NewsScoredParamsSchema = NewsParamsSchema.extend({
|
|
20
20
|
min_score: z.number().min(-10).max(10).optional().describe('최소 감정 점수 (-10~10)'),
|
|
21
21
|
max_score: z.number().min(-10).max(10).optional().describe('최대 감정 점수 (-10~10)'),
|
|
22
22
|
verdict: z.enum(['bullish', 'bearish', 'neutral']).optional().describe('판정 필터'),
|
|
23
|
-
market: z.string().optional().describe('시장 필터 (KR, US
|
|
23
|
+
market: z.string().optional().describe('시장 필터 (KR, US 등) - 호환성 유지용'), // [FIX] LLM Compatibility
|
|
24
24
|
}); // [MOD] Removed .strict()
|
|
25
25
|
// 뉴스 조회 (점수 제외)
|
|
26
26
|
export async function getNews(params) {
|
|
27
|
+
console.error(`[getNews] Params: ${JSON.stringify(params)}`); // [DEBUG]
|
|
27
28
|
const { tag_code, start_date, end_date, ...rest } = params;
|
|
29
|
+
// [FIX] Handle Aliases
|
|
28
30
|
const apiParams = { ...rest, tag: tag_code };
|
|
29
31
|
if (start_date && !apiParams.from_date)
|
|
30
32
|
apiParams.from_date = start_date;
|
|
@@ -35,29 +37,14 @@ export async function getNews(params) {
|
|
|
35
37
|
}
|
|
36
38
|
// 뉴스 조회 (점수 포함)
|
|
37
39
|
export async function getNewsScored(params) {
|
|
38
|
-
|
|
40
|
+
console.error(`[getNewsScored] Params: ${JSON.stringify(params)}`); // [DEBUG]
|
|
41
|
+
const { tag_code, start_date, end_date, ...rest } = params; // [FIXED] Include 'market' in API call by not destructuring it from rest (it's inside rest now or handled by type)
|
|
42
|
+
// [FIX] Handle Aliases
|
|
39
43
|
const apiParams = { ...rest, tag: tag_code };
|
|
40
44
|
if (start_date && !apiParams.from_date)
|
|
41
45
|
apiParams.from_date = start_date;
|
|
42
46
|
if (end_date && !apiParams.to_date)
|
|
43
47
|
apiParams.to_date = end_date;
|
|
44
|
-
// [FIX] JP/UK Fallback: 'news-scored' endpoint only supports scored news (news_final).
|
|
45
|
-
// Raw markets (JP/UK) are in raw tables accessed via 'news' endpoint.
|
|
46
|
-
// We hijack the call to 'news' and polyfill the score fields.
|
|
47
|
-
const market = apiParams.market?.toUpperCase();
|
|
48
|
-
if (market === 'JP' || market === 'UK') {
|
|
49
|
-
const result = await callApi('news', apiParams);
|
|
50
|
-
return {
|
|
51
|
-
...result,
|
|
52
|
-
data: (result.data || []).map(item => ({
|
|
53
|
-
...item,
|
|
54
|
-
sentiment_score: 0,
|
|
55
|
-
verdict: 'neutral',
|
|
56
|
-
tag_codes: item.tags || [] // 'news' endpoint returns tags as strings or codes? check 'news' return type.
|
|
57
|
-
// Actually 'news' endpoint handles mapping too.
|
|
58
|
-
}))
|
|
59
|
-
};
|
|
60
|
-
}
|
|
61
48
|
const result = await callApi('news-scored', apiParams);
|
|
62
49
|
return result;
|
|
63
50
|
}
|
package/dist/tools/research.d.ts
CHANGED
|
@@ -1,26 +1,39 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* Research (보고서) 관련 MCP Tools
|
|
3
3
|
*/
|
|
4
4
|
import { z } from 'zod';
|
|
5
5
|
export declare const ResearchParamsSchema: z.ZodObject<{
|
|
6
|
-
tag_code: z.ZodString
|
|
7
|
-
limit: z.ZodDefault<z.ZodNumber>;
|
|
6
|
+
tag_code: z.ZodOptional<z.ZodString>;
|
|
8
7
|
source: z.ZodOptional<z.ZodString>;
|
|
9
|
-
|
|
8
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
9
|
+
offset: z.ZodDefault<z.ZodNumber>;
|
|
10
|
+
}, "strip", z.ZodTypeAny, {
|
|
11
|
+
limit: number;
|
|
12
|
+
offset: number;
|
|
13
|
+
tag_code?: string | undefined;
|
|
14
|
+
source?: string | undefined;
|
|
15
|
+
}, {
|
|
16
|
+
tag_code?: string | undefined;
|
|
17
|
+
source?: string | undefined;
|
|
18
|
+
limit?: number | undefined;
|
|
19
|
+
offset?: number | undefined;
|
|
20
|
+
}>;
|
|
10
21
|
export type ResearchParams = z.infer<typeof ResearchParamsSchema>;
|
|
11
22
|
export declare function getResearch(params: ResearchParams): Promise<{
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
research_count: number;
|
|
15
|
-
research: Array<{
|
|
23
|
+
success: boolean;
|
|
24
|
+
data: Array<{
|
|
16
25
|
id: number;
|
|
17
26
|
title: string;
|
|
27
|
+
summary: string;
|
|
28
|
+
tag_codes: string[];
|
|
29
|
+
created_at: string;
|
|
30
|
+
processed_at: string;
|
|
18
31
|
source: string;
|
|
19
|
-
|
|
20
|
-
published_at: string | null;
|
|
21
|
-
chunks: Array<{
|
|
22
|
-
section: string;
|
|
23
|
-
content: string;
|
|
24
|
-
}>;
|
|
32
|
+
market_outlook?: string;
|
|
25
33
|
}>;
|
|
34
|
+
meta: {
|
|
35
|
+
count: number;
|
|
36
|
+
limit: number;
|
|
37
|
+
offset: number;
|
|
38
|
+
};
|
|
26
39
|
}>;
|
package/dist/tools/research.js
CHANGED
|
@@ -1,18 +1,18 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* Research (보고서) 관련 MCP Tools
|
|
3
3
|
*/
|
|
4
4
|
import { z } from 'zod';
|
|
5
5
|
import { callApi } from '../utils/api.js';
|
|
6
|
-
|
|
7
|
-
// 보고서 조회 파라미터 스키마
|
|
6
|
+
// Research 파라미터 스키마
|
|
8
7
|
export const ResearchParamsSchema = z.object({
|
|
9
|
-
tag_code: z.string().describe('
|
|
10
|
-
|
|
11
|
-
|
|
8
|
+
tag_code: z.string().optional().describe('Tag code filter (e.g., STK005930, USTK_AAPL)'),
|
|
9
|
+
source: z.string().optional().describe('Source filter (e.g., mckinsey, bcg, ls)'),
|
|
10
|
+
limit: z.number().min(1).max(50).default(10).describe('Result count (default: 10)'),
|
|
11
|
+
offset: z.number().min(0).default(0).describe('Pagination offset'),
|
|
12
12
|
});
|
|
13
|
-
// 보고서 조회
|
|
13
|
+
// Research 보고서 조회
|
|
14
14
|
export async function getResearch(params) {
|
|
15
|
-
|
|
16
|
-
const result = await callApi(
|
|
15
|
+
const endpoint = 'research';
|
|
16
|
+
const result = await callApi(endpoint, params);
|
|
17
17
|
return result;
|
|
18
18
|
}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
export declare const RoomsParamsSchema: z.ZodObject<{
|
|
3
|
+
search: z.ZodOptional<z.ZodString>;
|
|
4
|
+
type: z.ZodOptional<z.ZodEnum<["tag", "ticker", "keyword"]>>;
|
|
5
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
6
|
+
}, "strip", z.ZodTypeAny, {
|
|
7
|
+
limit: number;
|
|
8
|
+
type?: "ticker" | "tag" | "keyword" | undefined;
|
|
9
|
+
search?: string | undefined;
|
|
10
|
+
}, {
|
|
11
|
+
type?: "ticker" | "tag" | "keyword" | undefined;
|
|
12
|
+
search?: string | undefined;
|
|
13
|
+
limit?: number | undefined;
|
|
14
|
+
}>;
|
|
15
|
+
export type RoomsParams = z.infer<typeof RoomsParamsSchema>;
|
|
16
|
+
export declare const GetAvailableRoomsSchema: z.ZodObject<{
|
|
17
|
+
search: z.ZodOptional<z.ZodString>;
|
|
18
|
+
type: z.ZodOptional<z.ZodEnum<["tag", "ticker", "keyword"]>>;
|
|
19
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
20
|
+
}, "strip", z.ZodTypeAny, {
|
|
21
|
+
limit: number;
|
|
22
|
+
type?: "ticker" | "tag" | "keyword" | undefined;
|
|
23
|
+
search?: string | undefined;
|
|
24
|
+
}, {
|
|
25
|
+
type?: "ticker" | "tag" | "keyword" | undefined;
|
|
26
|
+
search?: string | undefined;
|
|
27
|
+
limit?: number | undefined;
|
|
28
|
+
}>;
|
|
29
|
+
export declare function getAvailableRooms(params: RoomsParams): Promise<{
|
|
30
|
+
rooms: any;
|
|
31
|
+
count: any;
|
|
32
|
+
help: string;
|
|
33
|
+
}>;
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
const SUPABASE_PROJECT_URL = 'https://xunrsikkybgxkybjzrgz.supabase.co';
|
|
3
|
+
const SUPABASE_REST_URL = `${SUPABASE_PROJECT_URL}/rest/v1`;
|
|
4
|
+
const SUPABASE_ANON_KEY = 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzdXBhYmFzZSIsInJlZiI6Inh1bnJzaWtreWJneGt5Ymp6cmd6Iiwicm9sZSI6ImFub24iLCJpYXQiOjE3NjQ0NTExNTgsImV4cCI6MjA4MDAyNzE1OH0.SsXri828-Rf0gHlu4Bls-pewhfMNNII4mbiuLnc9ACs';
|
|
5
|
+
export const RoomsParamsSchema = z.object({
|
|
6
|
+
search: z.string().optional().describe('Search term for rooms (e.g., "Samsung", "Semiconductor")'),
|
|
7
|
+
type: z.enum(['tag', 'ticker', 'keyword']).optional().describe('Filter by room type'),
|
|
8
|
+
limit: z.number().min(1).max(100).default(20).describe('Result count'),
|
|
9
|
+
});
|
|
10
|
+
export const GetAvailableRoomsSchema = RoomsParamsSchema;
|
|
11
|
+
export async function getAvailableRooms(params) {
|
|
12
|
+
const url = new URL(`${SUPABASE_REST_URL}/available_websocket_rooms`);
|
|
13
|
+
// Select specific columns
|
|
14
|
+
url.searchParams.append('select', 'room_id,type,description');
|
|
15
|
+
// Add filters
|
|
16
|
+
if (params.search) {
|
|
17
|
+
// Search in both description and room_id
|
|
18
|
+
url.searchParams.append('or', `(description.ilike.*${params.search}*,room_id.ilike.*${params.search}*)`);
|
|
19
|
+
}
|
|
20
|
+
if (params.type) {
|
|
21
|
+
url.searchParams.append('type', `eq.${params.type}`);
|
|
22
|
+
}
|
|
23
|
+
// Limit
|
|
24
|
+
url.searchParams.append('limit', String(params.limit));
|
|
25
|
+
const response = await fetch(url.toString(), {
|
|
26
|
+
method: 'GET',
|
|
27
|
+
headers: {
|
|
28
|
+
'Authorization': `Bearer ${SUPABASE_ANON_KEY}`,
|
|
29
|
+
'apikey': SUPABASE_ANON_KEY,
|
|
30
|
+
'Content-Type': 'application/json',
|
|
31
|
+
},
|
|
32
|
+
});
|
|
33
|
+
if (!response.ok) {
|
|
34
|
+
const error = await response.text();
|
|
35
|
+
throw new Error(`Failed to fetch rooms: ${response.status} - ${error}`);
|
|
36
|
+
}
|
|
37
|
+
const data = await response.json();
|
|
38
|
+
return {
|
|
39
|
+
rooms: data,
|
|
40
|
+
count: data.length,
|
|
41
|
+
help: "Use these room_ids to subscribe via WebSocket. Example: socket.emit('subscribe', 'tag:STK005930')"
|
|
42
|
+
};
|
|
43
|
+
}
|
|
@@ -4,11 +4,26 @@
|
|
|
4
4
|
import { z } from 'zod';
|
|
5
5
|
export declare const SnapshotsParamsSchema: z.ZodObject<{
|
|
6
6
|
tag_code: z.ZodOptional<z.ZodString>;
|
|
7
|
+
market: z.ZodOptional<z.ZodEnum<["KR", "US", "JP", "UK", "UNIFIED", "CRY", "FUTURES"]>>;
|
|
7
8
|
date: z.ZodOptional<z.ZodString>;
|
|
8
9
|
days: z.ZodDefault<z.ZodNumber>;
|
|
9
10
|
limit: z.ZodDefault<z.ZodNumber>;
|
|
10
11
|
offset: z.ZodDefault<z.ZodNumber>;
|
|
11
|
-
}, z.
|
|
12
|
+
}, "strip", z.ZodTypeAny, {
|
|
13
|
+
limit: number;
|
|
14
|
+
offset: number;
|
|
15
|
+
days: number;
|
|
16
|
+
tag_code?: string | undefined;
|
|
17
|
+
market?: "US" | "JP" | "UK" | "KR" | "UNIFIED" | "CRY" | "FUTURES" | undefined;
|
|
18
|
+
date?: string | undefined;
|
|
19
|
+
}, {
|
|
20
|
+
tag_code?: string | undefined;
|
|
21
|
+
limit?: number | undefined;
|
|
22
|
+
offset?: number | undefined;
|
|
23
|
+
market?: "US" | "JP" | "UK" | "KR" | "UNIFIED" | "CRY" | "FUTURES" | undefined;
|
|
24
|
+
date?: string | undefined;
|
|
25
|
+
days?: number | undefined;
|
|
26
|
+
}>;
|
|
12
27
|
export type SnapshotsParams = z.infer<typeof SnapshotsParamsSchema>;
|
|
13
28
|
export declare function getSnapshots(params: SnapshotsParams): Promise<{
|
|
14
29
|
success: boolean;
|
package/dist/tools/snapshots.js
CHANGED
|
@@ -6,15 +6,28 @@ import { callApi } from '../utils/api.js';
|
|
|
6
6
|
// 스냅샷 파라미터 스키마
|
|
7
7
|
export const SnapshotsParamsSchema = z.object({
|
|
8
8
|
tag_code: z.string().optional().describe('태그 코드 (예: STK005930)'),
|
|
9
|
+
market: z.enum(['KR', 'US', 'JP', 'UK', 'UNIFIED', 'CRY', 'FUTURES']).optional().describe('시장 구분 (KR/US/JP/UK/UNIFIED/CRY/FUTURES)'),
|
|
9
10
|
date: z.string().optional().describe('날짜 (YYYY-MM-DD)'),
|
|
10
|
-
days: z.number().min(1).
|
|
11
|
-
limit: z.number().min(1).
|
|
11
|
+
days: z.number().min(1).default(7).describe('최근 N일 (기본: 7, 무제한)'),
|
|
12
|
+
limit: z.number().min(1).default(50).describe('결과 수 (기본: 50, 무제한)'),
|
|
12
13
|
offset: z.number().min(0).default(0).describe('페이지네이션 오프셋'),
|
|
13
14
|
});
|
|
14
15
|
// 스냅샷 조회
|
|
16
|
+
// [IMPORTANT] Snapshots are generated daily at 17:00 KST (market close).
|
|
17
|
+
// If you request 'today' and get no results (because it's morning in KST),
|
|
18
|
+
// you MUST:
|
|
19
|
+
// 1. Fetch 'yesterday's snapshot for context.
|
|
20
|
+
// 2. Call 'get_news_scored' to get REAL-TIME news for the current day.
|
|
15
21
|
export async function getSnapshots(params) {
|
|
16
|
-
const endpoint =
|
|
22
|
+
const endpoint = 'snapshots';
|
|
17
23
|
const { tag_code, ...queryParams } = params;
|
|
24
|
+
// 태그 코드가 있으면 쿼리 파라미터에 추가
|
|
25
|
+
if (tag_code) {
|
|
26
|
+
queryParams.tag_code = tag_code;
|
|
27
|
+
}
|
|
28
|
+
if (params.market) {
|
|
29
|
+
queryParams.market = params.market;
|
|
30
|
+
}
|
|
18
31
|
const result = await callApi(endpoint, queryParams);
|
|
19
32
|
return result;
|
|
20
33
|
}
|
package/dist/tools/tags.d.ts
CHANGED
|
@@ -3,28 +3,68 @@
|
|
|
3
3
|
*/
|
|
4
4
|
import { z } from 'zod';
|
|
5
5
|
export declare const TagsSearchParamsSchema: z.ZodObject<{
|
|
6
|
-
q: z.ZodString
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
SECTOR: "SECTOR";
|
|
10
|
-
THEME: "THEME";
|
|
11
|
-
CRYPTO: "CRYPTO";
|
|
12
|
-
}>>;
|
|
6
|
+
q: z.ZodOptional<z.ZodString>;
|
|
7
|
+
query: z.ZodOptional<z.ZodString>;
|
|
8
|
+
type: z.ZodOptional<z.ZodEnum<["STOCK", "SECTOR", "THEME", "CRYPTO"]>>;
|
|
13
9
|
limit: z.ZodDefault<z.ZodNumber>;
|
|
14
|
-
}, z.
|
|
10
|
+
}, "strip", z.ZodTypeAny, {
|
|
11
|
+
limit: number;
|
|
12
|
+
type?: "STOCK" | "SECTOR" | "THEME" | "CRYPTO" | undefined;
|
|
13
|
+
q?: string | undefined;
|
|
14
|
+
query?: string | undefined;
|
|
15
|
+
}, {
|
|
16
|
+
type?: "STOCK" | "SECTOR" | "THEME" | "CRYPTO" | undefined;
|
|
17
|
+
limit?: number | undefined;
|
|
18
|
+
q?: string | undefined;
|
|
19
|
+
query?: string | undefined;
|
|
20
|
+
}>;
|
|
15
21
|
export declare const TagsMatchParamsSchema: z.ZodObject<{
|
|
16
22
|
text: z.ZodString;
|
|
17
|
-
types: z.ZodOptional<z.ZodArray<z.ZodEnum<
|
|
18
|
-
STOCK: "STOCK";
|
|
19
|
-
SECTOR: "SECTOR";
|
|
20
|
-
THEME: "THEME";
|
|
21
|
-
CRYPTO: "CRYPTO";
|
|
22
|
-
}>>>;
|
|
23
|
+
types: z.ZodOptional<z.ZodArray<z.ZodEnum<["STOCK", "SECTOR", "THEME", "CRYPTO"]>, "many">>;
|
|
23
24
|
limit: z.ZodDefault<z.ZodNumber>;
|
|
24
|
-
}, z.
|
|
25
|
+
}, "strip", z.ZodTypeAny, {
|
|
26
|
+
text: string;
|
|
27
|
+
limit: number;
|
|
28
|
+
types?: ("STOCK" | "SECTOR" | "THEME" | "CRYPTO")[] | undefined;
|
|
29
|
+
}, {
|
|
30
|
+
text: string;
|
|
31
|
+
limit?: number | undefined;
|
|
32
|
+
types?: ("STOCK" | "SECTOR" | "THEME" | "CRYPTO")[] | undefined;
|
|
33
|
+
}>;
|
|
25
34
|
export type TagsSearchParams = z.infer<typeof TagsSearchParamsSchema>;
|
|
26
35
|
export type TagsMatchParams = z.infer<typeof TagsMatchParamsSchema>;
|
|
27
|
-
export declare
|
|
36
|
+
export declare const SearchTagsParamsSchema: z.ZodObject<{
|
|
37
|
+
q: z.ZodOptional<z.ZodString>;
|
|
38
|
+
query: z.ZodOptional<z.ZodString>;
|
|
39
|
+
type: z.ZodOptional<z.ZodEnum<["STOCK", "SECTOR", "THEME", "CRYPTO"]>>;
|
|
40
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
41
|
+
}, "strip", z.ZodTypeAny, {
|
|
42
|
+
limit: number;
|
|
43
|
+
type?: "STOCK" | "SECTOR" | "THEME" | "CRYPTO" | undefined;
|
|
44
|
+
q?: string | undefined;
|
|
45
|
+
query?: string | undefined;
|
|
46
|
+
}, {
|
|
47
|
+
type?: "STOCK" | "SECTOR" | "THEME" | "CRYPTO" | undefined;
|
|
48
|
+
limit?: number | undefined;
|
|
49
|
+
q?: string | undefined;
|
|
50
|
+
query?: string | undefined;
|
|
51
|
+
}>;
|
|
52
|
+
export declare const MatchTagsParamsSchema: z.ZodObject<{
|
|
53
|
+
text: z.ZodString;
|
|
54
|
+
types: z.ZodOptional<z.ZodArray<z.ZodEnum<["STOCK", "SECTOR", "THEME", "CRYPTO"]>, "many">>;
|
|
55
|
+
limit: z.ZodDefault<z.ZodNumber>;
|
|
56
|
+
}, "strip", z.ZodTypeAny, {
|
|
57
|
+
text: string;
|
|
58
|
+
limit: number;
|
|
59
|
+
types?: ("STOCK" | "SECTOR" | "THEME" | "CRYPTO")[] | undefined;
|
|
60
|
+
}, {
|
|
61
|
+
text: string;
|
|
62
|
+
limit?: number | undefined;
|
|
63
|
+
types?: ("STOCK" | "SECTOR" | "THEME" | "CRYPTO")[] | undefined;
|
|
64
|
+
}>;
|
|
65
|
+
export declare function searchTags(params: TagsSearchParams & {
|
|
66
|
+
query?: string;
|
|
67
|
+
}): Promise<{
|
|
28
68
|
success: boolean;
|
|
29
69
|
data: Array<{
|
|
30
70
|
tag_code: string;
|
package/dist/tools/tags.js
CHANGED
|
@@ -5,7 +5,8 @@ import { z } from 'zod';
|
|
|
5
5
|
import { callApi, callApiPost } from '../utils/api.js';
|
|
6
6
|
// 태그 검색 파라미터 스키마
|
|
7
7
|
export const TagsSearchParamsSchema = z.object({
|
|
8
|
-
q: z.string().describe('검색어 (예: 삼성, 반도체)'),
|
|
8
|
+
q: z.string().describe('검색어 (예: 삼성, 반도체)').optional(),
|
|
9
|
+
query: z.string().optional().describe('검색어 alias'), // [FIX] LLM often sends 'query'
|
|
9
10
|
type: z.enum(['STOCK', 'SECTOR', 'THEME', 'CRYPTO']).optional().describe('태그 타입'),
|
|
10
11
|
limit: z.number().min(1).max(50).default(20).describe('결과 수'),
|
|
11
12
|
});
|
|
@@ -15,9 +16,19 @@ export const TagsMatchParamsSchema = z.object({
|
|
|
15
16
|
types: z.array(z.enum(['STOCK', 'SECTOR', 'THEME', 'CRYPTO'])).optional().describe('태그 타입 필터'),
|
|
16
17
|
limit: z.number().min(1).max(20).default(10).describe('결과 수'),
|
|
17
18
|
});
|
|
19
|
+
export const SearchTagsParamsSchema = TagsSearchParamsSchema;
|
|
20
|
+
export const MatchTagsParamsSchema = TagsMatchParamsSchema;
|
|
18
21
|
// 태그 검색
|
|
19
22
|
export async function searchTags(params) {
|
|
20
|
-
|
|
23
|
+
// [FIX] Alias mapping: query -> q
|
|
24
|
+
if (!params.q && params.query) {
|
|
25
|
+
params.q = params.query;
|
|
26
|
+
}
|
|
27
|
+
if (!params.q) {
|
|
28
|
+
throw new Error("검색어(q 또는 query)가 필요합니다.");
|
|
29
|
+
}
|
|
30
|
+
const { query, ...apiParams } = params; // Remove 'query' alias from API call
|
|
31
|
+
const result = await callApi('tags/search', apiParams);
|
|
21
32
|
return result;
|
|
22
33
|
}
|
|
23
34
|
// 태그 매칭 (텍스트 → 태그)
|