@ttkit/daily-hot-api 0.1.3 → 0.1.5

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.
Files changed (64) hide show
  1. package/.env.example +24 -0
  2. package/README.md +1 -0
  3. package/dist/app.module.js +2 -0
  4. package/dist/app.module.js.map +1 -1
  5. package/dist/config/validation.schema.d.ts +51 -0
  6. package/dist/config/validation.schema.js +69 -0
  7. package/dist/config/validation.schema.js.map +1 -1
  8. package/dist/daily-brief/clients/ai-analysis.client.d.ts +15 -6
  9. package/dist/daily-brief/clients/ai-analysis.client.js +103 -15
  10. package/dist/daily-brief/clients/ai-analysis.client.js.map +1 -1
  11. package/dist/daily-brief/daily-brief.module.js +1 -1
  12. package/dist/daily-brief/daily-brief.module.js.map +1 -1
  13. package/dist/daily-brief/daily-brief.service.js +1 -1
  14. package/dist/daily-brief/daily-brief.service.js.map +1 -1
  15. package/dist/database/database.module.js +15 -2
  16. package/dist/database/database.module.js.map +1 -1
  17. package/dist/database/repositories/daily-brief.repository.js +11 -1
  18. package/dist/database/repositories/daily-brief.repository.js.map +1 -1
  19. package/dist/database/repositories/hot-item.repository.d.ts +1 -1
  20. package/dist/database/repositories/hot-item.repository.js +7 -4
  21. package/dist/database/repositories/hot-item.repository.js.map +1 -1
  22. package/dist/database/repositories/news-brief.repository.d.ts +81 -0
  23. package/dist/database/repositories/news-brief.repository.js +208 -0
  24. package/dist/database/repositories/news-brief.repository.js.map +1 -0
  25. package/dist/database/schemas/news-brief.schema.d.ts +48 -0
  26. package/dist/database/schemas/news-brief.schema.js +130 -0
  27. package/dist/database/schemas/news-brief.schema.js.map +1 -0
  28. package/dist/news-brief/categories/news-category.registry.d.ts +5 -0
  29. package/dist/news-brief/categories/news-category.registry.js +106 -0
  30. package/dist/news-brief/categories/news-category.registry.js.map +1 -0
  31. package/dist/news-brief/clients/news-brief-ai.client.d.ts +45 -0
  32. package/dist/news-brief/clients/news-brief-ai.client.js +314 -0
  33. package/dist/news-brief/clients/news-brief-ai.client.js.map +1 -0
  34. package/dist/news-brief/clients/news-brief-search.service.d.ts +12 -0
  35. package/dist/news-brief/clients/news-brief-search.service.js +57 -0
  36. package/dist/news-brief/clients/news-brief-search.service.js.map +1 -0
  37. package/dist/news-brief/dto/generate-news-brief.dto.d.ts +7 -0
  38. package/dist/news-brief/dto/generate-news-brief.dto.js +45 -0
  39. package/dist/news-brief/dto/generate-news-brief.dto.js.map +1 -0
  40. package/dist/news-brief/dto/list-news-briefs-query.dto.d.ts +7 -0
  41. package/dist/news-brief/dto/list-news-briefs-query.dto.js +59 -0
  42. package/dist/news-brief/dto/list-news-briefs-query.dto.js.map +1 -0
  43. package/dist/news-brief/dto/news-brief-date-param.dto.d.ts +3 -0
  44. package/dist/news-brief/dto/news-brief-date-param.dto.js +22 -0
  45. package/dist/news-brief/dto/news-brief-date-param.dto.js.map +1 -0
  46. package/dist/news-brief/interfaces/news-brief.interface.d.ts +202 -0
  47. package/dist/news-brief/interfaces/news-brief.interface.js +3 -0
  48. package/dist/news-brief/interfaces/news-brief.interface.js.map +1 -0
  49. package/dist/news-brief/news-brief.config.d.ts +33 -0
  50. package/dist/news-brief/news-brief.config.js +118 -0
  51. package/dist/news-brief/news-brief.config.js.map +1 -0
  52. package/dist/news-brief/news-brief.controller.d.ts +56 -0
  53. package/dist/news-brief/news-brief.controller.js +185 -0
  54. package/dist/news-brief/news-brief.controller.js.map +1 -0
  55. package/dist/news-brief/news-brief.module.d.ts +2 -0
  56. package/dist/news-brief/news-brief.module.js +47 -0
  57. package/dist/news-brief/news-brief.module.js.map +1 -0
  58. package/dist/news-brief/news-brief.scheduler.d.ts +34 -0
  59. package/dist/news-brief/news-brief.scheduler.js +143 -0
  60. package/dist/news-brief/news-brief.scheduler.js.map +1 -0
  61. package/dist/news-brief/news-brief.service.d.ts +60 -0
  62. package/dist/news-brief/news-brief.service.js +676 -0
  63. package/dist/news-brief/news-brief.service.js.map +1 -0
  64. package/package.json +1 -1
@@ -0,0 +1,59 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var __metadata = (this && this.__metadata) || function (k, v) {
9
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.ListNewsBriefsQueryDto = void 0;
13
+ const class_transformer_1 = require("class-transformer");
14
+ const class_validator_1 = require("class-validator");
15
+ class ListNewsBriefsQueryDto {
16
+ constructor() {
17
+ this.page = 1;
18
+ this.limit = 20;
19
+ }
20
+ }
21
+ exports.ListNewsBriefsQueryDto = ListNewsBriefsQueryDto;
22
+ __decorate([
23
+ (0, class_validator_1.IsOptional)(),
24
+ (0, class_transformer_1.Type)(() => Number),
25
+ (0, class_validator_1.IsInt)(),
26
+ (0, class_validator_1.Min)(1),
27
+ __metadata("design:type", Number)
28
+ ], ListNewsBriefsQueryDto.prototype, "page", void 0);
29
+ __decorate([
30
+ (0, class_validator_1.IsOptional)(),
31
+ (0, class_transformer_1.Type)(() => Number),
32
+ (0, class_validator_1.IsInt)(),
33
+ (0, class_validator_1.Min)(1),
34
+ (0, class_validator_1.Max)(100),
35
+ __metadata("design:type", Number)
36
+ ], ListNewsBriefsQueryDto.prototype, "limit", void 0);
37
+ __decorate([
38
+ (0, class_validator_1.IsOptional)(),
39
+ (0, class_validator_1.IsString)(),
40
+ __metadata("design:type", String)
41
+ ], ListNewsBriefsQueryDto.prototype, "category", void 0);
42
+ __decorate([
43
+ (0, class_validator_1.IsOptional)(),
44
+ (0, class_validator_1.IsIn)(['generating', 'success', 'failed']),
45
+ __metadata("design:type", String)
46
+ ], ListNewsBriefsQueryDto.prototype, "status", void 0);
47
+ __decorate([
48
+ (0, class_validator_1.IsOptional)(),
49
+ (0, class_transformer_1.Transform)(({ value }) => {
50
+ if (typeof value !== 'string')
51
+ return value;
52
+ const trimmed = value.trim();
53
+ return trimmed === '' ? undefined : trimmed;
54
+ }),
55
+ (0, class_validator_1.IsString)(),
56
+ (0, class_validator_1.Matches)(/^[a-z0-9][a-z0-9-]{0,31}$/),
57
+ __metadata("design:type", String)
58
+ ], ListNewsBriefsQueryDto.prototype, "period", void 0);
59
+ //# sourceMappingURL=list-news-briefs-query.dto.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list-news-briefs-query.dto.js","sourceRoot":"","sources":["../../../src/news-brief/dto/list-news-briefs-query.dto.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,yDAAoD;AACpD,qDAQyB;AAEzB,MAAa,sBAAsB;IAAnC;QAKE,SAAI,GAAY,CAAC,CAAC;QAOlB,UAAK,GAAY,EAAE,CAAC;IAoBtB,CAAC;CAAA;AAhCD,wDAgCC;AA3BC;IAJC,IAAA,4BAAU,GAAE;IACZ,IAAA,wBAAI,EAAC,GAAG,EAAE,CAAC,MAAM,CAAC;IAClB,IAAA,uBAAK,GAAE;IACP,IAAA,qBAAG,EAAC,CAAC,CAAC;;oDACW;AAOlB;IALC,IAAA,4BAAU,GAAE;IACZ,IAAA,wBAAI,EAAC,GAAG,EAAE,CAAC,MAAM,CAAC;IAClB,IAAA,uBAAK,GAAE;IACP,IAAA,qBAAG,EAAC,CAAC,CAAC;IACN,IAAA,qBAAG,EAAC,GAAG,CAAC;;qDACW;AAIpB;IAFC,IAAA,4BAAU,GAAE;IACZ,IAAA,0BAAQ,GAAE;;wDACO;AAIlB;IAFC,IAAA,4BAAU,GAAE;IACZ,IAAA,sBAAI,EAAC,CAAC,YAAY,EAAE,SAAS,EAAE,QAAQ,CAAC,CAAC;;sDACG;AAW7C;IATC,IAAA,4BAAU,GAAE;IAEZ,IAAA,6BAAS,EAAC,CAAC,EAAE,KAAK,EAAE,EAAW,EAAE;QAChC,IAAI,OAAO,KAAK,KAAK,QAAQ;YAAE,OAAO,KAAgB,CAAC;QACvD,MAAM,OAAO,GAAG,KAAK,CAAC,IAAI,EAAE,CAAC;QAC7B,OAAO,OAAO,KAAK,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC;IAC9C,CAAC,CAAC;IACD,IAAA,0BAAQ,GAAE;IACV,IAAA,yBAAO,EAAC,2BAA2B,CAAC;;sDACrB"}
@@ -0,0 +1,3 @@
1
+ export declare class NewsBriefDateParamDto {
2
+ date: string;
3
+ }
@@ -0,0 +1,22 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var __metadata = (this && this.__metadata) || function (k, v) {
9
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.NewsBriefDateParamDto = void 0;
13
+ const class_validator_1 = require("class-validator");
14
+ class NewsBriefDateParamDto {
15
+ }
16
+ exports.NewsBriefDateParamDto = NewsBriefDateParamDto;
17
+ __decorate([
18
+ (0, class_validator_1.IsString)(),
19
+ (0, class_validator_1.Matches)(/^\d{4}-\d{2}-\d{2}$/),
20
+ __metadata("design:type", String)
21
+ ], NewsBriefDateParamDto.prototype, "date", void 0);
22
+ //# sourceMappingURL=news-brief-date-param.dto.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"news-brief-date-param.dto.js","sourceRoot":"","sources":["../../../src/news-brief/dto/news-brief-date-param.dto.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,qDAAoD;AAEpD,MAAa,qBAAqB;CAIjC;AAJD,sDAIC;AADC;IAFC,IAAA,0BAAQ,GAAE;IACV,IAAA,yBAAO,EAAC,qBAAqB,CAAC;;mDAClB"}
@@ -0,0 +1,202 @@
1
+ export type NewsBriefStatus = 'generating' | 'success' | 'failed';
2
+ export type NewsBriefGenerationStatus = 'success' | 'failed' | 'skipped';
3
+ export type NewsBriefSkipReason = 'already_generated' | 'generation_in_progress';
4
+ export interface NewsBriefSource {
5
+ code: string;
6
+ name: string;
7
+ url: string;
8
+ }
9
+ export interface NewsBriefItem {
10
+ id: string;
11
+ title: string;
12
+ summary: string;
13
+ content: string;
14
+ source: NewsBriefSource;
15
+ publishedAt?: string;
16
+ tags?: string[];
17
+ importance?: number;
18
+ extensions?: Record<string, unknown>;
19
+ }
20
+ export interface NewsBriefAiItem {
21
+ sourceRef: string;
22
+ title: string;
23
+ summary: string;
24
+ content: string;
25
+ tags?: string[];
26
+ importance?: number;
27
+ }
28
+ export interface NewsBriefAiPayload {
29
+ title: string;
30
+ summary: string;
31
+ highlights: string[];
32
+ items: NewsBriefAiItem[];
33
+ }
34
+ export interface NewsBriefAnalysis {
35
+ title: string;
36
+ summary: string;
37
+ highlights: string[];
38
+ items: NewsBriefItem[];
39
+ }
40
+ export interface NewsBriefInputItem {
41
+ ref: string;
42
+ source: string;
43
+ sourceName: string;
44
+ title: string;
45
+ desc?: string;
46
+ hot?: number | string;
47
+ url: string;
48
+ timestamp?: number;
49
+ }
50
+ export interface NewsBriefInputWindow {
51
+ start: Date;
52
+ end: Date;
53
+ lookbackHours: number;
54
+ }
55
+ export interface NewsBriefResponse {
56
+ briefDate: string;
57
+ period: string;
58
+ category: string;
59
+ categoryName: string;
60
+ status: NewsBriefStatus;
61
+ title?: string;
62
+ summary?: string;
63
+ highlights: string[];
64
+ items: NewsBriefItem[];
65
+ itemCount: number;
66
+ sources: string[];
67
+ inputWindow: {
68
+ start: string;
69
+ end: string;
70
+ lookbackHours: number;
71
+ };
72
+ model?: string;
73
+ searchProvidersUsed: string[];
74
+ error?: string;
75
+ createdAt?: string;
76
+ updatedAt?: string;
77
+ }
78
+ export interface GenerateNewsBriefOptions {
79
+ category?: string;
80
+ date?: string;
81
+ period?: string;
82
+ force?: boolean;
83
+ sources?: string[];
84
+ }
85
+ export interface NewsBriefSuccessResult {
86
+ category: string;
87
+ categoryName: string;
88
+ status: 'success';
89
+ brief: NewsBriefResponse;
90
+ }
91
+ export interface NewsBriefSkippedResult {
92
+ category: string;
93
+ categoryName: string;
94
+ status: 'skipped';
95
+ reason: NewsBriefSkipReason;
96
+ brief?: NewsBriefResponse;
97
+ }
98
+ export interface NewsBriefFailedResult {
99
+ category: string;
100
+ categoryName: string;
101
+ status: 'failed';
102
+ error: string;
103
+ previousBriefRetained?: boolean;
104
+ brief?: NewsBriefResponse;
105
+ }
106
+ export type NewsBriefGenerationResult = NewsBriefSuccessResult | NewsBriefSkippedResult | NewsBriefFailedResult;
107
+ export interface NewsBriefGenerateResponse {
108
+ briefDate: string;
109
+ period: string;
110
+ results: NewsBriefGenerationResult[];
111
+ }
112
+ export interface NewsCategoryProfile {
113
+ code: string;
114
+ name: string;
115
+ description: string;
116
+ focus: string;
117
+ sources: string[];
118
+ maxItems: number;
119
+ search: boolean;
120
+ }
121
+ export interface NewsCategorySummary {
122
+ code: string;
123
+ name: string;
124
+ description: string;
125
+ sources: string[];
126
+ maxItems: number;
127
+ }
128
+ export interface NewsBriefPublicConfig {
129
+ cronExpression: string;
130
+ timezone: string;
131
+ categories: NewsCategorySummary[];
132
+ lookbackHours: number;
133
+ topItemsPerSource: number;
134
+ maxCandidates: number;
135
+ maxItemsPerCategory: number;
136
+ categoryConcurrency: number;
137
+ sourceConcurrency: number;
138
+ generatingTimeoutMinutes: number;
139
+ manualGenerateEnabled: boolean;
140
+ model: string;
141
+ searchEnabled: boolean;
142
+ searchProviders: string[];
143
+ searchMaxQueries: number;
144
+ searchQueryMaxChars: number;
145
+ }
146
+ export interface NewsBriefSearchEvidence {
147
+ ref: string;
148
+ topicTitle: string;
149
+ query: string;
150
+ provider: import('../../daily-brief/interfaces/search-provider.interface').SearchProviderName | null;
151
+ results: import('../../daily-brief/interfaces/daily-brief.interface').BriefSearchResult[];
152
+ }
153
+ export interface NewsBriefListItem {
154
+ briefDate: string;
155
+ period: string;
156
+ category: string;
157
+ categoryName: string;
158
+ status: NewsBriefStatus;
159
+ title?: string;
160
+ summary?: string;
161
+ itemCount: number;
162
+ updatedAt?: Date;
163
+ }
164
+ export interface NewsBriefListResponse {
165
+ data: NewsBriefListItem[];
166
+ total: number;
167
+ page: number;
168
+ limit: number;
169
+ totalPages: number;
170
+ }
171
+ export interface ListNewsBriefsOptions {
172
+ page?: number;
173
+ limit?: number;
174
+ category?: string;
175
+ status?: NewsBriefStatus;
176
+ period?: string;
177
+ }
178
+ export type NewsBriefDigestStatus = NewsBriefStatus | 'missing';
179
+ export interface NewsBriefDigestCategory {
180
+ category: string;
181
+ categoryName: string;
182
+ status: NewsBriefDigestStatus;
183
+ brief: NewsBriefResponse | null;
184
+ }
185
+ export interface NewsBriefDigestResponse {
186
+ briefDate: string;
187
+ categories: NewsBriefDigestCategory[];
188
+ }
189
+ export interface NewsBriefDeleteResponse {
190
+ mode: 'date';
191
+ briefDate: string;
192
+ category: string;
193
+ period: string | null;
194
+ deletedCount: number;
195
+ }
196
+ export interface NewsBriefDeleteHistoryResponse {
197
+ mode: 'olderThan' | 'beforeDate';
198
+ olderThan: string | null;
199
+ beforeDate: string;
200
+ category: string | null;
201
+ deletedCount: number;
202
+ }
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ //# sourceMappingURL=news-brief.interface.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"news-brief.interface.js","sourceRoot":"","sources":["../../../src/news-brief/interfaces/news-brief.interface.ts"],"names":[],"mappings":""}
@@ -0,0 +1,33 @@
1
+ import { ConfigService } from '@nestjs/config';
2
+ import { NewsCategoryProfile, NewsCategorySummary } from './interfaces/news-brief.interface';
3
+ import { SearchProviderName } from '../daily-brief/interfaces/search-provider.interface';
4
+ export declare class NewsBriefConfigService {
5
+ private readonly configService;
6
+ constructor(configService: ConfigService);
7
+ get enabled(): boolean;
8
+ get cronExpression(): string;
9
+ get timezone(): string;
10
+ get categoryCodes(): string[];
11
+ get categories(): NewsCategoryProfile[];
12
+ get lookbackHours(): number;
13
+ get topItemsPerSource(): number;
14
+ get maxCandidates(): number;
15
+ get maxItemsPerCategory(): number;
16
+ get sourceConcurrency(): number;
17
+ get categoryConcurrency(): number;
18
+ get generatingTimeoutMinutes(): number;
19
+ get manualGenerateEnabled(): boolean;
20
+ get searchEnabled(): boolean;
21
+ get searchMaxQueries(): number;
22
+ get searchConcurrency(): number;
23
+ get searchQueryMaxChars(): number;
24
+ get searchProviders(): SearchProviderName[];
25
+ get aiModel(): string;
26
+ get aiTimeoutMs(): number;
27
+ get aiMaxRetries(): number;
28
+ get openaiApiKey(): string;
29
+ get openaiBaseUrl(): string | undefined;
30
+ get knownCategories(): NewsCategoryProfile[];
31
+ toCategorySummary(profile: NewsCategoryProfile): NewsCategorySummary;
32
+ get categorySummaries(): NewsCategorySummary[];
33
+ }
@@ -0,0 +1,118 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var __metadata = (this && this.__metadata) || function (k, v) {
9
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.NewsBriefConfigService = void 0;
13
+ const common_1 = require("@nestjs/common");
14
+ const config_1 = require("@nestjs/config");
15
+ const news_category_registry_1 = require("./categories/news-category.registry");
16
+ let NewsBriefConfigService = class NewsBriefConfigService {
17
+ constructor(configService) {
18
+ this.configService = configService;
19
+ }
20
+ get enabled() {
21
+ return this.configService.getOrThrow('NEWS_BRIEF_ENABLED');
22
+ }
23
+ get cronExpression() {
24
+ return this.configService.getOrThrow('NEWS_BRIEF_CRON_EXPRESSION');
25
+ }
26
+ get timezone() {
27
+ return this.configService.getOrThrow('NEWS_BRIEF_TIMEZONE');
28
+ }
29
+ get categoryCodes() {
30
+ return this.configService
31
+ .getOrThrow('NEWS_BRIEF_CATEGORIES')
32
+ .split(',')
33
+ .map((item) => item.trim())
34
+ .filter(Boolean);
35
+ }
36
+ get categories() {
37
+ return (0, news_category_registry_1.resolveNewsCategories)(this.categoryCodes);
38
+ }
39
+ get lookbackHours() {
40
+ return this.configService.getOrThrow('NEWS_BRIEF_LOOKBACK_HOURS');
41
+ }
42
+ get topItemsPerSource() {
43
+ return this.configService.getOrThrow('NEWS_BRIEF_TOP_ITEMS_PER_SOURCE');
44
+ }
45
+ get maxCandidates() {
46
+ return this.configService.getOrThrow('NEWS_BRIEF_MAX_CANDIDATES');
47
+ }
48
+ get maxItemsPerCategory() {
49
+ return this.configService.getOrThrow('NEWS_BRIEF_MAX_ITEMS_PER_CATEGORY');
50
+ }
51
+ get sourceConcurrency() {
52
+ return this.configService.getOrThrow('NEWS_BRIEF_SOURCE_CONCURRENCY');
53
+ }
54
+ get categoryConcurrency() {
55
+ return this.configService.getOrThrow('NEWS_BRIEF_CATEGORY_CONCURRENCY');
56
+ }
57
+ get generatingTimeoutMinutes() {
58
+ return this.configService.getOrThrow('NEWS_BRIEF_GENERATING_TIMEOUT_MINUTES');
59
+ }
60
+ get manualGenerateEnabled() {
61
+ return this.configService.getOrThrow('NEWS_BRIEF_MANUAL_GENERATE_ENABLED');
62
+ }
63
+ get searchEnabled() {
64
+ return this.configService.getOrThrow('NEWS_BRIEF_SEARCH_ENABLED');
65
+ }
66
+ get searchMaxQueries() {
67
+ return this.configService.getOrThrow('NEWS_BRIEF_SEARCH_MAX_QUERIES');
68
+ }
69
+ get searchConcurrency() {
70
+ return this.configService.getOrThrow('NEWS_BRIEF_SEARCH_CONCURRENCY');
71
+ }
72
+ get searchQueryMaxChars() {
73
+ return this.configService.getOrThrow('NEWS_BRIEF_SEARCH_QUERY_MAX_CHARS');
74
+ }
75
+ get searchProviders() {
76
+ return this.configService
77
+ .getOrThrow('NEWS_BRIEF_SEARCH_PROVIDERS')
78
+ .split(',')
79
+ .map((name) => name.trim())
80
+ .filter(Boolean);
81
+ }
82
+ get aiModel() {
83
+ return this.configService.getOrThrow('AI_MODEL');
84
+ }
85
+ get aiTimeoutMs() {
86
+ return this.configService.getOrThrow('AI_TIMEOUT_MS');
87
+ }
88
+ get aiMaxRetries() {
89
+ return this.configService.getOrThrow('AI_MAX_RETRIES');
90
+ }
91
+ get openaiApiKey() {
92
+ return this.configService.getOrThrow('OPENAI_API_KEY');
93
+ }
94
+ get openaiBaseUrl() {
95
+ return (this.configService.getOrThrow('OPENAI_API_BASE_URL') || undefined);
96
+ }
97
+ get knownCategories() {
98
+ return (0, news_category_registry_1.listNewsCategoryProfiles)();
99
+ }
100
+ toCategorySummary(profile) {
101
+ return {
102
+ code: profile.code,
103
+ name: profile.name,
104
+ description: profile.description,
105
+ sources: profile.sources,
106
+ maxItems: profile.maxItems,
107
+ };
108
+ }
109
+ get categorySummaries() {
110
+ return this.categories.map((profile) => this.toCategorySummary(profile));
111
+ }
112
+ };
113
+ exports.NewsBriefConfigService = NewsBriefConfigService;
114
+ exports.NewsBriefConfigService = NewsBriefConfigService = __decorate([
115
+ (0, common_1.Injectable)(),
116
+ __metadata("design:paramtypes", [config_1.ConfigService])
117
+ ], NewsBriefConfigService);
118
+ //# sourceMappingURL=news-brief.config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"news-brief.config.js","sourceRoot":"","sources":["../../src/news-brief/news-brief.config.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,56 @@
1
+ import { NewsBriefConfigService } from './news-brief.config';
2
+ import { NewsBriefService } from './news-brief.service';
3
+ import { NewsBriefScheduler } from './news-brief.scheduler';
4
+ import { GenerateNewsBriefDto } from './dto/generate-news-brief.dto';
5
+ import { NewsBriefDateParamDto } from './dto/news-brief-date-param.dto';
6
+ import { ListNewsBriefsQueryDto } from './dto/list-news-briefs-query.dto';
7
+ export declare class NewsBriefController {
8
+ private readonly newsBriefService;
9
+ private readonly newsBriefScheduler;
10
+ private readonly config;
11
+ constructor(newsBriefService: NewsBriefService, newsBriefScheduler: NewsBriefScheduler, config: NewsBriefConfigService);
12
+ generate(body: GenerateNewsBriefDto): Promise<import("./interfaces/news-brief.interface").NewsBriefGenerateResponse>;
13
+ getConfig(): {
14
+ cronExpression: string;
15
+ timezone: string;
16
+ categories: import("./interfaces/news-brief.interface").NewsCategorySummary[];
17
+ lookbackHours: number;
18
+ topItemsPerSource: number;
19
+ maxCandidates: number;
20
+ maxItemsPerCategory: number;
21
+ categoryConcurrency: number;
22
+ sourceConcurrency: number;
23
+ generatingTimeoutMinutes: number;
24
+ manualGenerateEnabled: boolean;
25
+ model: string;
26
+ searchEnabled: boolean;
27
+ searchProviders: string[];
28
+ searchMaxQueries: number;
29
+ searchQueryMaxChars: number;
30
+ enabled: boolean;
31
+ };
32
+ getCategories(): import("./interfaces/news-brief.interface").NewsCategorySummary[];
33
+ getDigest(categories?: string | string[], date?: string, period?: string): Promise<import("./interfaces/news-brief.interface").NewsBriefDigestResponse>;
34
+ getSchedulerStatus(): {
35
+ isRunning: boolean;
36
+ enabled: boolean;
37
+ cronExpression: string;
38
+ timezone: string;
39
+ categories: string[];
40
+ cronJobExists: boolean;
41
+ };
42
+ startScheduler(): {
43
+ message: string;
44
+ };
45
+ stopScheduler(): {
46
+ message: string;
47
+ };
48
+ reconfigureScheduler(): {
49
+ message: string;
50
+ };
51
+ findLatest(category?: string, period?: string, includeDebug?: string): Promise<import("./interfaces/news-brief.interface").NewsBriefResponse | null>;
52
+ list(query: ListNewsBriefsQueryDto): Promise<import("./interfaces/news-brief.interface").NewsBriefListResponse>;
53
+ deleteHistory(olderThan?: string, beforeDate?: string, category?: string): Promise<import("./interfaces/news-brief.interface").NewsBriefDeleteHistoryResponse>;
54
+ deleteByDate(params: NewsBriefDateParamDto, category?: string, period?: string): Promise<import("./interfaces/news-brief.interface").NewsBriefDeleteResponse>;
55
+ findByDate(params: NewsBriefDateParamDto, category?: string, period?: string, includeDebug?: string): Promise<import("./interfaces/news-brief.interface").NewsBriefResponse | null>;
56
+ }