langtrace-python-sdk 2.1.12__py3-none-any.whl → 2.1.13__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.
- examples/openai_example/images_edit.py +40 -0
- examples/openai_example/resources/lounge_flamingo.png +0 -0
- examples/openai_example/resources/mask.png +0 -0
- langtrace_python_sdk/constants/instrumentation/openai.py +4 -0
- langtrace_python_sdk/instrumentation/openai/instrumentation.py +9 -1
- langtrace_python_sdk/instrumentation/openai/patch.py +85 -3
- langtrace_python_sdk/version.py +1 -1
- {langtrace_python_sdk-2.1.12.dist-info → langtrace_python_sdk-2.1.13.dist-info}/METADATA +2 -2
- {langtrace_python_sdk-2.1.12.dist-info → langtrace_python_sdk-2.1.13.dist-info}/RECORD +11 -8
- {langtrace_python_sdk-2.1.12.dist-info → langtrace_python_sdk-2.1.13.dist-info}/WHEEL +0 -0
- {langtrace_python_sdk-2.1.12.dist-info → langtrace_python_sdk-2.1.13.dist-info}/licenses/LICENSE +0 -0
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
from dotenv import find_dotenv, load_dotenv
|
|
2
|
+
from openai import OpenAI
|
|
3
|
+
|
|
4
|
+
from langtrace_python_sdk import langtrace
|
|
5
|
+
|
|
6
|
+
# from PIL import Image
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
_ = load_dotenv(find_dotenv())
|
|
10
|
+
|
|
11
|
+
langtrace.init(write_spans_to_console=True)
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
client = OpenAI()
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
# use this to convert the image to RGBA
|
|
18
|
+
# def convert_to_rgba():
|
|
19
|
+
# Image.open("./resources/image.png").convert("RGBA").save("./resources/image_with_alpha.png")
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def image_edit():
|
|
23
|
+
|
|
24
|
+
response = client.images.edit(
|
|
25
|
+
model="dall-e-2",
|
|
26
|
+
image=open("./resources/lounge_flamingo.png", "rb"),
|
|
27
|
+
mask=open("./resources/mask.png", "rb"),
|
|
28
|
+
prompt="A sunlit indoor lounge area with a pool and duck standing in side with flamingo.",
|
|
29
|
+
n=1,
|
|
30
|
+
size="1024x1024",
|
|
31
|
+
response_format="url",
|
|
32
|
+
)
|
|
33
|
+
|
|
34
|
+
image_url = response.data[0].url
|
|
35
|
+
print(image_url)
|
|
36
|
+
print(response)
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
image_edit()
|
|
40
|
+
# convert_to_rgba()
|
|
Binary file
|
|
Binary file
|
|
@@ -40,6 +40,10 @@ APIS = {
|
|
|
40
40
|
"METHOD": OpenAIMethods.IMAGES_GENERATION.value,
|
|
41
41
|
"ENDPOINT": "/images/generations",
|
|
42
42
|
},
|
|
43
|
+
"IMAGES_EDIT": {
|
|
44
|
+
"METHOD": OpenAIMethods.IMAGES_EDIT.value,
|
|
45
|
+
"ENDPOINT": "/images/edits",
|
|
46
|
+
},
|
|
43
47
|
"EMBEDDINGS_CREATE": {
|
|
44
48
|
"METHOD": OpenAIMethods.EMBEDDINGS_CREATE.value,
|
|
45
49
|
"ENDPOINT": "/embeddings",
|
|
@@ -28,6 +28,7 @@ from langtrace_python_sdk.instrumentation.openai.patch import (
|
|
|
28
28
|
async_images_generate,
|
|
29
29
|
chat_completions_create,
|
|
30
30
|
embeddings_create,
|
|
31
|
+
images_edit,
|
|
31
32
|
images_generate,
|
|
32
33
|
)
|
|
33
34
|
|
|
@@ -37,7 +38,7 @@ logging.basicConfig(level=logging.FATAL)
|
|
|
37
38
|
class OpenAIInstrumentation(BaseInstrumentor):
|
|
38
39
|
|
|
39
40
|
def instrumentation_dependencies(self) -> Collection[str]:
|
|
40
|
-
return ["openai >= 0.27.0"]
|
|
41
|
+
return ["openai >= 0.27.0", "trace-attributes >= 4.0.5"]
|
|
41
42
|
|
|
42
43
|
def _instrument(self, **kwargs):
|
|
43
44
|
tracer_provider = kwargs.get("tracer_provider")
|
|
@@ -69,6 +70,13 @@ class OpenAIInstrumentation(BaseInstrumentor):
|
|
|
69
70
|
"AsyncImages.generate",
|
|
70
71
|
async_images_generate("openai.images.generate", version, tracer),
|
|
71
72
|
)
|
|
73
|
+
|
|
74
|
+
wrap_function_wrapper(
|
|
75
|
+
"openai.resources.images",
|
|
76
|
+
"Images.edit",
|
|
77
|
+
images_edit("openai.images.edit", version, tracer),
|
|
78
|
+
)
|
|
79
|
+
|
|
72
80
|
wrap_function_wrapper(
|
|
73
81
|
"openai.resources.embeddings",
|
|
74
82
|
"Embeddings.create",
|
|
@@ -16,20 +16,19 @@ limitations under the License.
|
|
|
16
16
|
|
|
17
17
|
import json
|
|
18
18
|
|
|
19
|
+
from importlib_metadata import version as v
|
|
19
20
|
from langtrace.trace_attributes import Event, LLMSpanAttributes
|
|
20
21
|
from opentelemetry import baggage
|
|
21
22
|
from opentelemetry.trace import SpanKind
|
|
22
23
|
from opentelemetry.trace.status import Status, StatusCode
|
|
23
24
|
|
|
25
|
+
from langtrace_python_sdk.constants import LANGTRACE_SDK_NAME
|
|
24
26
|
from langtrace_python_sdk.constants.instrumentation.common import (
|
|
25
27
|
LANGTRACE_ADDITIONAL_SPAN_ATTRIBUTES_KEY,
|
|
26
28
|
SERVICE_PROVIDERS,
|
|
27
29
|
)
|
|
28
30
|
from langtrace_python_sdk.constants.instrumentation.openai import APIS
|
|
29
31
|
from langtrace_python_sdk.utils.llm import calculate_prompt_tokens, estimate_tokens
|
|
30
|
-
from importlib_metadata import version as v
|
|
31
|
-
|
|
32
|
-
from langtrace_python_sdk.constants import LANGTRACE_SDK_NAME
|
|
33
32
|
|
|
34
33
|
|
|
35
34
|
def images_generate(original_method, version, tracer):
|
|
@@ -187,6 +186,89 @@ def async_images_generate(original_method, version, tracer):
|
|
|
187
186
|
return traced_method
|
|
188
187
|
|
|
189
188
|
|
|
189
|
+
def images_edit(original_method, version, tracer):
|
|
190
|
+
"""
|
|
191
|
+
Wrap the `edit` method of the `Images` class to trace it.
|
|
192
|
+
"""
|
|
193
|
+
|
|
194
|
+
def traced_method(wrapped, instance, args, kwargs):
|
|
195
|
+
base_url = (
|
|
196
|
+
str(instance._client._base_url)
|
|
197
|
+
if hasattr(instance, "_client") and hasattr(instance._client, "_base_url")
|
|
198
|
+
else ""
|
|
199
|
+
)
|
|
200
|
+
service_provider = SERVICE_PROVIDERS["OPENAI"]
|
|
201
|
+
extra_attributes = baggage.get_baggage(LANGTRACE_ADDITIONAL_SPAN_ATTRIBUTES_KEY)
|
|
202
|
+
|
|
203
|
+
span_attributes = {
|
|
204
|
+
"langtrace.sdk.name": "langtrace-python-sdk",
|
|
205
|
+
"langtrace.service.name": service_provider,
|
|
206
|
+
"langtrace.service.type": "llm",
|
|
207
|
+
"langtrace.service.version": version,
|
|
208
|
+
"langtrace.version": v(LANGTRACE_SDK_NAME),
|
|
209
|
+
"url.full": base_url,
|
|
210
|
+
"llm.api": APIS["IMAGES_EDIT"]["ENDPOINT"],
|
|
211
|
+
"llm.model": kwargs.get("model"),
|
|
212
|
+
"llm.response_format": kwargs.get("response_format"),
|
|
213
|
+
"llm.image.size": kwargs.get("size"),
|
|
214
|
+
"llm.prompts": json.dumps(
|
|
215
|
+
[
|
|
216
|
+
{
|
|
217
|
+
"role": kwargs.get("user", "user"),
|
|
218
|
+
"content": kwargs.get("prompt", []),
|
|
219
|
+
}
|
|
220
|
+
]
|
|
221
|
+
),
|
|
222
|
+
"llm.top_k": kwargs.get("n"),
|
|
223
|
+
**(extra_attributes if extra_attributes is not None else {}),
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
attributes = LLMSpanAttributes(**span_attributes)
|
|
227
|
+
|
|
228
|
+
with tracer.start_as_current_span(
|
|
229
|
+
APIS["IMAGES_EDIT"]["METHOD"], kind=SpanKind.CLIENT
|
|
230
|
+
) as span:
|
|
231
|
+
for field, value in attributes.model_dump(by_alias=True).items():
|
|
232
|
+
if value is not None:
|
|
233
|
+
span.set_attribute(field, value)
|
|
234
|
+
try:
|
|
235
|
+
# Attempt to call the original method
|
|
236
|
+
result = wrapped(*args, **kwargs)
|
|
237
|
+
|
|
238
|
+
response = []
|
|
239
|
+
# Parse each image object
|
|
240
|
+
for each_data in result.data:
|
|
241
|
+
response.append(
|
|
242
|
+
{
|
|
243
|
+
"role": "assistant",
|
|
244
|
+
"content": {
|
|
245
|
+
"url": each_data.url,
|
|
246
|
+
"revised_prompt": each_data.revised_prompt,
|
|
247
|
+
"base64": each_data.b64_json,
|
|
248
|
+
},
|
|
249
|
+
}
|
|
250
|
+
)
|
|
251
|
+
|
|
252
|
+
span.add_event(
|
|
253
|
+
name="response",
|
|
254
|
+
attributes={"llm.responses": json.dumps(response)},
|
|
255
|
+
)
|
|
256
|
+
|
|
257
|
+
span.set_status(StatusCode.OK)
|
|
258
|
+
return result
|
|
259
|
+
except Exception as err:
|
|
260
|
+
# Record the exception in the span
|
|
261
|
+
span.record_exception(err)
|
|
262
|
+
|
|
263
|
+
# Set the span status to indicate an error
|
|
264
|
+
span.set_status(Status(StatusCode.ERROR, str(err)))
|
|
265
|
+
|
|
266
|
+
# Reraise the exception to ensure it's not swallowed
|
|
267
|
+
raise
|
|
268
|
+
|
|
269
|
+
return traced_method
|
|
270
|
+
|
|
271
|
+
|
|
190
272
|
def chat_completions_create(original_method, version, tracer):
|
|
191
273
|
"""Wrap the `create` method of the `ChatCompletion` class to trace it."""
|
|
192
274
|
|
langtrace_python_sdk/version.py
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
__version__ = "2.1.
|
|
1
|
+
__version__ = "2.1.13"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.3
|
|
2
2
|
Name: langtrace-python-sdk
|
|
3
|
-
Version: 2.1.
|
|
3
|
+
Version: 2.1.13
|
|
4
4
|
Summary: Python SDK for LangTrace
|
|
5
5
|
Project-URL: Homepage, https://github.com/Scale3-Labs/langtrace-python-sdk
|
|
6
6
|
Author-email: Scale3 Labs <engineering@scale3labs.com>
|
|
@@ -19,7 +19,7 @@ Requires-Dist: opentelemetry-instrumentation>=0.46b0
|
|
|
19
19
|
Requires-Dist: opentelemetry-sdk>=1.25.0
|
|
20
20
|
Requires-Dist: sqlalchemy
|
|
21
21
|
Requires-Dist: tiktoken>=0.1.1
|
|
22
|
-
Requires-Dist: trace-attributes
|
|
22
|
+
Requires-Dist: trace-attributes==4.0.5
|
|
23
23
|
Provides-Extra: dev
|
|
24
24
|
Requires-Dist: anthropic; extra == 'dev'
|
|
25
25
|
Requires-Dist: chromadb; extra == 'dev'
|
|
@@ -26,10 +26,13 @@ examples/openai_example/async_tool_calling_streaming.py,sha256=PQMHSWAN1DfgjK88b
|
|
|
26
26
|
examples/openai_example/chat_completion.py,sha256=f2rMHJU1Dph_fAOv9qCksvtldl1s9UitEeLsvyoSpGA,1253
|
|
27
27
|
examples/openai_example/embeddings_create.py,sha256=d05rArTWxsmCxOdTRaGw3n9Yt1HXxOHHCtciCHIwBGc,502
|
|
28
28
|
examples/openai_example/function_calling.py,sha256=rrnrFw2HyV_gv4TdwUr299baP4tIupz6EQWWmLDtJkU,2265
|
|
29
|
+
examples/openai_example/images_edit.py,sha256=8GJac6PRn0TLfUSV5dVAZ0twoti4Ogq0sEGxTdxlU44,884
|
|
29
30
|
examples/openai_example/images_generate.py,sha256=SZNY8Visk7JUpx5QhNxTNINHmPAGdCUayF-Q7_iCr50,470
|
|
30
31
|
examples/openai_example/tool_calling.py,sha256=_IV7KoSI_37u1TTZWdVa58BYjkDfhSurvM86xwaNNhY,2316
|
|
31
32
|
examples/openai_example/tool_calling_nonstreaming.py,sha256=Yc848IooZRXNynHL6z0kOgJ4qbmL_NOufcb2VmWRukI,3847
|
|
32
33
|
examples/openai_example/tool_calling_streaming.py,sha256=mV1RbyAoVhumGRPpqPWQ6PMhnJyeifrlELd2-K1qJ_w,7015
|
|
34
|
+
examples/openai_example/resources/lounge_flamingo.png,sha256=aspniTtmWqwLp3YUhYqAe2ze8nJaq-bTSW7uUJudtd0,2416234
|
|
35
|
+
examples/openai_example/resources/mask.png,sha256=mUE9Dfp-x8jI0Nh4WGr0P9pueUqEZfpjwxR-6Rxzxz4,2483660
|
|
33
36
|
examples/perplexity_example/basic.py,sha256=bp7n27gaugJkaFVyt8pjaEfi66lYcqP6eFFjPewUShY,668
|
|
34
37
|
examples/pinecone_example/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
35
38
|
examples/pinecone_example/basic.py,sha256=gkb1uQwKFLnWmRuM2KGvAeTpT1AYlHmz2kRey5_-Dqs,1437
|
|
@@ -38,7 +41,7 @@ examples/qdrant_example/basic.py,sha256=DCMjHSuBZKkhEjCkwy5d5La9WMyW0lCWqtcZWiFC
|
|
|
38
41
|
examples/weaviate_example/query_text.py,sha256=iE9OiHsibjsprbCGzabE03eZsGN06e6ym2iS1A9P3ig,64650
|
|
39
42
|
langtrace_python_sdk/__init__.py,sha256=FuvyRuStRe_N2wo2SB2_ZQ0w7LGNIjV0lLi6S1IgGwY,958
|
|
40
43
|
langtrace_python_sdk/langtrace.py,sha256=pN-xJRXrtvJIenMOH0-xlNXcnqL9qMjg28SrW-PMRU0,6978
|
|
41
|
-
langtrace_python_sdk/version.py,sha256=
|
|
44
|
+
langtrace_python_sdk/version.py,sha256=59WYUQbpJnalweC5r75GQeXXOChhHcCgbKm0CW6XD1M,23
|
|
42
45
|
langtrace_python_sdk/constants/__init__.py,sha256=P8QvYwt5czUNDZsKS64vxm9Dc41ptGbuF1TFtAF6nv4,44
|
|
43
46
|
langtrace_python_sdk/constants/exporter/langtrace_exporter.py,sha256=5MNjnAOg-4am78J3gVMH6FSwq5N8TOj72ugkhsw4vi0,46
|
|
44
47
|
langtrace_python_sdk/constants/instrumentation/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
@@ -47,7 +50,7 @@ langtrace_python_sdk/constants/instrumentation/chroma.py,sha256=hiPGYdHS0Yj4Kh3e
|
|
|
47
50
|
langtrace_python_sdk/constants/instrumentation/cohere.py,sha256=tf9sDfb5K3qOAHChEE5o8eYWPZ1io58VsOjZDCZPxfw,577
|
|
48
51
|
langtrace_python_sdk/constants/instrumentation/common.py,sha256=TCHX8uqIJD2p9sONGrlX6Q3b5Mj859PTP-c729ogKcY,782
|
|
49
52
|
langtrace_python_sdk/constants/instrumentation/groq.py,sha256=VFXmIl4aqGY_fS0PAmjPj_Qm7Tibxbx7Ur_e7rQpqXc,134
|
|
50
|
-
langtrace_python_sdk/constants/instrumentation/openai.py,sha256=
|
|
53
|
+
langtrace_python_sdk/constants/instrumentation/openai.py,sha256=uEOH5UXapU2DSf2AdgXTRhhJEHGWXUNFkUGD5QafflM,1164
|
|
51
54
|
langtrace_python_sdk/constants/instrumentation/pinecone.py,sha256=Xaqqw-xBO0JJLGk75hiCUQGztNm0HiVaLQvjtYK7VJM,472
|
|
52
55
|
langtrace_python_sdk/constants/instrumentation/qdrant.py,sha256=yL7BopNQTXW7L7Z-gVM2PdusKD7r9qqcATvczFd7NtQ,1999
|
|
53
56
|
langtrace_python_sdk/constants/instrumentation/weaviate.py,sha256=Iytf2OpB_irZYEmvOQ7Pf483EdG5Bh59GxaBlXck0yY,1501
|
|
@@ -82,8 +85,8 @@ langtrace_python_sdk/instrumentation/llamaindex/__init__.py,sha256=rHvuqpuQKLj57
|
|
|
82
85
|
langtrace_python_sdk/instrumentation/llamaindex/instrumentation.py,sha256=8iAg-Oxwf2W4S60qRfO5mvzORYxublgq7FdGWqUB4q8,2965
|
|
83
86
|
langtrace_python_sdk/instrumentation/llamaindex/patch.py,sha256=LwnI9DCC5wcnixPUOmwIWSE7ryTk1J0xFBYdJja8t_Q,4324
|
|
84
87
|
langtrace_python_sdk/instrumentation/openai/__init__.py,sha256=VPHRNCQEdkizIVP2d0Uw_a7t8XOTSTprEIB8oboJFbs,95
|
|
85
|
-
langtrace_python_sdk/instrumentation/openai/instrumentation.py,sha256=
|
|
86
|
-
langtrace_python_sdk/instrumentation/openai/patch.py,sha256=
|
|
88
|
+
langtrace_python_sdk/instrumentation/openai/instrumentation.py,sha256=A0BJHRLcZ74TNVg6I0I9M5YWvSpAtXwMmME6N5CEQ_M,2945
|
|
89
|
+
langtrace_python_sdk/instrumentation/openai/patch.py,sha256=ugf3y-20YVqJmHsheQaL3EEy7FPbOgEMtcG5dOYjxiE,40553
|
|
87
90
|
langtrace_python_sdk/instrumentation/pinecone/__init__.py,sha256=DzXyGh9_MGWveJvXULkFwdkf7PbG2s3bAWtT1Dmz7Ok,99
|
|
88
91
|
langtrace_python_sdk/instrumentation/pinecone/instrumentation.py,sha256=mxQXe3oAOPLsMJGlEzAe6zpgK7RtWfqmcNmGW_gQXX4,1900
|
|
89
92
|
langtrace_python_sdk/instrumentation/pinecone/patch.py,sha256=nZUHZ_1HfLjByJS0gkvrDRj69JbdnfWpezk6zl1EMvU,5000
|
|
@@ -138,7 +141,7 @@ tests/pinecone/cassettes/test_query.yaml,sha256=b5v9G3ssUy00oG63PlFUR3JErF2Js-5A
|
|
|
138
141
|
tests/pinecone/cassettes/test_upsert.yaml,sha256=neWmQ1v3d03V8WoLl8FoFeeCYImb8pxlJBWnFd_lITU,38607
|
|
139
142
|
tests/qdrant/conftest.py,sha256=9n0uHxxIjWk9fbYc4bx-uP8lSAgLBVx-cV9UjnsyCHM,381
|
|
140
143
|
tests/qdrant/test_qdrant.py,sha256=pzjAjVY2kmsmGfrI2Gs2xrolfuaNHz7l1fqGQCjp5_o,3353
|
|
141
|
-
langtrace_python_sdk-2.1.
|
|
142
|
-
langtrace_python_sdk-2.1.
|
|
143
|
-
langtrace_python_sdk-2.1.
|
|
144
|
-
langtrace_python_sdk-2.1.
|
|
144
|
+
langtrace_python_sdk-2.1.13.dist-info/METADATA,sha256=sYv1f4zRAoiFCz20_lA_anHmpeCEk2y4Tf5OoQck0Wc,11860
|
|
145
|
+
langtrace_python_sdk-2.1.13.dist-info/WHEEL,sha256=zEMcRr9Kr03x1ozGwg5v9NQBKn3kndp6LSoSlVg-jhU,87
|
|
146
|
+
langtrace_python_sdk-2.1.13.dist-info/licenses/LICENSE,sha256=QwcOLU5TJoTeUhuIXzhdCEEDDvorGiC6-3YTOl4TecE,11356
|
|
147
|
+
langtrace_python_sdk-2.1.13.dist-info/RECORD,,
|
|
File without changes
|
{langtrace_python_sdk-2.1.12.dist-info → langtrace_python_sdk-2.1.13.dist-info}/licenses/LICENSE
RENAMED
|
File without changes
|