kdocs-sql-model 1.0.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.
- kdocs_sql_model/__init__.py +40 -0
- kdocs_sql_model/_client.py +120 -0
- kdocs_sql_model/kdocs_sql_model.py +911 -0
- kdocs_sql_model/py.typed +0 -0
- kdocs_sql_model-1.0.0.dist-info/METADATA +1432 -0
- kdocs_sql_model-1.0.0.dist-info/RECORD +9 -0
- kdocs_sql_model-1.0.0.dist-info/WHEEL +5 -0
- kdocs_sql_model-1.0.0.dist-info/licenses/LICENSE +674 -0
- kdocs_sql_model-1.0.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
#!/usr/bin/env python
|
|
2
|
+
# -*- coding: utf-8 -*-
|
|
3
|
+
"""
|
|
4
|
+
KDocsSQL Model - 类似 sqlite3 的数据库操作接口
|
|
5
|
+
|
|
6
|
+
提供与 sqlite3 模块兼容的 API,降低学习成本。
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
from .kdocs_sql_model import (
|
|
10
|
+
connect,
|
|
11
|
+
Connection,
|
|
12
|
+
Cursor,
|
|
13
|
+
KDocsSQLError,
|
|
14
|
+
OperationalError,
|
|
15
|
+
DatabaseError,
|
|
16
|
+
ProgrammingError,
|
|
17
|
+
complete_statement,
|
|
18
|
+
apilevel,
|
|
19
|
+
threadsafety,
|
|
20
|
+
paramstyle,
|
|
21
|
+
)
|
|
22
|
+
from ._client import KDocsSQLClient
|
|
23
|
+
|
|
24
|
+
__version__ = "1.0.0"
|
|
25
|
+
__author__ = "xiaomayisjh"
|
|
26
|
+
|
|
27
|
+
__all__ = [
|
|
28
|
+
'connect',
|
|
29
|
+
'Connection',
|
|
30
|
+
'Cursor',
|
|
31
|
+
'KDocsSQLError',
|
|
32
|
+
'OperationalError',
|
|
33
|
+
'DatabaseError',
|
|
34
|
+
'ProgrammingError',
|
|
35
|
+
'complete_statement',
|
|
36
|
+
'apilevel',
|
|
37
|
+
'threadsafety',
|
|
38
|
+
'paramstyle',
|
|
39
|
+
'KDocsSQLClient',
|
|
40
|
+
]
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
#!/usr/bin/env python
|
|
2
|
+
# -*- coding: utf-8 -*-
|
|
3
|
+
"""
|
|
4
|
+
KDocsSQL Python Client - 金山文档 SQL 引擎客户端
|
|
5
|
+
|
|
6
|
+
内部模块,用于 HTTP API 调用。
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
import json
|
|
10
|
+
|
|
11
|
+
try:
|
|
12
|
+
import requests
|
|
13
|
+
except ImportError:
|
|
14
|
+
raise ImportError("缺少 requests 库,请运行: pip install requests")
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
class KDocsSQLClient:
|
|
18
|
+
"""
|
|
19
|
+
KDocsSQL Python 客户端
|
|
20
|
+
|
|
21
|
+
用于通过 HTTP API 调用金山文档 AirScript SQL 引擎。
|
|
22
|
+
|
|
23
|
+
Attributes:
|
|
24
|
+
api_token (str): AirScript API Token
|
|
25
|
+
webhook_url (str): Webhook URL
|
|
26
|
+
timeout (int): 请求超时时间(秒)
|
|
27
|
+
"""
|
|
28
|
+
|
|
29
|
+
def __init__(self, api_token, webhook_url, timeout=30):
|
|
30
|
+
self.api_token = api_token
|
|
31
|
+
self.webhook_url = webhook_url
|
|
32
|
+
self.timeout = timeout
|
|
33
|
+
|
|
34
|
+
def execute(self, sql):
|
|
35
|
+
"""
|
|
36
|
+
执行 SQL 语句
|
|
37
|
+
|
|
38
|
+
Args:
|
|
39
|
+
sql (str): SQL 语句
|
|
40
|
+
|
|
41
|
+
Returns:
|
|
42
|
+
dict: 执行结果
|
|
43
|
+
"""
|
|
44
|
+
headers = {
|
|
45
|
+
"Content-Type": "application/json",
|
|
46
|
+
"AirScript-Token": self.api_token
|
|
47
|
+
}
|
|
48
|
+
payload = {"Context": {"argv": {"sql": sql}}}
|
|
49
|
+
|
|
50
|
+
try:
|
|
51
|
+
response = requests.post(
|
|
52
|
+
self.webhook_url,
|
|
53
|
+
headers=headers,
|
|
54
|
+
json=payload,
|
|
55
|
+
timeout=self.timeout
|
|
56
|
+
)
|
|
57
|
+
|
|
58
|
+
if response.status_code != 200:
|
|
59
|
+
return {
|
|
60
|
+
"success": False,
|
|
61
|
+
"error": "HTTP_ERROR",
|
|
62
|
+
"message": f"HTTP {response.status_code}: {response.text[:200]}"
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
return self._parse_response(response.json())
|
|
66
|
+
|
|
67
|
+
except requests.exceptions.Timeout:
|
|
68
|
+
return {
|
|
69
|
+
"success": False,
|
|
70
|
+
"error": "TIMEOUT",
|
|
71
|
+
"message": f"请求超时 ({self.timeout}秒)"
|
|
72
|
+
}
|
|
73
|
+
except requests.exceptions.ConnectionError:
|
|
74
|
+
return {
|
|
75
|
+
"success": False,
|
|
76
|
+
"error": "CONNECTION_ERROR",
|
|
77
|
+
"message": "网络连接失败"
|
|
78
|
+
}
|
|
79
|
+
except json.JSONDecodeError:
|
|
80
|
+
return {
|
|
81
|
+
"success": False,
|
|
82
|
+
"error": "JSON_ERROR",
|
|
83
|
+
"message": "响应解析失败"
|
|
84
|
+
}
|
|
85
|
+
except Exception as e:
|
|
86
|
+
return {
|
|
87
|
+
"success": False,
|
|
88
|
+
"error": "UNKNOWN_ERROR",
|
|
89
|
+
"message": str(e)
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
def _parse_response(self, response):
|
|
93
|
+
"""解析 API 响应"""
|
|
94
|
+
if not response.get("success") and response.get("error"):
|
|
95
|
+
return {
|
|
96
|
+
"success": False,
|
|
97
|
+
"error": "API_ERROR",
|
|
98
|
+
"message": response.get("error", "未知错误")
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
data = response.get("data", {})
|
|
102
|
+
result = data.get("result", {})
|
|
103
|
+
|
|
104
|
+
if not result.get("success", True):
|
|
105
|
+
return {
|
|
106
|
+
"success": False,
|
|
107
|
+
"error": result.get("error", "EXECUTION_ERROR"),
|
|
108
|
+
"message": result.get("message", "执行失败"),
|
|
109
|
+
"position": result.get("position")
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
return {
|
|
113
|
+
"success": True,
|
|
114
|
+
"type": result.get("type", ""),
|
|
115
|
+
"data": result.get("data", []),
|
|
116
|
+
"rowCount": result.get("rowCount", 0),
|
|
117
|
+
"affectedRows": result.get("affectedRows", 0),
|
|
118
|
+
"columns": result.get("columns", []),
|
|
119
|
+
"executionTime": result.get("executionTime", 0)
|
|
120
|
+
}
|