arize-phoenix 6.1.0__py3-none-any.whl → 7.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.

Potentially problematic release.


This version of arize-phoenix might be problematic. Click here for more details.

Files changed (54) hide show
  1. {arize_phoenix-6.1.0.dist-info → arize_phoenix-7.0.0.dist-info}/METADATA +9 -8
  2. {arize_phoenix-6.1.0.dist-info → arize_phoenix-7.0.0.dist-info}/RECORD +52 -38
  3. phoenix/config.py +4 -1
  4. phoenix/db/engines.py +1 -1
  5. phoenix/db/insertion/span.py +65 -30
  6. phoenix/db/migrate.py +4 -1
  7. phoenix/db/migrations/data_migration_scripts/__init__.py +0 -0
  8. phoenix/db/migrations/data_migration_scripts/populate_project_sessions.py +199 -0
  9. phoenix/db/migrations/versions/4ded9e43755f_create_project_sessions_table.py +66 -0
  10. phoenix/db/models.py +27 -0
  11. phoenix/metrics/wrappers.py +7 -1
  12. phoenix/server/api/context.py +15 -2
  13. phoenix/server/api/dataloaders/__init__.py +14 -2
  14. phoenix/server/api/dataloaders/session_io.py +75 -0
  15. phoenix/server/api/dataloaders/session_num_traces.py +30 -0
  16. phoenix/server/api/dataloaders/session_num_traces_with_error.py +32 -0
  17. phoenix/server/api/dataloaders/session_token_usages.py +41 -0
  18. phoenix/server/api/dataloaders/session_trace_latency_ms_quantile.py +55 -0
  19. phoenix/server/api/dataloaders/trace_by_trace_ids.py +25 -0
  20. phoenix/server/api/dataloaders/trace_root_spans.py +32 -0
  21. phoenix/server/api/input_types/ProjectSessionSort.py +29 -0
  22. phoenix/server/api/mutations/chat_mutations.py +5 -0
  23. phoenix/server/api/mutations/project_mutations.py +12 -2
  24. phoenix/server/api/queries.py +14 -9
  25. phoenix/server/api/subscriptions.py +6 -0
  26. phoenix/server/api/types/EmbeddingDimension.py +1 -1
  27. phoenix/server/api/types/ExperimentRun.py +3 -4
  28. phoenix/server/api/types/ExperimentRunAnnotation.py +3 -4
  29. phoenix/server/api/types/Project.py +150 -12
  30. phoenix/server/api/types/ProjectSession.py +139 -0
  31. phoenix/server/api/types/Span.py +6 -19
  32. phoenix/server/api/types/SpanIOValue.py +15 -0
  33. phoenix/server/api/types/TokenUsage.py +11 -0
  34. phoenix/server/api/types/Trace.py +59 -2
  35. phoenix/server/app.py +15 -2
  36. phoenix/server/static/.vite/manifest.json +40 -31
  37. phoenix/server/static/assets/{components-CdiZ1Osh.js → components-DKH6AzJw.js} +410 -351
  38. phoenix/server/static/assets/index-DLV87qiO.js +93 -0
  39. phoenix/server/static/assets/{pages-FArMEfgg.js → pages-CVY3Nv4Z.js} +638 -316
  40. phoenix/server/static/assets/vendor-Cb3zlNNd.js +894 -0
  41. phoenix/server/static/assets/{vendor-arizeai-BG6iwyLC.js → vendor-arizeai-Buo4e1A6.js} +2 -2
  42. phoenix/server/static/assets/{vendor-codemirror-BotnVFFX.js → vendor-codemirror-BuAQiUVf.js} +5 -5
  43. phoenix/server/static/assets/{vendor-recharts-Dy5gEFzQ.js → vendor-recharts-Cl9dK5tC.js} +1 -1
  44. phoenix/server/static/assets/{vendor-Bnv1dNRQ.js → vendor-shiki-CazYUixL.js} +5 -898
  45. phoenix/session/client.py +13 -4
  46. phoenix/trace/fixtures.py +8 -0
  47. phoenix/trace/schemas.py +16 -0
  48. phoenix/version.py +1 -1
  49. phoenix/server/api/dataloaders/trace_row_ids.py +0 -33
  50. phoenix/server/static/assets/index-D_sCOjlG.js +0 -101
  51. {arize_phoenix-6.1.0.dist-info → arize_phoenix-7.0.0.dist-info}/WHEEL +0 -0
  52. {arize_phoenix-6.1.0.dist-info → arize_phoenix-7.0.0.dist-info}/entry_points.txt +0 -0
  53. {arize_phoenix-6.1.0.dist-info → arize_phoenix-7.0.0.dist-info}/licenses/IP_NOTICE +0 -0
  54. {arize_phoenix-6.1.0.dist-info → arize_phoenix-7.0.0.dist-info}/licenses/LICENSE +0 -0
phoenix/session/client.py CHANGED
@@ -129,6 +129,7 @@ class Client(TraceDataExtractor):
129
129
  root_spans_only (bool, optional): If True, only root spans are returned. Default None.
130
130
  project_name (str, optional): The project name to query spans for. This can be set
131
131
  using environment variables. If not provided, falls back to the default project.
132
+ timeout (int, optional): The number of seconds to wait for the server to respond.
132
133
 
133
134
  Returns:
134
135
  Union[pd.DataFrame, list[pd.DataFrame]]:
@@ -216,6 +217,8 @@ class Client(TraceDataExtractor):
216
217
  def get_evaluations(
217
218
  self,
218
219
  project_name: Optional[str] = None,
220
+ *, # Only support kwargs from now on
221
+ timeout: Optional[int] = DEFAULT_TIMEOUT_IN_SECONDS,
219
222
  ) -> list[Evaluations]:
220
223
  """
221
224
  Retrieves evaluations for a given project from the Phoenix server or active session.
@@ -224,6 +227,7 @@ class Client(TraceDataExtractor):
224
227
  project_name (str, optional): The name of the project to retrieve evaluations for.
225
228
  This can be set using environment variables. If not provided, falls back to the
226
229
  default project.
230
+ timeout (int, optional): The number of seconds to wait for the server to respond.
227
231
 
228
232
  Returns:
229
233
  list[Evaluations]:
@@ -237,6 +241,7 @@ class Client(TraceDataExtractor):
237
241
  "project_name": project_name,
238
242
  "project-name": project_name, # for backward-compatibility
239
243
  },
244
+ timeout=timeout,
240
245
  )
241
246
  if response.status_code == 404:
242
247
  logger.info("No evaluations found.")
@@ -263,15 +268,18 @@ class Client(TraceDataExtractor):
263
268
  f"with `import phoenix as px; px.launch_app()`"
264
269
  )
265
270
 
266
- def log_evaluations(self, *evals: Evaluations, **kwargs: Any) -> None:
271
+ def log_evaluations(
272
+ self,
273
+ *evals: Evaluations,
274
+ timeout: Optional[int] = DEFAULT_TIMEOUT_IN_SECONDS,
275
+ **kwargs: Any,
276
+ ) -> None:
267
277
  """
268
278
  Logs evaluation data to the Phoenix server.
269
279
 
270
280
  Args:
271
281
  evals (Evaluations): One or more Evaluations objects containing the data to log.
272
- project_name (str, optional): The project name under which to log the evaluations.
273
- This can be set using environment variables. If not provided, falls back to the
274
- default project.
282
+ timeout (int, optional): The number of seconds to wait for the server to respond.
275
283
 
276
284
  Returns:
277
285
  None
@@ -290,6 +298,7 @@ class Client(TraceDataExtractor):
290
298
  url=urljoin(self._base_url, "v1/evaluations"),
291
299
  content=cast(bytes, sink.getvalue().to_pybytes()),
292
300
  headers=headers,
301
+ timeout=timeout,
293
302
  ).raise_for_status()
294
303
 
295
304
  def log_traces(self, trace_dataset: TraceDataset, project_name: Optional[str] = None) -> None:
phoenix/trace/fixtures.py CHANGED
@@ -222,6 +222,13 @@ llama_index_rag_fixture = TracesFixture(
222
222
  ),
223
223
  )
224
224
 
225
+ project_sessions_llama_index_rag_arize_docs_fixture = TracesFixture(
226
+ name="project_sessions_llama_index_rag_arize_docs",
227
+ project_name="SESSIONS-DEMO",
228
+ file_name="project_sessions_demo_llama_index_query_engine_arize_docs.parquet",
229
+ description="RAG queries grouped by session.id and user.id.",
230
+ )
231
+
225
232
  llama_index_calculator_agent_fixture = TracesFixture(
226
233
  name="llama_index_calculator_agent",
227
234
  description="Traces from running the llama_index with calculator tools.",
@@ -290,6 +297,7 @@ TRACES_FIXTURES: list[TracesFixture] = [
290
297
  llama_index_calculator_agent_fixture,
291
298
  vision_fixture,
292
299
  anthropic_tools_fixture,
300
+ project_sessions_llama_index_rag_arize_docs_fixture,
293
301
  ]
294
302
 
295
303
  NAME_TO_TRACES_FIXTURE: dict[str, TracesFixture] = {
phoenix/trace/schemas.py CHANGED
@@ -187,6 +187,22 @@ class MimeType(Enum):
187
187
  return None if v else cls.TEXT
188
188
 
189
189
 
190
+ @dataclass(frozen=True)
191
+ class SpanIOValue:
192
+ value: str
193
+ mime_type: MimeType = MimeType.TEXT
194
+
195
+
196
+ @dataclass(frozen=True)
197
+ class TokenUsage:
198
+ prompt: int = 0
199
+ completion: int = 0
200
+
201
+ def __post_init__(self) -> None:
202
+ assert self.prompt >= 0, "prompt must be non-negative"
203
+ assert self.completion >= 0, "completion must be non-negative"
204
+
205
+
190
206
  ATTRIBUTE_PREFIX = "attributes."
191
207
  CONTEXT_PREFIX = "context."
192
208
  COMPUTED_PREFIX = "__computed__."
phoenix/version.py CHANGED
@@ -1 +1 @@
1
- __version__ = "6.1.0"
1
+ __version__ = "7.0.0"
@@ -1,33 +0,0 @@
1
- from typing import Optional
2
-
3
- from sqlalchemy import select
4
- from strawberry.dataloader import DataLoader
5
- from typing_extensions import TypeAlias
6
-
7
- from phoenix.db import models
8
- from phoenix.server.types import DbSessionFactory
9
-
10
- TraceId: TypeAlias = str
11
- Key: TypeAlias = TraceId
12
- TraceRowId: TypeAlias = int
13
- ProjectRowId: TypeAlias = int
14
- Result: TypeAlias = Optional[tuple[TraceRowId, ProjectRowId]]
15
-
16
-
17
- class TraceRowIdsDataLoader(DataLoader[Key, Result]):
18
- def __init__(self, db: DbSessionFactory) -> None:
19
- super().__init__(load_fn=self._load_fn)
20
- self._db = db
21
-
22
- async def _load_fn(self, keys: list[Key]) -> list[Result]:
23
- stmt = select(
24
- models.Trace.trace_id,
25
- models.Trace.id,
26
- models.Trace.project_rowid,
27
- ).where(models.Trace.trace_id.in_(keys))
28
- async with self._db() as session:
29
- result = {
30
- trace_id: (id_, project_rowid)
31
- async for trace_id, id_, project_rowid in await session.stream(stmt)
32
- }
33
- return list(map(result.get, keys))
@@ -1,101 +0,0 @@
1
- import{r as c,j as e,dv as v,l as n,U as F,R as w,D as E,bb as R,dw as S,dx as L,dy as r,dz as z,dA as k,t as A,dB as $}from"./vendor-Bnv1dNRQ.js";import{D as C,d as I,$ as _,G as j,t as O,a4 as D}from"./vendor-arizeai-BG6iwyLC.js";import{E as T,L as G,R as N,r as B,b as M,F as U,A as J,c as K,d as W,P as q,h as H,M as V,e as m,D as Y,f as Q,g as X,i as Z,j as ee,k as re,l as ae,p as te,n as g,o as oe,q as ne,s as u,t as se,v as h,w as x,x as le,y as ie,z as de,B as ce,C as pe,G as f,H as me,S as ge,I as ue,J as he,K as xe,N as fe,O as be}from"./pages-FArMEfgg.js";import{c6 as ye,$ as Pe,R as ve,c7 as Fe,c8 as we}from"./components-CdiZ1Osh.js";import"./vendor-three-DwGkEfCM.js";import"./vendor-recharts-Dy5gEFzQ.js";import"./vendor-codemirror-BotnVFFX.js";(function(){const s=document.createElement("link").relList;if(s&&s.supports&&s.supports("modulepreload"))return;for(const t of document.querySelectorAll('link[rel="modulepreload"]'))d(t);new MutationObserver(t=>{for(const o of t)if(o.type==="childList")for(const l of o.addedNodes)l.tagName==="LINK"&&l.rel==="modulepreload"&&d(l)}).observe(document,{childList:!0,subtree:!0});function i(t){const o={};return t.integrity&&(o.integrity=t.integrity),t.referrerPolicy&&(o.referrerPolicy=t.referrerPolicy),t.crossOrigin==="use-credentials"?o.credentials="include":t.crossOrigin==="anonymous"?o.credentials="omit":o.credentials="same-origin",o}function d(t){if(t.ep)return;t.ep=!0;const o=i(t);fetch(t.href,o)}})();const b="arize-phoenix-feature-flags",p={__RESET__:!1};function Ee(){const a=localStorage.getItem(b);if(!a)return p;try{const s=JSON.parse(a);return Object.assign({},p,s)}catch{return p}}const y=c.createContext(null);function Re(){const a=w.useContext(y);if(a===null)throw new Error("useFeatureFlags must be used within a FeatureFlagsProvider");return a}function Se(a){const[s,i]=c.useState(Ee()),d=t=>{localStorage.setItem(b,JSON.stringify(t)),i(t)};return e(y.Provider,{value:{featureFlags:s,setFeatureFlags:d},children:e(Le,{children:a.children})})}function Le(a){const{children:s}=a,{featureFlags:i,setFeatureFlags:d}=Re(),[t,o]=c.useState(!1);return v("ctrl+shift+f",()=>o(!0)),n(F,{children:[s,e(j,{type:"modal",isDismissable:!0,onDismiss:()=>o(!1),children:t&&e(C,{title:"Feature Flags",children:e(I,{height:"size-1000",padding:"size-100",children:Object.keys(i).map(l=>e(_,{isSelected:i[l],onChange:P=>d({...i,[l]:P}),children:l},l))})})})]})}function ze(){return e(R,{styles:a=>E`
2
- body {
3
- background-color: var(--ac-global-color-grey-75);
4
- color: var(--ac-global-text-color-900);
5
- font-family: "Roboto";
6
- font-size: ${a.typography.sizes.medium.fontSize}px;
7
- margin: 0;
8
- overflow: hidden;
9
- #root,
10
- #root > div[data-overlay-container="true"],
11
- #root > div[data-overlay-container="true"] > .ac-theme {
12
- height: 100vh;
13
- }
14
- }
15
-
16
- /* Remove list styling */
17
- ul {
18
- display: block;
19
- list-style-type: none;
20
- margin-block-start: none;
21
- margin-block-end: 0;
22
- padding-inline-start: 0;
23
- margin-block-start: 0;
24
- }
25
-
26
- /* A reset style for buttons */
27
- .button--reset {
28
- background: none;
29
- border: none;
30
- padding: 0;
31
- }
32
- /* this css class is added to html via modernizr @see modernizr.js */
33
- .no-hiddenscroll {
34
- /* Works on Firefox */
35
- * {
36
- scrollbar-width: thin;
37
- scrollbar-color: var(--ac-global-color-grey-300)
38
- var(--ac-global-color-grey-400);
39
- }
40
-
41
- /* Works on Chrome, Edge, and Safari */
42
- *::-webkit-scrollbar {
43
- width: 14px;
44
- }
45
-
46
- *::-webkit-scrollbar-track {
47
- background: var(--ac-global-color-grey-100);
48
- }
49
-
50
- *::-webkit-scrollbar-thumb {
51
- background-color: var(--ac-global-color-grey-75);
52
- border-radius: 8px;
53
- border: 1px solid var(--ac-global-color-grey-300);
54
- }
55
- }
56
-
57
- :root {
58
- --px-blue-color: ${a.colors.arizeBlue};
59
-
60
- --px-flex-gap-sm: ${a.spacing.margin4}px;
61
- --px-flex-gap-sm: ${a.spacing.margin8}px;
62
-
63
- --px-section-background-color: ${a.colors.gray500};
64
-
65
- /* An item is a typically something in a list */
66
- --px-item-background-color: ${a.colors.gray800};
67
- --px-item-border-color: ${a.colors.gray600};
68
-
69
- --px-spacing-sm: ${a.spacing.padding4}px;
70
- --px-spacing-med: ${a.spacing.padding8}px;
71
- --px-spacing-lg: ${a.spacing.padding16}px;
72
-
73
- --px-border-radius-med: ${a.borderRadius.medium}px;
74
-
75
- --px-font-size-sm: ${a.typography.sizes.small.fontSize}px;
76
- --px-font-size-med: ${a.typography.sizes.medium.fontSize}px;
77
- --px-font-size-lg: ${a.typography.sizes.large.fontSize}px;
78
-
79
- --px-gradient-bar-height: 8px;
80
-
81
- --px-nav-collapsed-width: 45px;
82
- --px-nav-expanded-width: 200px;
83
- }
84
-
85
- .ac-theme--dark {
86
- --px-primary-color: #9efcfd;
87
- --px-primary-color--transparent: rgb(158, 252, 253, 0.2);
88
- --px-reference-color: #baa1f9;
89
- --px-reference-color--transparent: #baa1f982;
90
- --px-corpus-color: #92969c;
91
- --px-corpus-color--transparent: #92969c63;
92
- }
93
- .ac-theme--light {
94
- --px-primary-color: #00add0;
95
- --px-primary-color--transparent: rgba(0, 173, 208, 0.2);
96
- --px-reference-color: #4500d9;
97
- --px-reference-color--transparent: rgba(69, 0, 217, 0.2);
98
- --px-corpus-color: #92969c;
99
- --px-corpus-color--transparent: #92969c63;
100
- }
101
- `})}const ke=S(L(n(r,{path:"/",errorElement:e(T,{}),children:[e(r,{path:"/login",element:e(G,{})}),e(r,{path:"/reset-password",element:e(N,{}),loader:B}),e(r,{path:"/reset-password-with-token",element:e(M,{})}),e(r,{path:"/forgot-password",element:e(U,{})}),e(r,{element:e(J,{}),loader:K,children:n(r,{element:e(W,{}),children:[e(r,{path:"/profile",handle:{crumb:()=>"profile"},element:e(q,{})}),e(r,{index:!0,loader:H}),n(r,{path:"/model",handle:{crumb:()=>"model"},element:e(V,{}),children:[e(r,{index:!0,element:e(m,{})}),e(r,{element:e(m,{}),children:e(r,{path:"dimensions",children:e(r,{path:":dimensionId",element:e(Y,{}),loader:Q})})}),e(r,{path:"embeddings",children:e(r,{path:":embeddingDimensionId",element:e(X,{}),loader:Z,handle:{crumb:a=>a.embedding.name}})})]}),n(r,{path:"/projects",handle:{crumb:()=>"projects"},element:e(ee,{}),children:[e(r,{index:!0,element:e(re,{})}),n(r,{path:":projectId",element:e(ae,{}),loader:te,handle:{crumb:a=>a.project.name},children:[e(r,{index:!0,element:e(g,{})}),e(r,{element:e(g,{}),children:e(r,{path:"traces/:traceId",element:e(oe,{})})})]})]}),n(r,{path:"/datasets",handle:{crumb:()=>"datasets"},children:[e(r,{index:!0,element:e(ne,{})}),n(r,{path:":datasetId",loader:u,handle:{crumb:a=>a.dataset.name},children:[n(r,{element:e(se,{}),loader:u,children:[e(r,{index:!0,element:e(h,{}),loader:x}),e(r,{path:"experiments",element:e(h,{}),loader:x}),e(r,{path:"examples",element:e(le,{}),loader:ie,children:e(r,{path:":exampleId",element:e(de,{})})})]}),e(r,{path:"compare",handle:{crumb:()=>"compare"},loader:ce,element:e(pe,{})})]})]}),n(r,{path:"/playground",handle:{crumb:()=>"Playground"},children:[e(r,{index:!0,element:e(f,{})}),e(r,{path:"datasets/:datasetId",element:e(f,{}),children:e(r,{path:"examples/:exampleId",element:e(me,{})})}),e(r,{path:"spans/:spanId",element:e(ge,{}),loader:ue,handle:{crumb:a=>a.span.__typename==="Span"?`span ${a.span.context.spanId}`:"span unknown"}})]}),e(r,{path:"/apis",element:e(he,{}),handle:{crumb:()=>"APIs"}}),e(r,{path:"/settings",element:e(xe,{}),handle:{crumb:()=>"Settings"}})]})})]})),{basename:window.Config.basename});function Ae(){return e(z,{router:ke})}function $e(){return e(fe,{children:e(ye,{children:e(Ce,{})})})}function Ce(){const{theme:a}=Pe();return e(D,{theme:a,children:e(k,{theme:O,children:n(A.RelayEnvironmentProvider,{environment:ve,children:[e(ze,{}),e(Se,{children:e(Fe,{children:e(be,{children:e(c.Suspense,{children:e(we,{children:e(Ae,{})})})})})})]})})})}const Ie=document.getElementById("root"),_e=$.createRoot(Ie);_e.render(e($e,{}));