together 1.5.21__tar.gz → 1.5.23__tar.gz

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.
Files changed (73) hide show
  1. {together-1.5.21 → together-1.5.23}/PKG-INFO +28 -1
  2. {together-1.5.21 → together-1.5.23}/README.md +27 -0
  3. {together-1.5.21 → together-1.5.23}/pyproject.toml +1 -1
  4. together-1.5.23/src/together/cli/api/evaluation.py +379 -0
  5. {together-1.5.21 → together-1.5.23}/src/together/cli/api/finetune.py +0 -14
  6. {together-1.5.21 → together-1.5.23}/src/together/cli/cli.py +2 -0
  7. {together-1.5.21 → together-1.5.23}/src/together/client.py +4 -0
  8. {together-1.5.21 → together-1.5.23}/src/together/filemanager.py +2 -4
  9. {together-1.5.21 → together-1.5.23}/src/together/legacy/finetune.py +2 -2
  10. {together-1.5.21 → together-1.5.23}/src/together/resources/__init__.py +3 -0
  11. {together-1.5.21 → together-1.5.23}/src/together/resources/batch.py +0 -1
  12. together-1.5.23/src/together/resources/evaluation.py +724 -0
  13. {together-1.5.21 → together-1.5.23}/src/together/resources/finetune.py +13 -26
  14. {together-1.5.21 → together-1.5.23}/src/together/types/__init__.py +24 -0
  15. together-1.5.23/src/together/types/evaluation.py +87 -0
  16. {together-1.5.21 → together-1.5.23}/src/together/types/files.py +2 -0
  17. {together-1.5.21 → together-1.5.23}/src/together/types/finetune.py +1 -1
  18. {together-1.5.21 → together-1.5.23}/src/together/utils/files.py +178 -73
  19. {together-1.5.21 → together-1.5.23}/LICENSE +0 -0
  20. {together-1.5.21 → together-1.5.23}/src/together/__init__.py +0 -0
  21. {together-1.5.21 → together-1.5.23}/src/together/abstract/__init__.py +0 -0
  22. {together-1.5.21 → together-1.5.23}/src/together/abstract/api_requestor.py +0 -0
  23. {together-1.5.21 → together-1.5.23}/src/together/cli/__init__.py +0 -0
  24. {together-1.5.21 → together-1.5.23}/src/together/cli/api/__init__.py +0 -0
  25. {together-1.5.21 → together-1.5.23}/src/together/cli/api/chat.py +0 -0
  26. {together-1.5.21 → together-1.5.23}/src/together/cli/api/completions.py +0 -0
  27. {together-1.5.21 → together-1.5.23}/src/together/cli/api/endpoints.py +0 -0
  28. {together-1.5.21 → together-1.5.23}/src/together/cli/api/files.py +0 -0
  29. {together-1.5.21 → together-1.5.23}/src/together/cli/api/images.py +0 -0
  30. {together-1.5.21 → together-1.5.23}/src/together/cli/api/models.py +0 -0
  31. {together-1.5.21 → together-1.5.23}/src/together/cli/api/utils.py +0 -0
  32. {together-1.5.21 → together-1.5.23}/src/together/constants.py +0 -0
  33. {together-1.5.21 → together-1.5.23}/src/together/error.py +0 -0
  34. {together-1.5.21 → together-1.5.23}/src/together/legacy/__init__.py +0 -0
  35. {together-1.5.21 → together-1.5.23}/src/together/legacy/base.py +0 -0
  36. {together-1.5.21 → together-1.5.23}/src/together/legacy/complete.py +0 -0
  37. {together-1.5.21 → together-1.5.23}/src/together/legacy/embeddings.py +0 -0
  38. {together-1.5.21 → together-1.5.23}/src/together/legacy/files.py +0 -0
  39. {together-1.5.21 → together-1.5.23}/src/together/legacy/images.py +0 -0
  40. {together-1.5.21 → together-1.5.23}/src/together/legacy/models.py +0 -0
  41. {together-1.5.21 → together-1.5.23}/src/together/resources/audio/__init__.py +0 -0
  42. {together-1.5.21 → together-1.5.23}/src/together/resources/audio/speech.py +0 -0
  43. {together-1.5.21 → together-1.5.23}/src/together/resources/audio/transcriptions.py +0 -0
  44. {together-1.5.21 → together-1.5.23}/src/together/resources/audio/translations.py +0 -0
  45. {together-1.5.21 → together-1.5.23}/src/together/resources/chat/__init__.py +0 -0
  46. {together-1.5.21 → together-1.5.23}/src/together/resources/chat/completions.py +0 -0
  47. {together-1.5.21 → together-1.5.23}/src/together/resources/code_interpreter.py +0 -0
  48. {together-1.5.21 → together-1.5.23}/src/together/resources/completions.py +0 -0
  49. {together-1.5.21 → together-1.5.23}/src/together/resources/embeddings.py +0 -0
  50. {together-1.5.21 → together-1.5.23}/src/together/resources/endpoints.py +0 -0
  51. {together-1.5.21 → together-1.5.23}/src/together/resources/files.py +0 -0
  52. {together-1.5.21 → together-1.5.23}/src/together/resources/images.py +0 -0
  53. {together-1.5.21 → together-1.5.23}/src/together/resources/models.py +0 -0
  54. {together-1.5.21 → together-1.5.23}/src/together/resources/rerank.py +0 -0
  55. {together-1.5.21 → together-1.5.23}/src/together/together_response.py +0 -0
  56. {together-1.5.21 → together-1.5.23}/src/together/types/abstract.py +0 -0
  57. {together-1.5.21 → together-1.5.23}/src/together/types/audio_speech.py +0 -0
  58. {together-1.5.21 → together-1.5.23}/src/together/types/batch.py +0 -0
  59. {together-1.5.21 → together-1.5.23}/src/together/types/chat_completions.py +0 -0
  60. {together-1.5.21 → together-1.5.23}/src/together/types/code_interpreter.py +0 -0
  61. {together-1.5.21 → together-1.5.23}/src/together/types/common.py +0 -0
  62. {together-1.5.21 → together-1.5.23}/src/together/types/completions.py +0 -0
  63. {together-1.5.21 → together-1.5.23}/src/together/types/embeddings.py +0 -0
  64. {together-1.5.21 → together-1.5.23}/src/together/types/endpoints.py +0 -0
  65. {together-1.5.21 → together-1.5.23}/src/together/types/error.py +0 -0
  66. {together-1.5.21 → together-1.5.23}/src/together/types/images.py +0 -0
  67. {together-1.5.21 → together-1.5.23}/src/together/types/models.py +0 -0
  68. {together-1.5.21 → together-1.5.23}/src/together/types/rerank.py +0 -0
  69. {together-1.5.21 → together-1.5.23}/src/together/utils/__init__.py +0 -0
  70. {together-1.5.21 → together-1.5.23}/src/together/utils/_log.py +0 -0
  71. {together-1.5.21 → together-1.5.23}/src/together/utils/api_helpers.py +0 -0
  72. {together-1.5.21 → together-1.5.23}/src/together/utils/tools.py +0 -0
  73. {together-1.5.21 → together-1.5.23}/src/together/version.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: together
3
- Version: 1.5.21
3
+ Version: 1.5.23
4
4
  Summary: Python client for Together's Cloud Platform!
5
5
  License: Apache-2.0
6
6
  Author: Together AI
@@ -421,6 +421,33 @@ for model in models:
421
421
  print(model)
422
422
  ```
423
423
 
424
+ ### Batch Inference
425
+
426
+ The batch API allows you to submit larger inference jobs for completion with a 24 hour turn-around time, below is an example. To learn more refer to the [docs here](https://docs.together.ai/docs/batch-inference).
427
+
428
+ ```python
429
+ from together import Together
430
+
431
+ client = Together()
432
+
433
+ # Upload the batch file
434
+ batch_file = client.files.upload(file="simpleqa_batch_student.jsonl", purpose="batch-api")
435
+
436
+ # Create the batch job
437
+ batch = client.batches.create_batch(file_id=batch_file.id, endpoint="/v1/chat/completions")
438
+
439
+ # Monitor the batch status
440
+ batch_stat = client.batches.get_batch(batch.id)
441
+
442
+ # List all batches - contains other batches as well
443
+ client.batches.list_batches()
444
+
445
+ # Download the file content if job completed
446
+ if batch_stat.status == 'COMPLETED':
447
+ output_response = client.files.retrieve_content(id=batch_stat.output_file_id,
448
+ output="simpleqa_v3_output.jsonl")
449
+ ```
450
+
424
451
  ## Usage – CLI
425
452
 
426
453
  ### Chat Completions
@@ -386,6 +386,33 @@ for model in models:
386
386
  print(model)
387
387
  ```
388
388
 
389
+ ### Batch Inference
390
+
391
+ The batch API allows you to submit larger inference jobs for completion with a 24 hour turn-around time, below is an example. To learn more refer to the [docs here](https://docs.together.ai/docs/batch-inference).
392
+
393
+ ```python
394
+ from together import Together
395
+
396
+ client = Together()
397
+
398
+ # Upload the batch file
399
+ batch_file = client.files.upload(file="simpleqa_batch_student.jsonl", purpose="batch-api")
400
+
401
+ # Create the batch job
402
+ batch = client.batches.create_batch(file_id=batch_file.id, endpoint="/v1/chat/completions")
403
+
404
+ # Monitor the batch status
405
+ batch_stat = client.batches.get_batch(batch.id)
406
+
407
+ # List all batches - contains other batches as well
408
+ client.batches.list_batches()
409
+
410
+ # Download the file content if job completed
411
+ if batch_stat.status == 'COMPLETED':
412
+ output_response = client.files.retrieve_content(id=batch_stat.output_file_id,
413
+ output="simpleqa_v3_output.jsonl")
414
+ ```
415
+
389
416
  ## Usage – CLI
390
417
 
391
418
  ### Chat Completions
@@ -12,7 +12,7 @@ build-backend = "poetry.masonry.api"
12
12
 
13
13
  [tool.poetry]
14
14
  name = "together"
15
- version = "1.5.21"
15
+ version = "1.5.23"
16
16
  authors = ["Together AI <support@together.ai>"]
17
17
  description = "Python client for Together's Cloud Platform!"
18
18
  readme = "README.md"
@@ -0,0 +1,379 @@
1
+ import json
2
+ from typing import Optional, Dict, Union, Any
3
+
4
+ import click
5
+ from tabulate import tabulate
6
+
7
+ from together import Together
8
+ from together.utils import convert_unix_timestamp
9
+
10
+
11
+ @click.group()
12
+ @click.pass_context
13
+ def evaluation(ctx: click.Context) -> None:
14
+ """Evaluation API commands"""
15
+ pass
16
+
17
+
18
+ @evaluation.command()
19
+ @click.pass_context
20
+ @click.option(
21
+ "--type",
22
+ type=click.Choice(["classify", "score", "compare"]),
23
+ required=True,
24
+ help="Type of evaluation to create.",
25
+ )
26
+ @click.option(
27
+ "--judge-model-name",
28
+ type=str,
29
+ required=True,
30
+ help="Name of the judge model to use for evaluation.",
31
+ )
32
+ @click.option(
33
+ "--judge-system-template",
34
+ type=str,
35
+ required=True,
36
+ help="System template for the judge model.",
37
+ )
38
+ @click.option(
39
+ "--input-data-file-path",
40
+ type=str,
41
+ required=True,
42
+ help="Path to the input data file.",
43
+ )
44
+ @click.option(
45
+ "--model-field",
46
+ type=str,
47
+ help="Name of the field in the input file contaning text generated by the model."
48
+ "Can not be used when model-a-name and other model config parameters are specified",
49
+ )
50
+ @click.option(
51
+ "--model-to-evaluate-name",
52
+ type=str,
53
+ help="Model name when using the detailed config",
54
+ )
55
+ @click.option(
56
+ "--model-to-evaluate-max-tokens",
57
+ type=int,
58
+ help="Max tokens for model-to-evaluate",
59
+ )
60
+ @click.option(
61
+ "--model-to-evaluate-temperature",
62
+ type=float,
63
+ help="Temperature for model-to-evaluate",
64
+ )
65
+ @click.option(
66
+ "--model-to-evaluate-system-template",
67
+ type=str,
68
+ help="System template for model-to-evaluate",
69
+ )
70
+ @click.option(
71
+ "--model-to-evaluate-input-template",
72
+ type=str,
73
+ help="Input template for model-to-evaluate",
74
+ )
75
+ @click.option(
76
+ "--labels",
77
+ type=str,
78
+ help="Classification labels - comma-separated list",
79
+ )
80
+ @click.option(
81
+ "--pass-labels",
82
+ type=str,
83
+ help="Labels considered as passing (required for classify type). A comma-separated list.",
84
+ )
85
+ @click.option(
86
+ "--min-score",
87
+ type=float,
88
+ help="Minimum score value (required for score type).",
89
+ )
90
+ @click.option(
91
+ "--max-score",
92
+ type=float,
93
+ help="Maximum score value (required for score type).",
94
+ )
95
+ @click.option(
96
+ "--pass-threshold",
97
+ type=float,
98
+ help="Threshold score for passing (required for score type).",
99
+ )
100
+ @click.option(
101
+ "--model-a-field",
102
+ type=str,
103
+ help="Name of the field in the input file containing text generated by Model A. \
104
+ Can not be used when model-a-name and other model config parameters are specified",
105
+ )
106
+ @click.option(
107
+ "--model-a-name",
108
+ type=str,
109
+ help="Model name for model A when using detailed config.",
110
+ )
111
+ @click.option(
112
+ "--model-a-max-tokens",
113
+ type=int,
114
+ help="Max tokens for model A.",
115
+ )
116
+ @click.option(
117
+ "--model-a-temperature",
118
+ type=float,
119
+ help="Temperature for model A.",
120
+ )
121
+ @click.option(
122
+ "--model-a-system-template",
123
+ type=str,
124
+ help="System template for model A.",
125
+ )
126
+ @click.option(
127
+ "--model-a-input-template",
128
+ type=str,
129
+ help="Input template for model A.",
130
+ )
131
+ @click.option(
132
+ "--model-b-field",
133
+ type=str,
134
+ help="Name of the field in the input file containing text generated by Model B.\
135
+ Can not be used when model-b-name and other model config parameters are specified",
136
+ )
137
+ @click.option(
138
+ "--model-b-name",
139
+ type=str,
140
+ help="Model name for model B when using detailed config.",
141
+ )
142
+ @click.option(
143
+ "--model-b-max-tokens",
144
+ type=int,
145
+ help="Max tokens for model B.",
146
+ )
147
+ @click.option(
148
+ "--model-b-temperature",
149
+ type=float,
150
+ help="Temperature for model B.",
151
+ )
152
+ @click.option(
153
+ "--model-b-system-template",
154
+ type=str,
155
+ help="System template for model B.",
156
+ )
157
+ @click.option(
158
+ "--model-b-input-template",
159
+ type=str,
160
+ help="Input template for model B.",
161
+ )
162
+ def create(
163
+ ctx: click.Context,
164
+ type: str,
165
+ judge_model_name: str,
166
+ judge_system_template: str,
167
+ input_data_file_path: str,
168
+ model_field: Optional[str],
169
+ model_to_evaluate_name: Optional[str],
170
+ model_to_evaluate_max_tokens: Optional[int],
171
+ model_to_evaluate_temperature: Optional[float],
172
+ model_to_evaluate_system_template: Optional[str],
173
+ model_to_evaluate_input_template: Optional[str],
174
+ labels: str,
175
+ pass_labels: str,
176
+ min_score: Optional[float],
177
+ max_score: Optional[float],
178
+ pass_threshold: Optional[float],
179
+ model_a_field: Optional[str],
180
+ model_a_name: Optional[str],
181
+ model_a_max_tokens: Optional[int],
182
+ model_a_temperature: Optional[float],
183
+ model_a_system_template: Optional[str],
184
+ model_a_input_template: Optional[str],
185
+ model_b_field: Optional[str],
186
+ model_b_name: Optional[str],
187
+ model_b_max_tokens: Optional[int],
188
+ model_b_temperature: Optional[float],
189
+ model_b_system_template: Optional[str],
190
+ model_b_input_template: Optional[str],
191
+ ) -> None:
192
+ """Create a new evaluation job"""
193
+
194
+ client: Together = ctx.obj
195
+
196
+ # Convert strings to lists for labels
197
+ labels_list = labels.split(",") if labels else None
198
+ pass_labels_list = pass_labels.split(",") if pass_labels else None
199
+
200
+ # Build model configurations
201
+ model_to_evaluate_final: Union[Dict[str, Any], None, str] = None
202
+
203
+ # Check if any config parameters are provided
204
+ config_params_provided = any(
205
+ [
206
+ model_to_evaluate_name,
207
+ model_to_evaluate_max_tokens,
208
+ model_to_evaluate_temperature,
209
+ model_to_evaluate_system_template,
210
+ model_to_evaluate_input_template,
211
+ ]
212
+ )
213
+
214
+ if model_field:
215
+ # Simple mode: model_field is provided
216
+ if config_params_provided:
217
+ raise click.BadParameter(
218
+ "Cannot specify both --model-field and --model-to-evaluate-* parameters. "
219
+ "Use either --model-field alone if your input file has pre-generated responses, "
220
+ "or config parameters if you want to generate it on our end"
221
+ )
222
+ model_to_evaluate_final = model_field
223
+ elif config_params_provided:
224
+ # Config mode: config parameters are provided
225
+ model_to_evaluate_final = {
226
+ "model_name": model_to_evaluate_name,
227
+ "max_tokens": model_to_evaluate_max_tokens,
228
+ "temperature": model_to_evaluate_temperature,
229
+ "system_template": model_to_evaluate_system_template,
230
+ "input_template": model_to_evaluate_input_template,
231
+ }
232
+
233
+ # Build model-a configuration
234
+ model_a_final: Union[Dict[str, Any], None, str] = None
235
+ model_a_config_params = [
236
+ model_a_name,
237
+ model_a_max_tokens,
238
+ model_a_temperature,
239
+ model_a_system_template,
240
+ model_a_input_template,
241
+ ]
242
+
243
+ if model_a_field is not None:
244
+ # Simple mode: model_a_field is provided
245
+ if any(model_a_config_params):
246
+ raise click.BadParameter(
247
+ "Cannot specify both --model-a-field and config parameters (--model-a-name, etc.). "
248
+ "Use either --model-a-field alone if your input file has pre-generated responses, "
249
+ "or config parameters if you want to generate it on our end"
250
+ )
251
+ model_a_final = model_a_field
252
+ elif any(model_a_config_params):
253
+ # Config mode: config parameters are provided
254
+ model_a_final = {
255
+ "model_name": model_a_name,
256
+ "max_tokens": model_a_max_tokens,
257
+ "temperature": model_a_temperature,
258
+ "system_template": model_a_system_template,
259
+ "input_template": model_a_input_template,
260
+ }
261
+
262
+ # Build model-b configuration
263
+ model_b_final: Union[Dict[str, Any], None, str] = None
264
+ model_b_config_params = [
265
+ model_b_name,
266
+ model_b_max_tokens,
267
+ model_b_temperature,
268
+ model_b_system_template,
269
+ model_b_input_template,
270
+ ]
271
+
272
+ if model_b_field is not None:
273
+ # Simple mode: model_b_field is provided
274
+ if any(model_b_config_params):
275
+ raise click.BadParameter(
276
+ "Cannot specify both --model-b-field and config parameters (--model-b-name, etc.). "
277
+ "Use either --model-b-field alone if your input file has pre-generated responses, "
278
+ "or config parameters if you want to generate it on our end"
279
+ )
280
+ model_b_final = model_b_field
281
+ elif any(model_b_config_params):
282
+ # Config mode: config parameters are provided
283
+ model_b_final = {
284
+ "model_name": model_b_name,
285
+ "max_tokens": model_b_max_tokens,
286
+ "temperature": model_b_temperature,
287
+ "system_template": model_b_system_template,
288
+ "input_template": model_b_input_template,
289
+ }
290
+
291
+ try:
292
+ response = client.evaluation.create(
293
+ type=type,
294
+ judge_model_name=judge_model_name,
295
+ judge_system_template=judge_system_template,
296
+ input_data_file_path=input_data_file_path,
297
+ model_to_evaluate=model_to_evaluate_final,
298
+ labels=labels_list,
299
+ pass_labels=pass_labels_list,
300
+ min_score=min_score,
301
+ max_score=max_score,
302
+ pass_threshold=pass_threshold,
303
+ model_a=model_a_final,
304
+ model_b=model_b_final,
305
+ )
306
+ except ValueError as e:
307
+ raise click.BadParameter(str(e))
308
+
309
+ click.echo(json.dumps(response.model_dump(exclude_none=True), indent=4))
310
+
311
+
312
+ @evaluation.command()
313
+ @click.pass_context
314
+ @click.option(
315
+ "--status",
316
+ type=str,
317
+ help="Filter by job status.",
318
+ )
319
+ @click.option(
320
+ "--limit",
321
+ type=int,
322
+ help="Limit number of results (max 100).",
323
+ )
324
+ def list(ctx: click.Context, status: Optional[str], limit: Optional[int]) -> None:
325
+ """List evaluation jobs"""
326
+
327
+ client: Together = ctx.obj
328
+
329
+ response = client.evaluation.list(status=status, limit=limit)
330
+
331
+ display_list = []
332
+ for job in response:
333
+ if job.parameters:
334
+ model = job.parameters.get("model_to_evaluate", "")
335
+ model_a = job.parameters.get("model_a", "")
336
+ model_b = job.parameters.get("model_b", "")
337
+ else:
338
+ model = ""
339
+
340
+ display_list.append(
341
+ {
342
+ "Workflow ID": job.workflow_id or "",
343
+ "Type": job.type,
344
+ "Status": job.status,
345
+ "Created At": job.created_at or 0,
346
+ "Model": model,
347
+ "Model A": model_a,
348
+ "Model B": model_b,
349
+ }
350
+ )
351
+
352
+ table = tabulate(display_list, headers="keys", tablefmt="grid", showindex=True)
353
+ click.echo(table)
354
+
355
+
356
+ @evaluation.command()
357
+ @click.pass_context
358
+ @click.argument("evaluation_id", type=str, required=True)
359
+ def retrieve(ctx: click.Context, evaluation_id: str) -> None:
360
+ """Get details of a specific evaluation job"""
361
+
362
+ client: Together = ctx.obj
363
+
364
+ response = client.evaluation.retrieve(evaluation_id=evaluation_id)
365
+
366
+ click.echo(json.dumps(response.model_dump(exclude_none=True), indent=4))
367
+
368
+
369
+ @evaluation.command()
370
+ @click.pass_context
371
+ @click.argument("evaluation_id", type=str, required=True)
372
+ def status(ctx: click.Context, evaluation_id: str) -> None:
373
+ """Get the status and results of a specific evaluation job"""
374
+
375
+ client: Together = ctx.obj
376
+
377
+ response = client.evaluation.status(evaluation_id=evaluation_id)
378
+
379
+ click.echo(json.dumps(response.model_dump(exclude_none=True), indent=4))
@@ -304,13 +304,8 @@ def create(
304
304
  raise click.BadParameter(
305
305
  f"LoRA fine-tuning is not supported for the model `{model}`"
306
306
  )
307
- if training_method == "dpo":
308
- default_batch_size = model_limits.lora_training.max_batch_size_dpo
309
- else:
310
- default_batch_size = model_limits.lora_training.max_batch_size
311
307
  default_values = {
312
308
  "lora_r": model_limits.lora_training.max_rank,
313
- "batch_size": default_batch_size,
314
309
  "learning_rate": 1e-3,
315
310
  }
316
311
 
@@ -335,15 +330,6 @@ def create(
335
330
  f"Please change the job type with --lora or remove `{param}` from the arguments"
336
331
  )
337
332
 
338
- batch_size_source = ctx.get_parameter_source("batch_size") # type: ignore[attr-defined]
339
- if batch_size_source == ParameterSource.DEFAULT:
340
- if training_method == "dpo":
341
- training_args["batch_size"] = (
342
- model_limits.full_training.max_batch_size_dpo
343
- )
344
- else:
345
- training_args["batch_size"] = model_limits.full_training.max_batch_size
346
-
347
333
  if n_evals <= 0 and validation_file:
348
334
  log_warn(
349
335
  "Warning: You have specified a validation file but the number of evaluation loops is set to 0. No evaluations will be performed."
@@ -9,6 +9,7 @@ import together
9
9
  from together.cli.api.chat import chat, interactive
10
10
  from together.cli.api.completions import completions
11
11
  from together.cli.api.endpoints import endpoints
12
+ from together.cli.api.evaluation import evaluation
12
13
  from together.cli.api.files import files
13
14
  from together.cli.api.finetune import fine_tuning
14
15
  from together.cli.api.images import images
@@ -74,6 +75,7 @@ main.add_command(files)
74
75
  main.add_command(fine_tuning)
75
76
  main.add_command(models)
76
77
  main.add_command(endpoints)
78
+ main.add_command(evaluation)
77
79
 
78
80
  if __name__ == "__main__":
79
81
  main()
@@ -25,6 +25,7 @@ class Together:
25
25
  audio: resources.Audio
26
26
  batches: resources.Batches
27
27
  code_interpreter: CodeInterpreter
28
+ evaluation: resources.Evaluation
28
29
 
29
30
  # client options
30
31
  client: TogetherClient
@@ -92,6 +93,7 @@ class Together:
92
93
  self.endpoints = resources.Endpoints(self.client)
93
94
  self.code_interpreter = CodeInterpreter(self.client)
94
95
  self.batches = resources.Batches(self.client)
96
+ self.evaluation = resources.Evaluation(self.client)
95
97
 
96
98
 
97
99
  class AsyncTogether:
@@ -106,6 +108,7 @@ class AsyncTogether:
106
108
  audio: resources.AsyncAudio
107
109
  code_interpreter: CodeInterpreter
108
110
  batches: resources.AsyncBatches
111
+ evaluation: resources.AsyncEvaluation
109
112
  # client options
110
113
  client: TogetherClient
111
114
 
@@ -171,6 +174,7 @@ class AsyncTogether:
171
174
  self.audio = resources.AsyncAudio(self.client)
172
175
  self.code_interpreter = CodeInterpreter(self.client)
173
176
  self.batches = resources.AsyncBatches(self.client)
177
+ self.evaluation = resources.AsyncEvaluation(self.client)
174
178
 
175
179
 
176
180
  Client = Together
@@ -73,8 +73,6 @@ def _get_file_size(
73
73
  if len(range_parts) == 2:
74
74
  total_size_in_bytes = int(range_parts[1])
75
75
 
76
- assert total_size_in_bytes != 0, "Unable to retrieve remote file."
77
-
78
76
  return total_size_in_bytes
79
77
 
80
78
 
@@ -213,8 +211,6 @@ class DownloadManager:
213
211
  if not fetch_metadata:
214
212
  file_size = int(response.headers.get("content-length", 0))
215
213
 
216
- assert file_size != 0, "Unable to retrieve remote file."
217
-
218
214
  with tqdm(
219
215
  total=file_size,
220
216
  unit="B",
@@ -334,6 +330,8 @@ class UploadManager:
334
330
  filetype = FileType.jsonl
335
331
  elif file.suffix == ".parquet":
336
332
  filetype = FileType.parquet
333
+ elif file.suffix == ".csv":
334
+ filetype = FileType.csv
337
335
  else:
338
336
  raise FileTypeError(
339
337
  f"Unknown extension of file {file}. "
@@ -16,7 +16,7 @@ class Finetune:
16
16
  model: str,
17
17
  n_epochs: int = 1,
18
18
  n_checkpoints: int | None = 1,
19
- batch_size: int | None = 32,
19
+ batch_size: int | Literal["max"] = "max",
20
20
  learning_rate: float = 0.00001,
21
21
  suffix: (
22
22
  str | None
@@ -43,7 +43,7 @@ class Finetune:
43
43
  model=model,
44
44
  n_epochs=n_epochs,
45
45
  n_checkpoints=n_checkpoints,
46
- batch_size=batch_size if isinstance(batch_size, int) else "max",
46
+ batch_size=batch_size,
47
47
  learning_rate=learning_rate,
48
48
  suffix=suffix,
49
49
  wandb_api_key=wandb_api_key,
@@ -9,6 +9,7 @@ from together.resources.images import AsyncImages, Images
9
9
  from together.resources.models import AsyncModels, Models
10
10
  from together.resources.rerank import AsyncRerank, Rerank
11
11
  from together.resources.batch import Batches, AsyncBatches
12
+ from together.resources.evaluation import Evaluation, AsyncEvaluation
12
13
 
13
14
 
14
15
  __all__ = [
@@ -34,4 +35,6 @@ __all__ = [
34
35
  "Endpoints",
35
36
  "Batches",
36
37
  "AsyncBatches",
38
+ "Evaluation",
39
+ "AsyncEvaluation",
37
40
  ]
@@ -16,7 +16,6 @@ class Batches:
16
16
  self._client = client
17
17
 
18
18
  def create_batch(self, file_id: str, endpoint: str) -> BatchJob:
19
-
20
19
  requestor = api_requestor.APIRequestor(
21
20
  client=self._client,
22
21
  )