From ba1079ff6698ef238c5c7f771dd2b698ec76f8d9 Mon Sep 17 00:00:00 2001 From: Krrish Dholakia Date: Thu, 3 Aug 2023 06:26:55 -0700 Subject: [PATCH] fix helicone-claude integration --- litellm/__pycache__/utils.cpython-311.pyc | Bin 18290 -> 18290 bytes .../__pycache__/helicone.cpython-311.pyc | Bin 3384 -> 3924 bytes litellm/integrations/helicone.py | 21 ++++++++++++++++++ litellm/tests/test_client.py | 12 ++++++++-- 4 files changed, 31 insertions(+), 2 deletions(-) diff --git a/litellm/__pycache__/utils.cpython-311.pyc b/litellm/__pycache__/utils.cpython-311.pyc index 76bf2d548a06d35fbbfd4bf9564ed1b819af0526..11fdde95d073fa8f7588ac22edf7426a2d36da67 100644 GIT binary patch delta 21 bcmey=$M~s_k!v|GFBbz4_$}VZmEjHmP6Gxr delta 21 bcmey=$M~s_k!v|GFBbz4oG{zSmEjHmPQC^} diff --git a/litellm/integrations/__pycache__/helicone.cpython-311.pyc b/litellm/integrations/__pycache__/helicone.cpython-311.pyc index 731a7e377f6c8f4435cc6788ec5940a8f60a11ad..27ab71696157f2ffa3f6202c2857f62cd2bec044 100644 GIT binary patch delta 1957 zcma)7U2GFa5Z?Ro`ObD?J9cnLfEZGKTr%w5PniBk%BDaJrW1o=k8sg zpmQCmR1H-n5*<~j2vRDwKucAnY9Htu4{e2137wJES|?S?OCS2?s(pz1)LGjxK~SlC zyR&mM-^|YJ?%X|WFKueR*VN=d(0=;zXZ)#auDOlL&TZeg4kOH_xePzXXKZ6O2C+y+ zlfvAQjWPR}okfEPbJq~&@3IIzfKh8>B4$QW$o2<)9r=Q_Ttlai9UO_DICcEki8n0i z;BcLtn_b83n7h~IxQ50AEP##un@^1XRwH+1uk#b1>Jsug*|kP zSUgeEvc*rSGO_GQC9BCb$!VaOP*O=*B{V3@o{?2GF)mw8s;1=P zYC(Q`O3o(b5NA1(fKSU>O39Koigi{YL{6w6q3043i3g^dR;+tcEfaFBt1G~+&@fa*unE>1@lprPbzCNq%cZj8S2qsH z=@cX?A63T3Wzzk;nuew>1DQs@`Gcl+%ZyMCbXJgEI>6NE%wXBwdMjYMgV4*q_FH>y z7WOY*cG1|q><;dQL zp;9DPcyzK98GJ02BB#vJv!%#6b0SkgsKAV{Fm)cUQ&a3%c5gFx^qTHoQ|u)^NHZw_ zS#6ZBmd+#`^9Rg4l8^>PwAyBv3k+tii8`8WNMqGos@jiD0Xe-~<<9^W!ym}Tm-L5-yC-yF|x=U}OGj4(5gX(BD=K1ab zMx&?;G3X4U+&kPEbeRdYju@ZWPP?mDSEaE8gVV%oID~%Y6=O(<_Rt-@+BBZiBCmD# zM6@Y#UJ0>PIOzlxp^=8THG&`rj61@2%ueH!UET%YFvabpILYD?*(;WBqJCfF)sl>- zQ>sR~D9UYY7X7cffVISWRj3x9Q&cVFc~)b!m4kpX=ERV554GGyN!a*NEHGYUKni;| zgFyWqPIYA(RroH+YkVU0N0!}zTRruQ9_{%x8haXzJ?=5zN}A+dGa4&K3#DkG=;<~+ z!Nu^mzeq=z{q0^e~&`hZwcBCAahC6`JP`b#17Ut&4aN&?4gSWD7KA}OCw zBrn#YSdFZs7TP~zADq%uTHZ&FgDou+^@j1iD>4}|(Mx(6wM+{o)KWzL67rkKUq&8t VwO81E3}o>l`IE~2eu<)*-oJG(;kf_+ delta 1416 zcmZuxO>7%Q6rS0&*Sq%mCypGKl%(r8rP(MpkSG$E2317{!XXDNsG3R`$FmJ~9k1D4 zlMp#_C6FjwNVEYC1gR2IK+1)`0}_{V;M5-0)gI7FIUx=l5Jm;b>IL4cvmrl>X1|$z z?|bikZ)R#ECNW3QrBEGHM% zhgMXg)TByXs;SG8-Yl0DUC&A8H2=zg<9D4pJ$gyHsYT3>`8hmj+WeE_F|e(Nmm5ZA zCOexkn%a^oGujYX9exE;l$I6U%n9G&Ve=0`X={&x2MA|j(S~U(U+C9LtxvqHyxCNA zLs~8AQe8DX71x`!tW+>cMpKub1C=>B?D!j6rEWNEss6Sz_=Zxel-0UYbY&K672VKi z;|@zXf>8k>Mroy?3D>BV*ZOsI$JbDG!|@r)n&E_i0u_p7r~olqsjMuO$~PRrtyEOj z%5qE#Q`xjR?F`K%YKq=a>$*}@m#XHEK{<4u`bH_7HUAE_al~wfrY53b&~tECy_=}( z8xzL%#Q`fm{pBnG%#Ju?i!+uuV}28w`}R@sCEO0jH^(>EwzC~EWs50GOzkJnZExHz ze0AZD&r0Sy$-JG+-+B@9Y)))vI-+EYk|jz%N0W9meOtdDowTBp`?17kwG&I(v6SV_ zUt2c`eo&0D%hki;YDCQE+ z$Jqs$Gd~ZX&&afG+NySu!XO3ud1w&|J`V!0(dW#EVYxl-AM2vi(2t@4GUsqaHI({W z8vXfbQvgn=rj|(Y!2AR?ySb0od&pmeuc28}p4Bb`h5iTWs{maVW8CEsj$6pQ7a28~ V=*a981|6s2Pip(?e;lsBe*s}2Mh5@@ diff --git a/litellm/integrations/helicone.py b/litellm/integrations/helicone.py index 559481daa73..ec4e9b634d0 100644 --- a/litellm/integrations/helicone.py +++ b/litellm/integrations/helicone.py @@ -2,6 +2,7 @@ # On success, logs events to Helicone import dotenv, os import requests +from anthropic import HUMAN_PROMPT, AI_PROMPT dotenv.load_dotenv() # Loading env variables using dotenv import traceback class HeliconeLogger: @@ -11,6 +12,23 @@ class HeliconeLogger: # Instance variables self.provider_url = "https://api.openai.com/v1" self.key = os.getenv('HELICONE_API_KEY') + + def claude_mapping(self, model, messages, response_obj): + prompt = f"{HUMAN_PROMPT}" + for message in messages: + if "role" in message: + if message["role"] == "user": + prompt += f"{HUMAN_PROMPT}{message['content']}" + else: + prompt += f"{AI_PROMPT}{message['content']}" + else: + prompt += f"{HUMAN_PROMPT}{message['content']}" + prompt += f"{AI_PROMPT}" + claude_provider_request = {"model": model, "prompt": prompt} + + claude_response_obj = {"completion": response_obj['choices'][0]['message']['content'], "model": model, "stop_reason": "stop_sequence"} + + return claude_provider_request, claude_response_obj def log_success(self, model, messages, response_obj, start_time, end_time): # Method definition @@ -18,6 +36,9 @@ class HeliconeLogger: model = model if any(accepted_model in model for accepted_model in self.helicone_model_list) else "gpt-3.5-turbo" provider_request = {"model": model, "messages": messages} + if "claude" in model: + provider_request, response_obj = self.claude_mapping(model=model, messages=messages, response_obj=response_obj) + providerResponse = { "json": response_obj, "headers": {"openai-version": "2020-10-01"}, diff --git a/litellm/tests/test_client.py b/litellm/tests/test_client.py index 1b95914cb70..d791f10ebd1 100644 --- a/litellm/tests/test_client.py +++ b/litellm/tests/test_client.py @@ -30,14 +30,22 @@ def test_completion_openai(): except Exception as e: traceback.print_exc() pytest.fail(f"Error occurred: {e}") -test_completion_openai() -def test_completion_non_openai(): + + +def test_completion_claude(): try: response = completion(model="claude-instant-1", messages=messages, logger_fn=logger_fn) # Add any assertions here to check the response except Exception as e: pytest.fail(f"Error occurred: {e}") +def test_completion_non_openai(): + try: + response = completion(model="command-nightly", messages=messages, logger_fn=logger_fn) + # Add any assertions here to check the response + except Exception as e: + pytest.fail(f"Error occurred: {e}") + def test_embedding_openai(): try: response = embedding(model='text-embedding-ada-002', input=[user_message], logger_fn=logger_fn)