ima-python-sdk 0.1.0__py3-none-any.whl

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.
ima_sdk/types.py ADDED
@@ -0,0 +1,424 @@
1
+ """IMA OpenAPI 数据类型定义。"""
2
+
3
+ from __future__ import annotations
4
+
5
+ import enum
6
+ from dataclasses import dataclass, field
7
+ from typing import Dict, List, Optional
8
+
9
+
10
+ # ── 枚举 ──────────────────────────────────────────────────────────────────────
11
+
12
+
13
+ class MediaType(enum.IntEnum):
14
+ """知识库媒体类型。"""
15
+
16
+ PDF = 1
17
+ WEB = 2
18
+ WORD = 3
19
+ PPT = 4
20
+ EXCEL = 5
21
+ WECHAT_ARTICLE = 6
22
+ MARKDOWN = 7
23
+ IMAGE = 9
24
+ NOTE = 11
25
+ AI_SESSION = 12
26
+ TXT = 13
27
+ XMIND = 14
28
+ AUDIO = 15
29
+ VIDEO = 16 # 不支持通过 API 添加
30
+
31
+
32
+ class ContentFormat(enum.IntEnum):
33
+ """笔记内容格式。"""
34
+
35
+ PLAINTEXT = 0
36
+ MARKDOWN = 1
37
+ JSON = 2
38
+
39
+
40
+ class SearchType(enum.IntEnum):
41
+ """笔记搜索方式。"""
42
+
43
+ TITLE = 0
44
+ CONTENT = 1
45
+
46
+
47
+ class SortType(enum.IntEnum):
48
+ """笔记排序方式。"""
49
+
50
+ MODIFY_TIME = 0
51
+ CREATE_TIME = 1
52
+ TITLE = 2
53
+ SIZE = 3
54
+
55
+
56
+ class FolderType(enum.IntEnum):
57
+ """笔记本类型。"""
58
+
59
+ USER_CREATED = 0
60
+ ALL_NOTES = 1
61
+ UNCATEGORIZED = 2
62
+
63
+
64
+ # ── 知识库数据结构 ────────────────────────────────────────────────────────────
65
+
66
+
67
+ @dataclass
68
+ class KnowledgeBaseInfo:
69
+ """知识库信息。"""
70
+
71
+ id: str = ""
72
+ name: str = ""
73
+ cover_url: str = ""
74
+ description: str = ""
75
+ recommended_questions: List[str] = field(default_factory=list)
76
+
77
+ @classmethod
78
+ def from_dict(cls, d: dict) -> KnowledgeBaseInfo:
79
+ return cls(
80
+ id=d.get("id", ""),
81
+ name=d.get("name", ""),
82
+ cover_url=d.get("cover_url", ""),
83
+ description=d.get("description", ""),
84
+ recommended_questions=d.get("recommended_questions", []),
85
+ )
86
+
87
+
88
+ @dataclass
89
+ class KnowledgeInfo:
90
+ """知识条目。"""
91
+
92
+ media_id: str = ""
93
+ title: str = ""
94
+ parent_folder_id: str = ""
95
+
96
+ @classmethod
97
+ def from_dict(cls, d: dict) -> KnowledgeInfo:
98
+ return cls(
99
+ media_id=d.get("media_id", ""),
100
+ title=d.get("title", ""),
101
+ parent_folder_id=d.get("parent_folder_id", ""),
102
+ )
103
+
104
+
105
+ @dataclass
106
+ class KBFolderInfo:
107
+ """知识库文件夹条目。"""
108
+
109
+ folder_id: str = ""
110
+ name: str = ""
111
+ file_number: int = 0
112
+ folder_number: int = 0
113
+ parent_folder_id: str = ""
114
+ is_top: bool = False
115
+
116
+ @classmethod
117
+ def from_dict(cls, d: dict) -> KBFolderInfo:
118
+ return cls(
119
+ folder_id=d.get("folder_id", ""),
120
+ name=d.get("name", ""),
121
+ file_number=d.get("file_number", 0),
122
+ folder_number=d.get("folder_number", 0),
123
+ parent_folder_id=d.get("parent_folder_id", ""),
124
+ is_top=d.get("is_top", False),
125
+ )
126
+
127
+
128
+ @dataclass
129
+ class AddableKnowledgeBaseInfo:
130
+ """可添加的知识库信息。"""
131
+
132
+ id: str = ""
133
+ name: str = ""
134
+
135
+ @classmethod
136
+ def from_dict(cls, d: dict) -> AddableKnowledgeBaseInfo:
137
+ return cls(id=d.get("id", ""), name=d.get("name", ""))
138
+
139
+
140
+ @dataclass
141
+ class SearchedKnowledgeBaseInfo:
142
+ """搜索到的知识库信息。"""
143
+
144
+ id: str = ""
145
+ name: str = ""
146
+ cover_url: str = ""
147
+
148
+ @classmethod
149
+ def from_dict(cls, d: dict) -> SearchedKnowledgeBaseInfo:
150
+ return cls(
151
+ id=d.get("id", "") or d.get("kb_id", ""),
152
+ name=d.get("name", "") or d.get("kb_name", ""),
153
+ cover_url=d.get("cover_url", ""),
154
+ )
155
+
156
+
157
+ @dataclass
158
+ class SearchedKnowledgeInfo:
159
+ """搜索到的知识条目。"""
160
+
161
+ media_id: str = ""
162
+ title: str = ""
163
+ parent_folder_id: str = ""
164
+ highlight_content: str = ""
165
+
166
+ @classmethod
167
+ def from_dict(cls, d: dict) -> SearchedKnowledgeInfo:
168
+ return cls(
169
+ media_id=d.get("media_id", ""),
170
+ title=d.get("title", ""),
171
+ parent_folder_id=d.get("parent_folder_id", ""),
172
+ highlight_content=d.get("highlight_content", ""),
173
+ )
174
+
175
+
176
+ @dataclass
177
+ class ImportURLResult:
178
+ """URL 导入结果。"""
179
+
180
+ url: str = ""
181
+ ret_code: int = 0
182
+ media_id: str = ""
183
+
184
+ @classmethod
185
+ def from_dict(cls, d: dict) -> ImportURLResult:
186
+ return cls(
187
+ url=d.get("url", ""),
188
+ ret_code=d.get("ret_code", 0),
189
+ media_id=d.get("media_id", ""),
190
+ )
191
+
192
+
193
+ @dataclass
194
+ class CosCredential:
195
+ """COS 上传凭证。"""
196
+
197
+ token: str = ""
198
+ secret_id: str = ""
199
+ secret_key: str = ""
200
+ start_time: int = 0
201
+ expired_time: int = 0
202
+ appid: str = ""
203
+ bucket_name: str = ""
204
+ region: str = ""
205
+ custom_domain: str = ""
206
+ cos_key: str = ""
207
+
208
+ @classmethod
209
+ def from_dict(cls, d: dict) -> CosCredential:
210
+ return cls(
211
+ token=d.get("token", ""),
212
+ secret_id=d.get("secret_id", ""),
213
+ secret_key=d.get("secret_key", ""),
214
+ start_time=int(d.get("start_time", 0)),
215
+ expired_time=int(d.get("expired_time", 0)),
216
+ appid=d.get("appid", ""),
217
+ bucket_name=d.get("bucket_name", ""),
218
+ region=d.get("region", ""),
219
+ custom_domain=d.get("custom_domain", ""),
220
+ cos_key=d.get("cos_key", ""),
221
+ )
222
+
223
+
224
+ @dataclass
225
+ class FileInfo:
226
+ """文件信息(add_knowledge 使用)。"""
227
+
228
+ cos_key: str = ""
229
+ file_size: int = 0
230
+ last_modify_time: int = 0
231
+ password: str = ""
232
+ file_name: str = ""
233
+
234
+ def to_dict(self) -> dict:
235
+ d: dict = {
236
+ "cos_key": self.cos_key,
237
+ "file_size": self.file_size,
238
+ "file_name": self.file_name,
239
+ }
240
+ if self.last_modify_time:
241
+ d["last_modify_time"] = self.last_modify_time
242
+ if self.password:
243
+ d["password"] = self.password
244
+ return d
245
+
246
+
247
+ @dataclass
248
+ class CheckRepeatedNameResult:
249
+ """文件名重复检查结果。"""
250
+
251
+ name: str = ""
252
+ is_repeated: bool = False
253
+
254
+ @classmethod
255
+ def from_dict(cls, d: dict) -> CheckRepeatedNameResult:
256
+ return cls(name=d.get("name", ""), is_repeated=d.get("is_repeated", False))
257
+
258
+
259
+ @dataclass
260
+ class CreateMediaResult:
261
+ """创建媒体返回结果。"""
262
+
263
+ media_id: str = ""
264
+ cos_credential: Optional[CosCredential] = None
265
+
266
+ @classmethod
267
+ def from_dict(cls, d: dict) -> CreateMediaResult:
268
+ cred = d.get("cos_credential")
269
+ return cls(
270
+ media_id=d.get("media_id", ""),
271
+ cos_credential=CosCredential.from_dict(cred) if cred else None,
272
+ )
273
+
274
+
275
+ # ── 知识库列表返回结构 ────────────────────────────────────────────────────────
276
+
277
+
278
+ @dataclass
279
+ class KnowledgeListResult:
280
+ """浏览知识库内容返回结果。"""
281
+
282
+ knowledge_list: List[KnowledgeInfo] = field(default_factory=list)
283
+ folder_list: List[KBFolderInfo] = field(default_factory=list)
284
+ is_end: bool = True
285
+ next_cursor: str = ""
286
+ current_path: List[KBFolderInfo] = field(default_factory=list)
287
+
288
+ @classmethod
289
+ def from_dict(cls, d: dict) -> KnowledgeListResult:
290
+ return cls(
291
+ knowledge_list=[
292
+ KnowledgeInfo.from_dict(i) for i in d.get("knowledge_list", [])
293
+ ],
294
+ folder_list=[
295
+ KBFolderInfo.from_dict(i) for i in d.get("folder_list", [])
296
+ ],
297
+ is_end=d.get("is_end", True),
298
+ next_cursor=d.get("next_cursor", ""),
299
+ current_path=[
300
+ KBFolderInfo.from_dict(i) for i in d.get("current_path", [])
301
+ ],
302
+ )
303
+
304
+
305
+ # ── 笔记数据结构 ─────────────────────────────────────────────────────────────
306
+
307
+
308
+ @dataclass
309
+ class DocBasic:
310
+ """笔记基本信息。"""
311
+
312
+ doc_id: str = ""
313
+ title: str = ""
314
+ summary: str = ""
315
+ create_time: int = 0
316
+ modify_time: int = 0
317
+ status: int = 0 # 0=正常, 1=已删除
318
+ folder_id: str = ""
319
+ folder_name: str = ""
320
+
321
+ @classmethod
322
+ def from_dict(cls, d: dict) -> DocBasic:
323
+ return cls(
324
+ doc_id=d.get("docid", ""),
325
+ title=d.get("title", ""),
326
+ summary=d.get("summary", ""),
327
+ create_time=d.get("create_time", 0),
328
+ modify_time=d.get("modify_time", 0),
329
+ status=d.get("status", 0),
330
+ folder_id=d.get("folder_id", ""),
331
+ folder_name=d.get("folder_name", ""),
332
+ )
333
+
334
+
335
+ @dataclass
336
+ class NoteFolderItem:
337
+ """笔记本条目。"""
338
+
339
+ folder_id: str = ""
340
+ name: str = ""
341
+ note_number: int = 0
342
+ create_time: int = 0
343
+ modify_time: int = 0
344
+ parent_folder_id: str = ""
345
+ folder_type: int = 0 # 0=用户自建, 1=全部笔记, 2=未分类
346
+ status: int = 0
347
+
348
+ @classmethod
349
+ def from_dict(cls, d: dict) -> NoteFolderItem:
350
+ # API 返回嵌套结构: folder.basic_info.{fields}
351
+ basic = d
352
+ if "folder" in d:
353
+ folder = d["folder"]
354
+ if "basic_info" in folder:
355
+ basic = folder["basic_info"]
356
+ return cls(
357
+ folder_id=basic.get("folder_id", ""),
358
+ name=basic.get("name", ""),
359
+ note_number=basic.get("note_number", 0),
360
+ create_time=basic.get("create_time", 0),
361
+ modify_time=basic.get("modify_time", 0),
362
+ parent_folder_id=basic.get("parent_folder_id", ""),
363
+ folder_type=basic.get("folder_type", 0),
364
+ status=basic.get("status", 0),
365
+ )
366
+
367
+
368
+ @dataclass
369
+ class NoteBookInfo:
370
+ """笔记信息(笔记列表返回)。"""
371
+
372
+ doc: DocBasic = field(default_factory=DocBasic)
373
+
374
+ @classmethod
375
+ def from_dict(cls, d: dict) -> NoteBookInfo:
376
+ # API 返回嵌套结构: basic_info.basic_info.{fields}
377
+ basic = d
378
+ if "basic_info" in d:
379
+ inner = d["basic_info"]
380
+ if "basic_info" in inner:
381
+ basic = inner["basic_info"]
382
+ else:
383
+ basic = inner
384
+ return cls(doc=DocBasic.from_dict(basic))
385
+
386
+
387
+ @dataclass
388
+ class SearchedDoc:
389
+ """搜索到的笔记。"""
390
+
391
+ doc: DocBasic = field(default_factory=DocBasic)
392
+ highlight_info: Dict[str, str] = field(default_factory=dict)
393
+
394
+ @classmethod
395
+ def from_dict(cls, d: dict) -> SearchedDoc:
396
+ doc_data = d.get("doc", {})
397
+ basic = doc_data
398
+ if "basic_info" in doc_data:
399
+ inner = doc_data["basic_info"]
400
+ if "basic_info" in inner:
401
+ basic = inner["basic_info"]
402
+ else:
403
+ basic = inner
404
+ return cls(
405
+ doc=DocBasic.from_dict(basic),
406
+ highlight_info=d.get("highlight_info", {}),
407
+ )
408
+
409
+
410
+ # ── 文件预检结果 ─────────────────────────────────────────────────────────────
411
+
412
+
413
+ @dataclass
414
+ class FileCheckResult:
415
+ """文件预检结果。"""
416
+
417
+ passed: bool = False
418
+ file_path: str = ""
419
+ file_name: str = ""
420
+ file_ext: str = ""
421
+ file_size: int = 0
422
+ media_type: Optional[int] = None
423
+ content_type: Optional[str] = None
424
+ reason: str = ""