hjxdl 0.3.34__py3-none-any.whl → 0.3.40__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.
- hdl/_version.py +2 -2
- hdl/utils/decorators/llm.py +1 -1
- hdl/utils/general/runners.py +22 -1
- hdl/utils/llm/llm_wrapper.py +23 -2
- hdl/utils/llm/vis.py +68 -0
- {hjxdl-0.3.34.dist-info → hjxdl-0.3.40.dist-info}/METADATA +3 -2
- {hjxdl-0.3.34.dist-info → hjxdl-0.3.40.dist-info}/RECORD +10 -10
- {hjxdl-0.3.34.dist-info → hjxdl-0.3.40.dist-info}/WHEEL +1 -1
- {hjxdl-0.3.34.dist-info → hjxdl-0.3.40.dist-info/licenses}/LICENSE +0 -0
- {hjxdl-0.3.34.dist-info → hjxdl-0.3.40.dist-info}/top_level.txt +0 -0
hdl/_version.py
CHANGED
hdl/utils/decorators/llm.py
CHANGED
@@ -45,7 +45,7 @@ def measure_stream_performance(func):
|
|
45
45
|
|
46
46
|
# 总时间计算
|
47
47
|
end_time = time.time()
|
48
|
-
total_time = end_time -
|
48
|
+
total_time = end_time - first_char_time
|
49
49
|
time_to_first_char = first_char_time - start_time if first_char_time else total_time
|
50
50
|
|
51
51
|
# 每秒输出的字符数
|
hdl/utils/general/runners.py
CHANGED
@@ -18,6 +18,7 @@ def execute_code(code):
|
|
18
18
|
# Execute the code in a subprocess for safety
|
19
19
|
print(code)
|
20
20
|
python_path = sys.executable # 获取当前 Python 解释器路径
|
21
|
+
python_path = sys.executable
|
21
22
|
result = subprocess.run(
|
22
23
|
[
|
23
24
|
python_path, # 使用当前 conda 环境中的 Python
|
@@ -26,6 +27,13 @@ def execute_code(code):
|
|
26
27
|
],
|
27
28
|
capture_output=True,
|
28
29
|
text=True,
|
30
|
+
timeout=5,
|
31
|
+
python_path,
|
32
|
+
'-c',
|
33
|
+
code
|
34
|
+
],
|
35
|
+
capture_output=True,
|
36
|
+
text=True,
|
29
37
|
timeout=5,
|
30
38
|
env={"PYTHONPATH": os.getcwd()}
|
31
39
|
)
|
@@ -119,8 +127,20 @@ def count_character_occurrences(text, char):
|
|
119
127
|
# # 等待进程结束
|
120
128
|
# process.wait()
|
121
129
|
|
122
|
-
|
123
130
|
def run_cmd(cmd: str):
|
131
|
+
"""
|
132
|
+
Executes a command in a subprocess.
|
133
|
+
|
134
|
+
This function receives a command string, splits it into separate arguments,
|
135
|
+
and then executes it in a subprocess. The output of the subprocess is
|
136
|
+
neither redirected to stdout nor stderr.
|
137
|
+
|
138
|
+
Args:
|
139
|
+
cmd (str): The command to execute.
|
140
|
+
|
141
|
+
Returns:
|
142
|
+
None
|
143
|
+
"""
|
124
144
|
command = cmd.split(" ")
|
125
145
|
|
126
146
|
# 直接执行命令,让 stdout 和 stderr 直接流式输出到终端
|
@@ -128,3 +148,4 @@ def run_cmd(cmd: str):
|
|
128
148
|
|
129
149
|
# 等待进程执行完
|
130
150
|
process.wait()
|
151
|
+
|
hdl/utils/llm/llm_wrapper.py
CHANGED
@@ -142,6 +142,8 @@ class OpenAIWrapper(object):
|
|
142
142
|
assis_info: str = None,
|
143
143
|
images: list = None,
|
144
144
|
image_keys: tuple = ("image_url", "url"),
|
145
|
+
videos: list = None,
|
146
|
+
video_keys: tuple = ("video_url", "url"),
|
145
147
|
model: str=None,
|
146
148
|
tools: list = None,
|
147
149
|
tool_choice: str = "auto",
|
@@ -207,10 +209,30 @@ class OpenAIWrapper(object):
|
|
207
209
|
elif len(image_keys) == 1:
|
208
210
|
image_keys = (image_keys[0],) * 3
|
209
211
|
|
212
|
+
if isinstance(video_keys, str):
|
213
|
+
video_keys = (video_keys,) * 3
|
214
|
+
elif len(video_keys) == 2:
|
215
|
+
video_keys = (video_keys[0],) + tuple(video_keys)
|
216
|
+
elif len(video_keys) == 1:
|
217
|
+
video_keys = (video_keys[0],) * 3
|
218
|
+
|
210
219
|
content = [{
|
211
220
|
"type": "text",
|
212
221
|
"text": prompt
|
213
222
|
}]
|
223
|
+
|
224
|
+
if videos:
|
225
|
+
if isinstance(videos, str):
|
226
|
+
images = [videos]
|
227
|
+
for video in videos:
|
228
|
+
content.append({
|
229
|
+
"type": video_keys[0],
|
230
|
+
video_keys[1]: {
|
231
|
+
video_keys[2]: img
|
232
|
+
}
|
233
|
+
})
|
234
|
+
|
235
|
+
|
214
236
|
if images:
|
215
237
|
if isinstance(images, str):
|
216
238
|
images = [images]
|
@@ -221,8 +243,7 @@ class OpenAIWrapper(object):
|
|
221
243
|
image_keys[2]: img
|
222
244
|
}
|
223
245
|
})
|
224
|
-
|
225
|
-
# If no images are provided, content is simply the prompt text
|
246
|
+
if (not images) and (not videos):
|
226
247
|
content = prompt
|
227
248
|
|
228
249
|
# Add the user's input as a message
|
hdl/utils/llm/vis.py
CHANGED
@@ -24,6 +24,13 @@ from hdl.jupyfuncs.show.pbar import tqdm
|
|
24
24
|
from redis.commands.search.query import Query
|
25
25
|
|
26
26
|
|
27
|
+
from decord import VideoReader, cpu
|
28
|
+
|
29
|
+
import base64
|
30
|
+
from io import BytesIO
|
31
|
+
from PIL import Image
|
32
|
+
import numpy as np
|
33
|
+
import requests
|
27
34
|
# from ..database_tools.connect import conn_redis
|
28
35
|
|
29
36
|
|
@@ -731,4 +738,65 @@ class ImgHandler:
|
|
731
738
|
return results
|
732
739
|
|
733
740
|
|
741
|
+
def to_video_base64(video_path, max_frames=80, is_fps_sampling=True):
|
742
|
+
"""
|
743
|
+
Converts a video file or a video from a given URL to a list of base64 encoded image frames.
|
744
|
+
|
745
|
+
Args:
|
746
|
+
video_path (str): The path to the video file or the URL of the video.
|
747
|
+
max_frames (int, optional): The maximum number of frames to return. Defaults to 80.
|
748
|
+
is_fps_sampling (bool, optional): A flag to indicate whether to sample frames based on average FPS. Defaults to True.
|
734
749
|
|
750
|
+
Returns:
|
751
|
+
list: A list of base64 encoded strings representing the sampled frames of the video.
|
752
|
+
|
753
|
+
Raises:
|
754
|
+
Exception: If the video cannot be loaded or if the URL is unreachable.
|
755
|
+
|
756
|
+
Note:
|
757
|
+
This function uses the VideoReader class for reading video frames and requires the necessary libraries for handling images and base64 encoding.
|
758
|
+
"""
|
759
|
+
if video_path.startswith("http") or video_path.startswith("https"):
|
760
|
+
response = requests.get(video_path)
|
761
|
+
if response.status_code == 200:
|
762
|
+
video_path = BytesIO(response.content)
|
763
|
+
else:
|
764
|
+
print('failed to load the video')
|
765
|
+
|
766
|
+
vr = VideoReader(video_path, ctx=cpu(0), num_threads=1)
|
767
|
+
total_frame_num = len(vr)
|
768
|
+
if is_fps_sampling:
|
769
|
+
# FPS Sampling
|
770
|
+
avg_fps = round(vr.get_avg_fps())
|
771
|
+
frame_idx = [i for i in range(
|
772
|
+
0, total_frame_num, avg_fps)]
|
773
|
+
if len(frame_idx) > max_frames:
|
774
|
+
uniform_sampled_frames = np.linspace(
|
775
|
+
0, total_frame_num - 1, max_frames, dtype=int
|
776
|
+
)
|
777
|
+
frame_idx = uniform_sampled_frames.tolist()
|
778
|
+
print(frame_idx)
|
779
|
+
else:
|
780
|
+
# uniform sampling
|
781
|
+
if total_frame_num > max_frames:
|
782
|
+
uniform_sampled_frames = np.linspace(
|
783
|
+
0, total_frame_num - 1, max_frames, dtype=int
|
784
|
+
)
|
785
|
+
frame_idx = uniform_sampled_frames.tolist()
|
786
|
+
else:
|
787
|
+
frame_idx = [i for i in range(0, total_frame_num)]
|
788
|
+
print(frame_idx)
|
789
|
+
|
790
|
+
frames = vr.get_batch(frame_idx).asnumpy()
|
791
|
+
print("actual frames", len(frames))
|
792
|
+
|
793
|
+
base64_frames = []
|
794
|
+
for frame in frames:
|
795
|
+
img = Image.fromarray(frame)
|
796
|
+
output_buffer = BytesIO()
|
797
|
+
img.save(output_buffer, format="PNG")
|
798
|
+
|
799
|
+
byte_data = output_buffer.getvalue()
|
800
|
+
base64_str = base64.b64encode(byte_data).decode("utf-8")
|
801
|
+
base64_frames.append(base64_str)
|
802
|
+
return base64_frames
|
@@ -1,6 +1,6 @@
|
|
1
|
-
Metadata-Version: 2.
|
1
|
+
Metadata-Version: 2.4
|
2
2
|
Name: hjxdl
|
3
|
-
Version: 0.3.
|
3
|
+
Version: 0.3.40
|
4
4
|
Summary: A collection of functions for Jupyter notebooks
|
5
5
|
Home-page: https://github.com/huluxiaohuowa/hdl
|
6
6
|
Author: Jianxing Hu
|
@@ -31,6 +31,7 @@ Dynamic: classifier
|
|
31
31
|
Dynamic: description
|
32
32
|
Dynamic: description-content-type
|
33
33
|
Dynamic: home-page
|
34
|
+
Dynamic: license-file
|
34
35
|
Dynamic: requires-dist
|
35
36
|
Dynamic: requires-python
|
36
37
|
Dynamic: summary
|
@@ -1,5 +1,5 @@
|
|
1
1
|
hdl/__init__.py,sha256=GffnD0jLJdhkd-vo989v40N90sQbofkayRBwxc6TVhQ,72
|
2
|
-
hdl/_version.py,sha256=
|
2
|
+
hdl/_version.py,sha256=FM2ay9B4jNpEspCcoKvkx6ALhoNo3bt_Okj6w9c819c,513
|
3
3
|
hdl/args/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
4
4
|
hdl/args/loss_args.py,sha256=s7YzSdd7IjD24rZvvOrxLLFqMZQb9YylxKeyelSdrTk,70
|
5
5
|
hdl/controllers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
@@ -122,30 +122,30 @@ hdl/utils/database_tools/connect.py,sha256=xCacGucKxlQUXs6AsNddpeECvdqT1180V1ZWq
|
|
122
122
|
hdl/utils/database_tools/datetime.py,sha256=xqE2xNiOpADzX-R8_bM0bioJRF3Ay9Jp1CAG6dy6uVI,1202
|
123
123
|
hdl/utils/database_tools/web.py,sha256=awJ8lafL-2KRjf3V1uuij8JIvX9U5fI8fLZKOkOvqtk,5771
|
124
124
|
hdl/utils/decorators/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
125
|
-
hdl/utils/decorators/llm.py,sha256=
|
125
|
+
hdl/utils/decorators/llm.py,sha256=PeoSrPLwTE8DRfjUdEXADjxK5FQH4Gd651_FgXEEdFE,3115
|
126
126
|
hdl/utils/desc/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
127
127
|
hdl/utils/desc/func_desc.py,sha256=sHmVZZmV7Zgii--gnHqMs6fTb7HVkqTOf8Pl_0F6qlI,3808
|
128
128
|
hdl/utils/desc/template.py,sha256=Kf_tbL-XkDCKNQ3UncbCuYEeUgXEa7kRVCf9TD2b8og,2526
|
129
129
|
hdl/utils/desc/tools.py,sha256=tovV4sqjMBCHI6PG5YGJYBKpoXRhgYilzt77ZYTL7Jk,673
|
130
130
|
hdl/utils/general/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
131
131
|
hdl/utils/general/glob.py,sha256=Zuf7WHU0UdUPOs9UrhxmrCiMC8GrHxQU6n3mTThv6yc,1120
|
132
|
-
hdl/utils/general/runners.py,sha256=
|
132
|
+
hdl/utils/general/runners.py,sha256=R0lhqABIuT43jEyjFkeio84e_PFfvAkszOP1FBlAnQ8,4927
|
133
133
|
hdl/utils/llm/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
134
134
|
hdl/utils/llm/chat.py,sha256=q0zQmf-6DeSYOrC2qDn_QFOlILjRHU69eVRUn0eIIbA,26526
|
135
135
|
hdl/utils/llm/chatgr.py,sha256=5F5PJHe8vz3iCfi4TT54DCLRi1UeJshECdVtgvvvao0,3696
|
136
136
|
hdl/utils/llm/embs.py,sha256=Tf0FOYrOFZp7qQpEPiSCXzlgyHH0X9HVTUtsup74a9E,7174
|
137
137
|
hdl/utils/llm/extract.py,sha256=2sK_WJzmYIc8iuWaM9DA6Nw3_6q1O4lJ5pKpcZo-bBA,6512
|
138
138
|
hdl/utils/llm/llama_chat.py,sha256=watcHGOaz-bv3x-yDucYlGk5f8FiqfFhwWogrl334fk,4387
|
139
|
-
hdl/utils/llm/llm_wrapper.py,sha256=
|
139
|
+
hdl/utils/llm/llm_wrapper.py,sha256=kectOfy2lbT0UcSYXbbmeQDlYMtdf6gpV10fI7ilgug,15929
|
140
140
|
hdl/utils/llm/ollama.py,sha256=uEdLsNAc6b56r37hNiE3nrd6oZ2lmQ0gYbVvOc9YVIM,1389
|
141
|
-
hdl/utils/llm/vis.py,sha256=
|
141
|
+
hdl/utils/llm/vis.py,sha256=CLZApXlC636mYsxP7yg1UWRn0Q16pXpOX8ShJbfv5us,28739
|
142
142
|
hdl/utils/llm/visrag.py,sha256=0i-VrxqgiV-J7R3VPshu9oc7-rKjFJOldYik3HDXj6M,10176
|
143
143
|
hdl/utils/schedulers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
144
144
|
hdl/utils/schedulers/norm_lr.py,sha256=bDwCmdEK-WkgxQMFBiMuchv8Mm7C0-GZJ6usm-PQk14,4461
|
145
145
|
hdl/utils/weather/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
146
146
|
hdl/utils/weather/weather.py,sha256=k11o6wM15kF8b9NMlEfrg68ak-SfSYLN3nOOflFUv-I,4381
|
147
|
-
hjxdl-0.3.
|
148
|
-
hjxdl-0.3.
|
149
|
-
hjxdl-0.3.
|
150
|
-
hjxdl-0.3.
|
151
|
-
hjxdl-0.3.
|
147
|
+
hjxdl-0.3.40.dist-info/licenses/LICENSE,sha256=lkMiSbeZHBQLB9LJEkS9-L3Z-LBC4yGnKrzHSG8RkPM,2599
|
148
|
+
hjxdl-0.3.40.dist-info/METADATA,sha256=otgYEo9D3UeXTRx9Qqgyi7e5f4t6ZonGvfTdDbMoS4I,1358
|
149
|
+
hjxdl-0.3.40.dist-info/WHEEL,sha256=CmyFI0kx5cdEMTLiONQRbGQwjIoR1aIYB7eCAQ4KPJ0,91
|
150
|
+
hjxdl-0.3.40.dist-info/top_level.txt,sha256=-kxwTM5JPhylp06z3zAVO3w6_h7wtBfBo2zgM6YZoTk,4
|
151
|
+
hjxdl-0.3.40.dist-info/RECORD,,
|
File without changes
|
File without changes
|