@mindbase/express-knowledge 1.0.8 → 1.0.12

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.
@@ -1,271 +1,271 @@
1
- import { knowledgeTag, knowledgeTagRelation } from "../orm/Tag.schema";
2
- import { knowledge } from "../orm/Knowledge.schema";
3
- import { eq, and, sql, desc, or, inArray } from "drizzle-orm";
4
- import type { InsertTag } from "../types";
5
-
6
- let _db: any;
7
-
8
- /**
9
- * 初始化 Service 的数据库实例
10
- */
11
- export function initTagService(db: any) {
12
- _db = db;
13
- }
14
-
15
- function getDB() {
16
- if (!_db) throw new Error("TagService not initialized with DB");
17
- return _db;
18
- }
19
-
20
- // ==================== 标签管理 ====================
21
-
22
- /**
23
- * 创建标签
24
- */
25
- export async function createTag(data: InsertTag & { userId?: number }) {
26
- const db = getDB();
27
- const now = new Date();
28
-
29
- const result = await db
30
- .insert(knowledgeTag)
31
- .values({
32
- name: data.name,
33
- color: data.color,
34
- userId: data.userId,
35
- created: now,
36
- })
37
- .execute();
38
-
39
- const lastId = result.lastInsertRowid as number;
40
- return getTagById(lastId);
41
- }
42
-
43
- /**
44
- * 获取标签详情
45
- */
46
- export async function getTagById(id: number) {
47
- const db = getDB();
48
- const [tag] = await db.select().from(knowledgeTag).where(eq(knowledgeTag.id, id)).limit(1);
49
-
50
- return tag || null;
51
- }
52
-
53
- /**
54
- * 获取标签列表
55
- */
56
- export async function listTags(userId?: number) {
57
- const db = getDB();
58
-
59
- let conditions = [];
60
- if (userId !== undefined) {
61
- conditions.push(eq(knowledgeTag.userId, userId));
62
- }
63
-
64
- return await db
65
- .select()
66
- .from(knowledgeTag)
67
- .where(conditions.length > 0 ? and(...conditions) : undefined)
68
- .orderBy(knowledgeTag.name)
69
- .execute();
70
- }
71
-
72
- /**
73
- * 更新标签
74
- */
75
- export async function updateTag(id: number, data: Partial<InsertTag>, userId: number) {
76
- const db = getDB();
77
-
78
- // 检查权限
79
- const [tag] = await db
80
- .select()
81
- .from(knowledgeTag)
82
- .where(and(eq(knowledgeTag.id, id), eq(knowledgeTag.userId, userId)))
83
- .limit(1);
84
-
85
- if (!tag) {
86
- throw new Error("标签不存在或无权操作");
87
- }
88
-
89
- await db
90
- .update(knowledgeTag)
91
- .set({
92
- ...(data.name !== undefined && { name: data.name }),
93
- ...(data.color !== undefined && { color: data.color }),
94
- })
95
- .where(eq(knowledgeTag.id, id))
96
- .execute();
97
-
98
- return getTagById(id);
99
- }
100
-
101
- /**
102
- * 删除标签
103
- */
104
- export async function deleteTag(id: number, userId: number) {
105
- const db = getDB();
106
-
107
- // 检查权限
108
- const [tag] = await db
109
- .select()
110
- .from(knowledgeTag)
111
- .where(and(eq(knowledgeTag.id, id), eq(knowledgeTag.userId, userId)))
112
- .limit(1);
113
-
114
- if (!tag) {
115
- throw new Error("标签不存在或无权操作");
116
- }
117
-
118
- // 删除标签关联
119
- await db.delete(knowledgeTagRelation).where(eq(knowledgeTagRelation.tagId, id)).execute();
120
-
121
- // 删除标签
122
- await db.delete(knowledgeTag).where(eq(knowledgeTag.id, id)).execute();
123
-
124
- return { success: true };
125
- }
126
-
127
- // ==================== 标签关联 ====================
128
-
129
- /**
130
- * 为知识库内容添加标签
131
- */
132
- export async function addTagToKnowledge(knowledgeId: number, tagId: number, userId: number) {
133
- const db = getDB();
134
-
135
- // 检查标签是否存在
136
- const [tag] = await db.select().from(knowledgeTag).where(eq(knowledgeTag.id, tagId)).limit(1);
137
-
138
- if (!tag) {
139
- throw new Error("标签不存在");
140
- }
141
-
142
- // 检查是否已存在关联
143
- const [existing] = await db
144
- .select()
145
- .from(knowledgeTagRelation)
146
- .where(and(eq(knowledgeTagRelation.knowledgeId, knowledgeId), eq(knowledgeTagRelation.tagId, tagId)))
147
- .limit(1);
148
-
149
- if (existing) {
150
- return { success: true, message: "标签已存在" };
151
- }
152
-
153
- // 创建关联
154
- await db
155
- .insert(knowledgeTagRelation)
156
- .values({
157
- knowledgeId,
158
- tagId,
159
- })
160
- .execute();
161
-
162
- return { success: true };
163
- }
164
-
165
- /**
166
- * 移除知识库内容的标签
167
- */
168
- export async function removeTagFromKnowledge(knowledgeId: number, tagId: number) {
169
- const db = getDB();
170
-
171
- await db
172
- .delete(knowledgeTagRelation)
173
- .where(and(eq(knowledgeTagRelation.knowledgeId, knowledgeId), eq(knowledgeTagRelation.tagId, tagId)))
174
- .execute();
175
-
176
- return { success: true };
177
- }
178
-
179
- /**
180
- * 获取知识库内容的标签列表
181
- */
182
- export async function getKnowledgeTags(knowledgeId: number) {
183
- const db = getDB();
184
-
185
- return await db
186
- .select({
187
- id: knowledgeTag.id,
188
- name: knowledgeTag.name,
189
- color: knowledgeTag.color,
190
- })
191
- .from(knowledgeTagRelation)
192
- .innerJoin(knowledgeTag, eq(knowledgeTagRelation.tagId, knowledgeTag.id))
193
- .where(eq(knowledgeTagRelation.knowledgeId, knowledgeId))
194
- .execute();
195
- }
196
-
197
- /**
198
- * 按标签查询知识库内容
199
- */
200
- export async function getKnowledgeByTag(
201
- tagId: number,
202
- options: {
203
- pageIndex?: number;
204
- pageSize?: number;
205
- safe?: number[];
206
- userId?: number;
207
- isAdmin?: boolean;
208
- }
209
- ) {
210
- const db = getDB();
211
- const { pageIndex = 1, pageSize = 10, safe = [0], userId, isAdmin } = options;
212
-
213
- // 获取带有该标签的知识库 ID 列表
214
- const relations = await db.select().from(knowledgeTagRelation).where(eq(knowledgeTagRelation.tagId, tagId)).execute();
215
-
216
- if (relations.length === 0) {
217
- return { list: [], total: 0, pageIndex, pageSize };
218
- }
219
-
220
- const knowledgeIds = relations.map((r) => r.knowledgeId);
221
-
222
- let conditions = [eq(knowledge.isDelete, 0), inArray(knowledge.id, knowledgeIds)];
223
-
224
- // 权限筛选
225
- const safeConditions = [];
226
- for (const s of safe) {
227
- switch (s) {
228
- case 0: // 公开
229
- safeConditions.push(eq(knowledge.safe, s));
230
- break;
231
- case 1: // 登录共享
232
- if (userId) {
233
- safeConditions.push(eq(knowledge.safe, s));
234
- }
235
- break;
236
- case 2: // 个人私密
237
- if (userId) {
238
- safeConditions.push(and(eq(knowledge.safe, s), isAdmin ? sql`1=1` : eq(knowledge.userId, userId)));
239
- }
240
- break;
241
- }
242
- }
243
-
244
- if (safeConditions.length > 0) {
245
- conditions.push(or(...safeConditions));
246
- }
247
-
248
- const offset = (pageIndex - 1) * pageSize;
249
-
250
- const list = await db
251
- .select()
252
- .from(knowledge)
253
- .where(and(...conditions))
254
- .limit(pageSize)
255
- .offset(offset)
256
- .orderBy(desc(knowledge.created))
257
- .execute();
258
-
259
- const [totalResult] = await db
260
- .select({ count: sql<number>`count(*)` })
261
- .from(knowledge)
262
- .where(and(...conditions))
263
- .execute();
264
-
265
- return {
266
- list,
267
- total: totalResult.count,
268
- pageIndex,
269
- pageSize,
270
- };
271
- }
1
+ import { knowledgeTag, knowledgeTagRelation } from "../orm/Tag.schema";
2
+ import { knowledge } from "../orm/Knowledge.schema";
3
+ import { eq, and, sql, desc, or, inArray } from "drizzle-orm";
4
+ import type { InsertTag } from "../types";
5
+
6
+ let _db: any;
7
+
8
+ /**
9
+ * 初始化 Service 的数据库实例
10
+ */
11
+ export function initTagService(db: any) {
12
+ _db = db;
13
+ }
14
+
15
+ function getDB() {
16
+ if (!_db) throw new Error("TagService not initialized with DB");
17
+ return _db;
18
+ }
19
+
20
+ // ==================== 标签管理 ====================
21
+
22
+ /**
23
+ * 创建标签
24
+ */
25
+ export async function createTag(data: InsertTag & { userId?: number }) {
26
+ const db = getDB();
27
+ const now = new Date();
28
+
29
+ const result = await db
30
+ .insert(knowledgeTag)
31
+ .values({
32
+ name: data.name,
33
+ color: data.color,
34
+ userId: data.userId,
35
+ created: now,
36
+ })
37
+ .execute();
38
+
39
+ const lastId = result.lastInsertRowid as number;
40
+ return getTagById(lastId);
41
+ }
42
+
43
+ /**
44
+ * 获取标签详情
45
+ */
46
+ export async function getTagById(id: number) {
47
+ const db = getDB();
48
+ const [tag] = await db.select().from(knowledgeTag).where(eq(knowledgeTag.id, id)).limit(1);
49
+
50
+ return tag || null;
51
+ }
52
+
53
+ /**
54
+ * 获取标签列表
55
+ */
56
+ export async function listTags(userId?: number) {
57
+ const db = getDB();
58
+
59
+ let conditions = [];
60
+ if (userId !== undefined) {
61
+ conditions.push(eq(knowledgeTag.userId, userId));
62
+ }
63
+
64
+ return await db
65
+ .select()
66
+ .from(knowledgeTag)
67
+ .where(conditions.length > 0 ? and(...conditions) : undefined)
68
+ .orderBy(knowledgeTag.name)
69
+ .execute();
70
+ }
71
+
72
+ /**
73
+ * 更新标签
74
+ */
75
+ export async function updateTag(id: number, data: Partial<InsertTag>, userId: number) {
76
+ const db = getDB();
77
+
78
+ // 检查权限
79
+ const [tag] = await db
80
+ .select()
81
+ .from(knowledgeTag)
82
+ .where(and(eq(knowledgeTag.id, id), eq(knowledgeTag.userId, userId)))
83
+ .limit(1);
84
+
85
+ if (!tag) {
86
+ throw new Error("标签不存在或无权操作");
87
+ }
88
+
89
+ await db
90
+ .update(knowledgeTag)
91
+ .set({
92
+ ...(data.name !== undefined && { name: data.name }),
93
+ ...(data.color !== undefined && { color: data.color }),
94
+ })
95
+ .where(eq(knowledgeTag.id, id))
96
+ .execute();
97
+
98
+ return getTagById(id);
99
+ }
100
+
101
+ /**
102
+ * 删除标签
103
+ */
104
+ export async function deleteTag(id: number, userId: number) {
105
+ const db = getDB();
106
+
107
+ // 检查权限
108
+ const [tag] = await db
109
+ .select()
110
+ .from(knowledgeTag)
111
+ .where(and(eq(knowledgeTag.id, id), eq(knowledgeTag.userId, userId)))
112
+ .limit(1);
113
+
114
+ if (!tag) {
115
+ throw new Error("标签不存在或无权操作");
116
+ }
117
+
118
+ // 删除标签关联
119
+ await db.delete(knowledgeTagRelation).where(eq(knowledgeTagRelation.tagId, id)).execute();
120
+
121
+ // 删除标签
122
+ await db.delete(knowledgeTag).where(eq(knowledgeTag.id, id)).execute();
123
+
124
+ return { success: true };
125
+ }
126
+
127
+ // ==================== 标签关联 ====================
128
+
129
+ /**
130
+ * 为知识库内容添加标签
131
+ */
132
+ export async function addTagToKnowledge(knowledgeId: number, tagId: number, userId: number) {
133
+ const db = getDB();
134
+
135
+ // 检查标签是否存在
136
+ const [tag] = await db.select().from(knowledgeTag).where(eq(knowledgeTag.id, tagId)).limit(1);
137
+
138
+ if (!tag) {
139
+ throw new Error("标签不存在");
140
+ }
141
+
142
+ // 检查是否已存在关联
143
+ const [existing] = await db
144
+ .select()
145
+ .from(knowledgeTagRelation)
146
+ .where(and(eq(knowledgeTagRelation.knowledgeId, knowledgeId), eq(knowledgeTagRelation.tagId, tagId)))
147
+ .limit(1);
148
+
149
+ if (existing) {
150
+ return { success: true, message: "标签已存在" };
151
+ }
152
+
153
+ // 创建关联
154
+ await db
155
+ .insert(knowledgeTagRelation)
156
+ .values({
157
+ knowledgeId,
158
+ tagId,
159
+ })
160
+ .execute();
161
+
162
+ return { success: true };
163
+ }
164
+
165
+ /**
166
+ * 移除知识库内容的标签
167
+ */
168
+ export async function removeTagFromKnowledge(knowledgeId: number, tagId: number) {
169
+ const db = getDB();
170
+
171
+ await db
172
+ .delete(knowledgeTagRelation)
173
+ .where(and(eq(knowledgeTagRelation.knowledgeId, knowledgeId), eq(knowledgeTagRelation.tagId, tagId)))
174
+ .execute();
175
+
176
+ return { success: true };
177
+ }
178
+
179
+ /**
180
+ * 获取知识库内容的标签列表
181
+ */
182
+ export async function getKnowledgeTags(knowledgeId: number) {
183
+ const db = getDB();
184
+
185
+ return await db
186
+ .select({
187
+ id: knowledgeTag.id,
188
+ name: knowledgeTag.name,
189
+ color: knowledgeTag.color,
190
+ })
191
+ .from(knowledgeTagRelation)
192
+ .innerJoin(knowledgeTag, eq(knowledgeTagRelation.tagId, knowledgeTag.id))
193
+ .where(eq(knowledgeTagRelation.knowledgeId, knowledgeId))
194
+ .execute();
195
+ }
196
+
197
+ /**
198
+ * 按标签查询知识库内容
199
+ */
200
+ export async function getKnowledgeByTag(
201
+ tagId: number,
202
+ options: {
203
+ pageIndex?: number;
204
+ pageSize?: number;
205
+ safe?: number[];
206
+ userId?: number;
207
+ isAdmin?: boolean;
208
+ }
209
+ ) {
210
+ const db = getDB();
211
+ const { pageIndex = 1, pageSize = 10, safe = [0], userId, isAdmin } = options;
212
+
213
+ // 获取带有该标签的知识库 ID 列表
214
+ const relations = await db.select().from(knowledgeTagRelation).where(eq(knowledgeTagRelation.tagId, tagId)).execute();
215
+
216
+ if (relations.length === 0) {
217
+ return { list: [], total: 0, pageIndex, pageSize };
218
+ }
219
+
220
+ const knowledgeIds = relations.map((r) => r.knowledgeId);
221
+
222
+ let conditions = [eq(knowledge.isDelete, 0), inArray(knowledge.id, knowledgeIds)];
223
+
224
+ // 权限筛选
225
+ const safeConditions = [];
226
+ for (const s of safe) {
227
+ switch (s) {
228
+ case 0: // 公开
229
+ safeConditions.push(eq(knowledge.safe, s));
230
+ break;
231
+ case 1: // 登录共享
232
+ if (userId) {
233
+ safeConditions.push(eq(knowledge.safe, s));
234
+ }
235
+ break;
236
+ case 2: // 个人私密
237
+ if (userId) {
238
+ safeConditions.push(and(eq(knowledge.safe, s), isAdmin ? sql`1=1` : eq(knowledge.userId, userId)));
239
+ }
240
+ break;
241
+ }
242
+ }
243
+
244
+ if (safeConditions.length > 0) {
245
+ conditions.push(or(...safeConditions));
246
+ }
247
+
248
+ const offset = (pageIndex - 1) * pageSize;
249
+
250
+ const list = await db
251
+ .select()
252
+ .from(knowledge)
253
+ .where(and(...conditions))
254
+ .limit(pageSize)
255
+ .offset(offset)
256
+ .orderBy(desc(knowledge.created))
257
+ .execute();
258
+
259
+ const [totalResult] = await db
260
+ .select({ count: sql<number>`count(*)` })
261
+ .from(knowledge)
262
+ .where(and(...conditions))
263
+ .execute();
264
+
265
+ return {
266
+ list,
267
+ total: totalResult.count,
268
+ pageIndex,
269
+ pageSize,
270
+ };
271
+ }