openweights 0.1.0__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.
- openweights-0.1.0/.dockerignore +8 -0
- openweights-0.1.0/.env.example +3 -0
- openweights-0.1.0/.github/ISSUE_TEMPLATE/bug_report.md +27 -0
- openweights-0.1.0/.github/ISSUE_TEMPLATE/feature_request.md +12 -0
- openweights-0.1.0/.github/workflows/ci.yaml +99 -0
- openweights-0.1.0/.github/workflows/manual_publish.yaml +24 -0
- openweights-0.1.0/.gitignore +76 -0
- openweights-0.1.0/.pdm-python +1 -0
- openweights-0.1.0/LICENSE.txt +21 -0
- openweights-0.1.0/PKG-INFO +139 -0
- openweights-0.1.0/README.md +113 -0
- openweights-0.1.0/docs/finetuning.md +144 -0
- openweights-0.1.0/entrypoint.sh +60 -0
- openweights-0.1.0/example/analyze_hparam_sweep.ipynb +923 -0
- openweights-0.1.0/example/cancel.py +12 -0
- openweights-0.1.0/example/compute_outputs.py +18 -0
- openweights-0.1.0/example/custom_job/README.md +36 -0
- openweights-0.1.0/example/custom_job/add_numbers.py +17 -0
- openweights-0.1.0/example/custom_job/start_custom_job.py +64 -0
- openweights-0.1.0/example/download.py +65 -0
- openweights-0.1.0/example/gradio_ui_with_temporary_api.py +35 -0
- openweights-0.1.0/example/guided-inference/guided_inference.py +138 -0
- openweights-0.1.0/example/guided-inference/messages.jsonl +1 -0
- openweights-0.1.0/example/guided-inference/start_custom_job.py +103 -0
- openweights-0.1.0/example/hparams_sweep.py +92 -0
- openweights-0.1.0/example/multi_lora_deploy.py +12 -0
- openweights-0.1.0/example/multi_model_chat.py +82 -0
- openweights-0.1.0/example/restart_failed.py +13 -0
- openweights-0.1.0/example/run_ft_job.py +43 -0
- openweights-0.1.0/example/run_inference_job.py +51 -0
- openweights-0.1.0/example/run_script_job.py +34 -0
- openweights-0.1.0/openweights/__init__.py +3 -0
- openweights-0.1.0/openweights/client/__init__.py +176 -0
- openweights-0.1.0/openweights/client/cache_on_disk.py +34 -0
- openweights-0.1.0/openweights/client/chat.py +135 -0
- openweights-0.1.0/openweights/client/custom_job.py +96 -0
- openweights-0.1.0/openweights/client/events.py +42 -0
- openweights-0.1.0/openweights/client/files.py +106 -0
- openweights-0.1.0/openweights/client/jobs.py +293 -0
- openweights-0.1.0/openweights/client/run.py +189 -0
- openweights-0.1.0/openweights/client/temporary_api.py +231 -0
- openweights-0.1.0/openweights/cluster/.gitignore +1 -0
- openweights-0.1.0/openweights/cluster/README.md +32 -0
- openweights-0.1.0/openweights/cluster/org_manager.py +366 -0
- openweights-0.1.0/openweights/cluster/start_runpod.py +211 -0
- openweights-0.1.0/openweights/cluster/supervisor.py +177 -0
- openweights-0.1.0/openweights/dashboard/README.md +77 -0
- openweights-0.1.0/openweights/dashboard/backend/database.py +432 -0
- openweights-0.1.0/openweights/dashboard/backend/main.py +285 -0
- openweights-0.1.0/openweights/dashboard/backend/models.py +69 -0
- openweights-0.1.0/openweights/dashboard/backend/static/assets/ow.svg +22 -0
- openweights-0.1.0/openweights/dashboard/backend/static/assets/vite.svg +1 -0
- openweights-0.1.0/openweights/dashboard/backend/utils.py +143 -0
- openweights-0.1.0/openweights/dashboard/deploy.sh +41 -0
- openweights-0.1.0/openweights/dashboard/frontend/.gitignore +24 -0
- openweights-0.1.0/openweights/dashboard/frontend/README.md +50 -0
- openweights-0.1.0/openweights/dashboard/frontend/eslint.config.js +28 -0
- openweights-0.1.0/openweights/dashboard/frontend/index.html +13 -0
- openweights-0.1.0/openweights/dashboard/frontend/package-lock.json +7839 -0
- openweights-0.1.0/openweights/dashboard/frontend/package.json +40 -0
- openweights-0.1.0/openweights/dashboard/frontend/public/ow.svg +22 -0
- openweights-0.1.0/openweights/dashboard/frontend/public/vite.svg +1 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/App.css +47 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/App.tsx +300 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/api.ts +292 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/assets/react.svg +1 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/Auth/Auth.tsx +231 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/FileContent.tsx +40 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/JobDetailView.tsx +213 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/MetricsDisplay.tsx +90 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/MetricsPlots.tsx +179 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/OutputsDisplay.tsx +62 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/RunDetailView.tsx +147 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/WorkerDetailView.tsx +257 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews/index.ts +3 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/DetailViews.tsx +1 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/JobsListView.tsx +134 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/JobsView.tsx +366 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/Organizations/OrganizationDetail.tsx +592 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/Organizations/OrganizationList.tsx +227 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/Organizations/OrganizationSwitcher.tsx +39 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/Organizations/OrganizationsList.tsx +168 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/Organizations/TokensTab.tsx +261 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/RefreshButton.tsx +33 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/RunsListView.tsx +134 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/RunsView.tsx +332 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/StatusCheckboxes.tsx +62 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/TokenView.tsx +245 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/ViewToggle.tsx +33 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/WorkersListView.tsx +140 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/components/WorkersView.tsx +357 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/contexts/AuthContext.tsx +103 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/contexts/OrganizationContext.tsx +92 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/index.css +59 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/main.tsx +10 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/supabaseClient.ts +11 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/types/supabase.ts +63 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/types.ts +64 -0
- openweights-0.1.0/openweights/dashboard/frontend/src/vite-env.d.ts +1 -0
- openweights-0.1.0/openweights/dashboard/frontend/tsconfig.app.json +26 -0
- openweights-0.1.0/openweights/dashboard/frontend/tsconfig.json +7 -0
- openweights-0.1.0/openweights/dashboard/frontend/tsconfig.node.json +24 -0
- openweights-0.1.0/openweights/dashboard/frontend/vite.config.ts +8 -0
- openweights-0.1.0/openweights/dashboard/runpod-startup.sh +107 -0
- openweights-0.1.0/openweights/dashboard/screenshots/job_details.png +0 -0
- openweights-0.1.0/openweights/dashboard/screenshots/jobs_view.png +0 -0
- openweights-0.1.0/openweights/dashboard/screenshots/run_details.png +0 -0
- openweights-0.1.0/openweights/dashboard/screenshots/workers.png +0 -0
- openweights-0.1.0/openweights/utils.py +250 -0
- openweights-0.1.0/openweights/validate.py +276 -0
- openweights-0.1.0/openweights/worker/__init__.py +0 -0
- openweights-0.1.0/openweights/worker/dpo_ft.py +67 -0
- openweights-0.1.0/openweights/worker/gpu_health_check.py +111 -0
- openweights-0.1.0/openweights/worker/inference.py +140 -0
- openweights-0.1.0/openweights/worker/main.py +435 -0
- openweights-0.1.0/openweights/worker/orpo_ft.py +64 -0
- openweights-0.1.0/openweights/worker/sft.py +109 -0
- openweights-0.1.0/openweights/worker/training.py +94 -0
- openweights-0.1.0/openweights/worker/utils.py +88 -0
- openweights-0.1.0/ow-axolotl.Dockerfile +37 -0
- openweights-0.1.0/ow-inference.Dockerfile +30 -0
- openweights-0.1.0/ow-unsloth.Dockerfile +24 -0
- openweights-0.1.0/pyproject.toml +35 -0
- openweights-0.1.0/scripts/migrate_files.py +106 -0
- openweights-0.1.0/scripts/use_local_vllm_client.py +37 -0
- openweights-0.1.0/supabase/.gitignore +4 -0
- openweights-0.1.0/supabase/config.toml +256 -0
- openweights-0.1.0/supabase/migrations/20241120094415_remote_schema.sql +161 -0
- openweights-0.1.0/supabase/migrations/20241120161019_add_gpu_columns.sql +9 -0
- openweights-0.1.0/supabase/migrations/20241127132826_add_docker_image.sql +8 -0
- openweights-0.1.0/supabase/migrations/20241127153031_add_docker_image_to_workers.sql +1 -0
- openweights-0.1.0/supabase/migrations/20241202233213_add_updated_at_columns.sql +52 -0
- openweights-0.1.0/supabase/migrations/20241203000542_add_api_job_type.sql +2 -0
- openweights-0.1.0/supabase/migrations/20241205000000_add_organizations.sql +67 -0
- openweights-0.1.0/supabase/migrations/20241205000001_add_organization_functions.sql +124 -0
- openweights-0.1.0/supabase/migrations/20241205000002_add_rls_policies.sql +66 -0
- openweights-0.1.0/supabase/migrations/20241205000003_add_service_accounts.sql +151 -0
- openweights-0.1.0/supabase/migrations/20241205000004_add_storage_policies.sql +130 -0
- openweights-0.1.0/supabase/migrations/20241205000005_add_token_functions.sql +46 -0
- openweights-0.1.0/supabase/migrations/20241205000006_fix_jwt_secret.sql +22 -0
- openweights-0.1.0/supabase/migrations/20241205000007_add_organization_secrets.sql +184 -0
- openweights-0.1.0/supabase/migrations/20241205000008_fix_member_functions.sql +83 -0
- openweights-0.1.0/supabase/migrations/20241205000009_fix_email_ambiguity.sql +83 -0
- openweights-0.1.0/supabase/migrations/20241205000010_remove_token_org_fallback.sql +25 -0
- openweights-0.1.0/supabase/migrations/20241205000011_add_job_timeout.sql +20 -0
- openweights-0.1.0/supabase/migrations/20250101195830_add_worker_logfile.sql +8 -0
- openweights-0.1.0/supabase/migrations/20250101195831_add_custom_job_type.sql +2 -0
- openweights-0.1.0/supabase/migrations/20250115171900_add_job_locking_functions.sql +38 -0
- openweights-0.1.0/supabase/migrations/20250116110200_fix_job_locking_naming.sql +50 -0
- openweights-0.1.0/supabase/migrations/20250116111600_fix_job_id_dtypes.sql +51 -0
- openweights-0.1.0/supabase/migrations/20250116112300_fix_job_status_type.sql +24 -0
- openweights-0.1.0/supabase/migrations_dev/20241120094415_remote_schema.sql +161 -0
- openweights-0.1.0/supabase/migrations_dev/20241120161019_add_gpu_columns.sql +9 -0
- openweights-0.1.0/supabase/migrations_dev/20241127132826_add_docker_image.sql +8 -0
- openweights-0.1.0/supabase/migrations_dev/20241127153031_add_docker_image_to_workers.sql +1 -0
- openweights-0.1.0/supabase/migrations_dev/20241202233213_add_updated_at_columns.sql +52 -0
- openweights-0.1.0/supabase/migrations_dev/20241203000542_add_api_job_type.sql +2 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000000_add_organizations.sql +206 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000002_fix_organization_policies.sql +47 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000003_fix_organization_member_policies.sql +24 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000004_fix_all_organization_policies.sql +100 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000005_add_organization_functions.sql +51 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000006_fix_organization_function_types.sql +55 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000007_fix_get_user_by_email_param.sql +25 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000008_improve_get_user_by_email.sql +33 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000009_add_invite_member_function.sql +60 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000010_fix_invite_member_function.sql +67 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000011_fix_get_members_function.sql +33 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000012_fix_organization_check_functions.sql +102 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000013_fix_all_user_id_references.sql +96 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000014_add_storage_policies.sql +79 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000015_migrate_existing_files.sql +40 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000016_fix_file_migration.sql +67 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000017_migrate_file_references.sql +76 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000018_revert_file_references.sql +62 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000019_verify_file_locations.sql +115 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000020_fix_storage_locations.sql +102 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000021_check_storage.sql +6 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000022_fix_storage_policies.sql +71 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000023_add_api_tokens.sql +122 -0
- openweights-0.1.0/supabase/migrations_dev/20241205000024_add_token_validation.sql +28 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000001_add_long_lived_tokens.sql +40 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000002_add_token_hash.sql +3 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000003_update_rls_for_custom_tokens.sql +100 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000004_update_token_auth.sql +128 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000005_service_accounts.sql +121 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000006_cleanup_token_tables.sql +9 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000007_fix_token_creation.sql +60 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000009_jwt_secret_function.sql +69 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000010_fix_token_validation.sql +221 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000011_fix_job_policies.sql +22 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000012_add_get_org_function.sql +31 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000013_fix_storage_policies.sql +119 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000014_fix_storage_setup.sql +141 -0
- openweights-0.1.0/supabase/migrations_dev/20241219000015_fix_run_policies.sql +75 -0
- openweights-0.1.0/tests/inference_dataset_with_prefill.jsonl +3 -0
- openweights-0.1.0/tests/preference_dataset.jsonl +4 -0
- openweights-0.1.0/tests/sft_dataset.jsonl +1 -0
- openweights-0.1.0/tests/test_client.py +218 -0
- openweights-0.1.0/tests/test_run.py +145 -0
- openweights-0.1.0/tests/test_validation.py +133 -0
- openweights-0.1.0/tests/test_worker.py +49 -0
- openweights-0.1.0/todo.md +33 -0
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: Bug report
|
|
3
|
+
about: Create a report to help us improve
|
|
4
|
+
title: ''
|
|
5
|
+
labels: ''
|
|
6
|
+
assignees: ''
|
|
7
|
+
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
**Relevant `job_id`, `run_id`, or `worker_id`:
|
|
11
|
+
- eg job: ft-12345678
|
|
12
|
+
|
|
13
|
+
**Describe the bug**
|
|
14
|
+
A clear and concise description of what the bug is.
|
|
15
|
+
|
|
16
|
+
**To Reproduce**
|
|
17
|
+
Steps to reproduce the behavior:
|
|
18
|
+
1. Go to '...'
|
|
19
|
+
2. Click on '....'
|
|
20
|
+
3. Scroll down to '....'
|
|
21
|
+
4. See error
|
|
22
|
+
|
|
23
|
+
**Expected behavior**
|
|
24
|
+
A clear and concise description of what you expected to happen.
|
|
25
|
+
|
|
26
|
+
**Screenshots**
|
|
27
|
+
If applicable, add screenshots to help explain your problem.
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
name: "ci"
|
|
2
|
+
on: # rebuild any PRs and main branch changes
|
|
3
|
+
pull_request:
|
|
4
|
+
push:
|
|
5
|
+
branches:
|
|
6
|
+
- main
|
|
7
|
+
|
|
8
|
+
concurrency:
|
|
9
|
+
group: ${{ github.repository_owner }}-${{ github.repository }}-${{ github.ref }}
|
|
10
|
+
cancel-in-progress: true
|
|
11
|
+
|
|
12
|
+
env:
|
|
13
|
+
FORCE_COLOR: "1"
|
|
14
|
+
PYTHONUNBUFFERED: "1"
|
|
15
|
+
|
|
16
|
+
jobs:
|
|
17
|
+
build:
|
|
18
|
+
runs-on: ubuntu-latest
|
|
19
|
+
permissions:
|
|
20
|
+
contents: read
|
|
21
|
+
packages: write
|
|
22
|
+
|
|
23
|
+
strategy:
|
|
24
|
+
matrix:
|
|
25
|
+
python-version: ["3.10", "3.11", "3.12"]
|
|
26
|
+
|
|
27
|
+
steps:
|
|
28
|
+
- name: Checkout repository
|
|
29
|
+
uses: actions/checkout@v4
|
|
30
|
+
- name: Setup PDM
|
|
31
|
+
uses: pdm-project/setup-pdm@v4
|
|
32
|
+
with:
|
|
33
|
+
cache: false # project doesn't use pdm lock files
|
|
34
|
+
python-version: ${{ matrix.python-version }}
|
|
35
|
+
- name: Setup UV
|
|
36
|
+
uses: astral-sh/setup-uv@v5
|
|
37
|
+
- name: Configure PDM to use UV
|
|
38
|
+
run: pdm config use_uv true
|
|
39
|
+
- name: Cache Huggingface assets
|
|
40
|
+
uses: actions/cache@v4
|
|
41
|
+
with:
|
|
42
|
+
key: huggingface-${{ runner.os }}-${{ matrix.python-version }}-${{ hashFiles('**/pyproject.toml') }}
|
|
43
|
+
path: ~/.cache/huggingface
|
|
44
|
+
restore-keys: |
|
|
45
|
+
huggingface-${{ runner.os }}-${{ matrix.python-version }}-
|
|
46
|
+
- name: Install dependencies
|
|
47
|
+
run: pdm install --group dev --no-lock
|
|
48
|
+
|
|
49
|
+
# TODO: re-enable when we have pre-commit hooks
|
|
50
|
+
# - name: Install pre-commit hooks
|
|
51
|
+
# run: pdm run pre-commit install
|
|
52
|
+
# - name: Ensure pre-commit hooks pass
|
|
53
|
+
# run: pdm run pre-commit run --all-files
|
|
54
|
+
|
|
55
|
+
# TODO: tests don't currently pass due to missing torch dependency
|
|
56
|
+
# see: https://github.com/longtermrisk/openweights/actions/runs/13210898278/job/36883965796?pr=11#step:8:29
|
|
57
|
+
|
|
58
|
+
# - name: Run tests
|
|
59
|
+
# env:
|
|
60
|
+
# HF_TOKEN: ${{ secrets.HF_TOKEN }}
|
|
61
|
+
# run: pdm run python -m pytest tests
|
|
62
|
+
|
|
63
|
+
release:
|
|
64
|
+
needs: build
|
|
65
|
+
environment: pypi
|
|
66
|
+
permissions:
|
|
67
|
+
contents: write
|
|
68
|
+
id-token: write
|
|
69
|
+
# https://github.community/t/how-do-i-specify-job-dependency-running-in-another-workflow/16482
|
|
70
|
+
if: github.event_name == 'push' && github.ref == 'refs/heads/main' && !contains(github.event.head_commit.message, 'chore')
|
|
71
|
+
runs-on: ubuntu-latest
|
|
72
|
+
concurrency: release
|
|
73
|
+
steps:
|
|
74
|
+
- uses: actions/checkout@v4
|
|
75
|
+
with:
|
|
76
|
+
fetch-depth: 0
|
|
77
|
+
- uses: pdm-project/setup-pdm@v4
|
|
78
|
+
with:
|
|
79
|
+
cache: true
|
|
80
|
+
python-version: "3.12"
|
|
81
|
+
- name: build
|
|
82
|
+
run: pdm build
|
|
83
|
+
- name: Semantic Release
|
|
84
|
+
id: release
|
|
85
|
+
uses: python-semantic-release/python-semantic-release@v8.0.7
|
|
86
|
+
with:
|
|
87
|
+
github_token: ${{ secrets.GITHUB_TOKEN }}
|
|
88
|
+
|
|
89
|
+
# - name: Publish package distributions to PyPI
|
|
90
|
+
# uses: pypa/gh-action-pypi-publish@release/v1
|
|
91
|
+
# if: steps.release.outputs.released == 'true'
|
|
92
|
+
- name: Publish package distributions to GitHub Releases
|
|
93
|
+
uses: python-semantic-release/upload-to-gh-release@main
|
|
94
|
+
if: steps.release.outputs.released == 'true'
|
|
95
|
+
with:
|
|
96
|
+
github_token: ${{ secrets.GITHUB_TOKEN }}
|
|
97
|
+
|
|
98
|
+
# TODO: build and deploy docs to gh-pages
|
|
99
|
+
# do this as part of the semantic release step to ensure version is bumped
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
name: "manual-publish"
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
workflow_dispatch: # Allows manual triggering
|
|
5
|
+
|
|
6
|
+
jobs:
|
|
7
|
+
publish:
|
|
8
|
+
runs-on: ubuntu-latest
|
|
9
|
+
environment: pypi
|
|
10
|
+
permissions:
|
|
11
|
+
id-token: write
|
|
12
|
+
|
|
13
|
+
steps:
|
|
14
|
+
- uses: actions/checkout@v4
|
|
15
|
+
|
|
16
|
+
- uses: pdm-project/setup-pdm@v4
|
|
17
|
+
with:
|
|
18
|
+
python-version: "3.12"
|
|
19
|
+
|
|
20
|
+
- name: Build
|
|
21
|
+
run: pdm build
|
|
22
|
+
|
|
23
|
+
- name: Publish package distributions to PyPI
|
|
24
|
+
uses: pypa/gh-action-pypi-publish@release/v1
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
logs/
|
|
2
|
+
openweights/dashboard/backend/backend.log
|
|
3
|
+
openweights/dashboard/backend/backend.pid
|
|
4
|
+
build-docker-in-runpod
|
|
5
|
+
.env
|
|
6
|
+
.env.dev
|
|
7
|
+
.env.prod
|
|
8
|
+
.env.ow-dev
|
|
9
|
+
.env.ow-migrations
|
|
10
|
+
openweights/dashboard/backend/.env.ow-dev
|
|
11
|
+
openweights/dashboard/backend/.env.ow-migrations
|
|
12
|
+
openweights/dashboard/frontend/.env.ow-dev
|
|
13
|
+
openweights/dashboard/frontend/.env.ow-migrations
|
|
14
|
+
artifacts/
|
|
15
|
+
debug/
|
|
16
|
+
example/.ipynb_checkpoints/
|
|
17
|
+
example/Untitled1.ipynb
|
|
18
|
+
dev.py
|
|
19
|
+
planb/
|
|
20
|
+
vulnerable-code/
|
|
21
|
+
openweights/client/.llm-cache
|
|
22
|
+
# yeaa
|
|
23
|
+
cache
|
|
24
|
+
# Bazel
|
|
25
|
+
/bazel-*
|
|
26
|
+
/bazel-bin
|
|
27
|
+
/bazel-genfiles
|
|
28
|
+
/bazel-out
|
|
29
|
+
/bazel-testlogs
|
|
30
|
+
/bazel-workspace
|
|
31
|
+
|
|
32
|
+
# Bazel symlinks
|
|
33
|
+
/bazel-*
|
|
34
|
+
|
|
35
|
+
# Bazel disk cache
|
|
36
|
+
.bazel-cache/
|
|
37
|
+
|
|
38
|
+
# Bazel IntelliJ plugin
|
|
39
|
+
.ijwb/
|
|
40
|
+
|
|
41
|
+
# Python
|
|
42
|
+
__pycache__/
|
|
43
|
+
*.py[cod]
|
|
44
|
+
*$py.class
|
|
45
|
+
*.so
|
|
46
|
+
.Python
|
|
47
|
+
build/
|
|
48
|
+
develop-eggs/
|
|
49
|
+
dist/
|
|
50
|
+
downloads/
|
|
51
|
+
eggs/
|
|
52
|
+
.eggs/
|
|
53
|
+
lib/
|
|
54
|
+
lib64/
|
|
55
|
+
parts/
|
|
56
|
+
sdist/
|
|
57
|
+
var/
|
|
58
|
+
wheels/
|
|
59
|
+
*.egg-info/
|
|
60
|
+
.installed.cfg
|
|
61
|
+
*.egg
|
|
62
|
+
|
|
63
|
+
# Virtual Environment
|
|
64
|
+
venv/
|
|
65
|
+
env/
|
|
66
|
+
ENV/
|
|
67
|
+
|
|
68
|
+
# IDE
|
|
69
|
+
.idea/
|
|
70
|
+
.vscode/
|
|
71
|
+
*.swp
|
|
72
|
+
*.swo
|
|
73
|
+
|
|
74
|
+
# OS
|
|
75
|
+
.DS_Store
|
|
76
|
+
Thumbs.db
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
/home/runner/work/openweights/openweights/.venv/bin/python
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 Center on Longterm Risk
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: openweights
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: An openai-like sdk for finetuning and batch inference
|
|
5
|
+
License: MIT
|
|
6
|
+
License-File: LICENSE.txt
|
|
7
|
+
Requires-Python: >=3.11
|
|
8
|
+
Requires-Dist: diskcache
|
|
9
|
+
Requires-Dist: fastapi
|
|
10
|
+
Requires-Dist: fire
|
|
11
|
+
Requires-Dist: httpx>=0.24.0
|
|
12
|
+
Requires-Dist: huggingface-hub
|
|
13
|
+
Requires-Dist: openai
|
|
14
|
+
Requires-Dist: pyjwt
|
|
15
|
+
Requires-Dist: python-dotenv
|
|
16
|
+
Requires-Dist: runpod
|
|
17
|
+
Requires-Dist: scp
|
|
18
|
+
Requires-Dist: supabase
|
|
19
|
+
Requires-Dist: uvicorn
|
|
20
|
+
Provides-Extra: dev
|
|
21
|
+
Requires-Dist: black; extra == 'dev'
|
|
22
|
+
Requires-Dist: isort; extra == 'dev'
|
|
23
|
+
Requires-Dist: pytest-asyncio>=0.21.0; extra == 'dev'
|
|
24
|
+
Requires-Dist: pytest>=7.0.0; extra == 'dev'
|
|
25
|
+
Description-Content-Type: text/markdown
|
|
26
|
+
|
|
27
|
+
This repo is research code and not 100% stable. Please use github issues or contact me via email (niels dot warncke at gmail dot com) or slack when you encounter issues.
|
|
28
|
+
|
|
29
|
+
# OpenWeights
|
|
30
|
+
An openai-like sdk for finetuning and batch inference. Manages runpod instances for you, or you can run a [worker](openweights/worker) on your own GPU.
|
|
31
|
+
|
|
32
|
+
# Installation
|
|
33
|
+
Clone the repo and run `pip install -e .`.
|
|
34
|
+
Then add your `$OPENWEIGHTS_API_KEY` to the `.env`. You can create one via the [dashboard](https://ktf8znsjvlhidw-8124.proxy.runpod.net/).
|
|
35
|
+
|
|
36
|
+
# Quickstart
|
|
37
|
+
```python
|
|
38
|
+
from openweights import OpenWeights
|
|
39
|
+
client = OpenWeights()
|
|
40
|
+
|
|
41
|
+
with open('tests/preference_dataset.jsonl', 'rb') as file:
|
|
42
|
+
file = client.files.create(file, purpose="preference")
|
|
43
|
+
|
|
44
|
+
job = client.fine_tuning.create(
|
|
45
|
+
model='unsloth/llama-3-8b-Instruct',
|
|
46
|
+
training_file=file['id'],
|
|
47
|
+
loss='dpo'
|
|
48
|
+
)
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
# Client-side usage:
|
|
52
|
+
|
|
53
|
+
## Create a finetuning job
|
|
54
|
+
|
|
55
|
+
```python
|
|
56
|
+
from openweights import OpenWeights
|
|
57
|
+
from dotenv import load_dotenv
|
|
58
|
+
|
|
59
|
+
load_dotenv()
|
|
60
|
+
client = OpenWeights()
|
|
61
|
+
|
|
62
|
+
with open('tests/sft_dataset.jsonl', 'rb') as file:
|
|
63
|
+
file = client.files.create(file, purpose="conversations")
|
|
64
|
+
|
|
65
|
+
job = client.fine_tuning.create(
|
|
66
|
+
model='unsloth/llama-3-8b-Instruct',
|
|
67
|
+
training_file=file['id'],
|
|
68
|
+
requires_vram_gb=48,
|
|
69
|
+
loss='sft',
|
|
70
|
+
epochs=1
|
|
71
|
+
)
|
|
72
|
+
```
|
|
73
|
+
The `job_id` is based on the params hash, which means that if you submit the same job many times, it will only run once. If you resubmit a failed or canceled job, it will reset the job status to `pending`.
|
|
74
|
+
|
|
75
|
+
More infos: [Fine-tuning Options](docs/finetuning.md)
|
|
76
|
+
|
|
77
|
+
## Do batch inference
|
|
78
|
+
```python
|
|
79
|
+
|
|
80
|
+
file = client.files.create(
|
|
81
|
+
file=open("mydata.jsonl", "rb"),
|
|
82
|
+
purpose="conversations"
|
|
83
|
+
)
|
|
84
|
+
|
|
85
|
+
job = client.inference.create(
|
|
86
|
+
model=model,
|
|
87
|
+
input_file_id=file['id'],
|
|
88
|
+
max_tokens=1000,
|
|
89
|
+
temperature=1,
|
|
90
|
+
min_tokens=600,
|
|
91
|
+
)
|
|
92
|
+
print(job)
|
|
93
|
+
|
|
94
|
+
job = client.jobs.retrieve(job['id'])
|
|
95
|
+
```
|
|
96
|
+
Wait until job is finished, then get the output:
|
|
97
|
+
|
|
98
|
+
```py
|
|
99
|
+
output_file_id = job['outputs']['file']
|
|
100
|
+
output = client.files.content(output_file_id).decode('utf-8')
|
|
101
|
+
print(output)
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
## Custom jobs
|
|
105
|
+
Maybe you'd like to use autoscaling with queues for workloads that are not currently supported. You can start a pod that is set up like a worker but doesn't start `openweights/worker/main.py` by running:
|
|
106
|
+
```sh
|
|
107
|
+
python openweights/cluster/start_runpod.py A6000 finetuning --dev_mode=true
|
|
108
|
+
```
|
|
109
|
+
Then develop your script and finally create a `CustomJob` like in this [example](example/custom_job).
|
|
110
|
+
|
|
111
|
+
## Deploy a model as a temporary Openai-like API
|
|
112
|
+
|
|
113
|
+
You can deploy models as openai-like APIs in one of the following ways (sorted from highest to lowest level of abstraction)
|
|
114
|
+
- create chat completions via `ow.chat.completions.sync_create` or `.async_create` - this will deploy models when needed. This queues to-be-deployed models for 5 seconds and then deploys them via `ow.multi_deploy`. This client is optimized to not overload the vllm server it is talking to and caches requests on disk when a `seed` parameter is given.
|
|
115
|
+
- pass a list of models to deploy to `ow.multi_deploy` - this takes a list of models or lora adapters, groups them by `base_model`, and deploys all lora adapters of the same base model on one API to save runpod resources. Calls `ow.deploy` for each single deployment job. [Example](example/multi_lora_deploy.py)
|
|
116
|
+
- `ow.deploy` - takes a single model and optionally a list of lora adapters, then creates a job of type `api`. Returns a `openweights.client.temporary_api.TemporaryAPI` object. [Example](example/gradio_ui_with_temporary_api.py)
|
|
117
|
+
|
|
118
|
+
API jobs can never complete, they stop either because they are canceled or failed. API jobs have a timeout 15 minutes in the future when they are being created, and while a `TemporaryAPI` is alive (after `api.up()` and before `api.down()` has been called), it resets the timeout every minute. This ensures that an API is alive while the process that created it is running, at that it will automatically shut down later - but not immediately so that during debugging you don't always have to wait for deployment.
|
|
119
|
+
|
|
120
|
+
|
|
121
|
+
## Using `client.deploy(model)`
|
|
122
|
+
```py
|
|
123
|
+
from openweights import OpenWeights
|
|
124
|
+
|
|
125
|
+
client = OpenWeights()
|
|
126
|
+
|
|
127
|
+
model = 'unsloth/llama-3-8b-Instruct'
|
|
128
|
+
with client.deploy(model) as openai:
|
|
129
|
+
completion = openai.chat.completions.create(
|
|
130
|
+
model=model,
|
|
131
|
+
messages=[{"role": "user", "content": "is 9.11 > 9.9?"}]
|
|
132
|
+
)
|
|
133
|
+
print(completion.choices[0].message)
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
More examples:
|
|
137
|
+
- do a [hyperparameter sweep](example/hparams_sweep.py) and [visualize the results](example/analyze_hparam_sweep.ipynb)
|
|
138
|
+
- [download artifacts](example/download.py) from a job and plot training
|
|
139
|
+
- and [more](example/)
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
This repo is research code and not 100% stable. Please use github issues or contact me via email (niels dot warncke at gmail dot com) or slack when you encounter issues.
|
|
2
|
+
|
|
3
|
+
# OpenWeights
|
|
4
|
+
An openai-like sdk for finetuning and batch inference. Manages runpod instances for you, or you can run a [worker](openweights/worker) on your own GPU.
|
|
5
|
+
|
|
6
|
+
# Installation
|
|
7
|
+
Clone the repo and run `pip install -e .`.
|
|
8
|
+
Then add your `$OPENWEIGHTS_API_KEY` to the `.env`. You can create one via the [dashboard](https://ktf8znsjvlhidw-8124.proxy.runpod.net/).
|
|
9
|
+
|
|
10
|
+
# Quickstart
|
|
11
|
+
```python
|
|
12
|
+
from openweights import OpenWeights
|
|
13
|
+
client = OpenWeights()
|
|
14
|
+
|
|
15
|
+
with open('tests/preference_dataset.jsonl', 'rb') as file:
|
|
16
|
+
file = client.files.create(file, purpose="preference")
|
|
17
|
+
|
|
18
|
+
job = client.fine_tuning.create(
|
|
19
|
+
model='unsloth/llama-3-8b-Instruct',
|
|
20
|
+
training_file=file['id'],
|
|
21
|
+
loss='dpo'
|
|
22
|
+
)
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
# Client-side usage:
|
|
26
|
+
|
|
27
|
+
## Create a finetuning job
|
|
28
|
+
|
|
29
|
+
```python
|
|
30
|
+
from openweights import OpenWeights
|
|
31
|
+
from dotenv import load_dotenv
|
|
32
|
+
|
|
33
|
+
load_dotenv()
|
|
34
|
+
client = OpenWeights()
|
|
35
|
+
|
|
36
|
+
with open('tests/sft_dataset.jsonl', 'rb') as file:
|
|
37
|
+
file = client.files.create(file, purpose="conversations")
|
|
38
|
+
|
|
39
|
+
job = client.fine_tuning.create(
|
|
40
|
+
model='unsloth/llama-3-8b-Instruct',
|
|
41
|
+
training_file=file['id'],
|
|
42
|
+
requires_vram_gb=48,
|
|
43
|
+
loss='sft',
|
|
44
|
+
epochs=1
|
|
45
|
+
)
|
|
46
|
+
```
|
|
47
|
+
The `job_id` is based on the params hash, which means that if you submit the same job many times, it will only run once. If you resubmit a failed or canceled job, it will reset the job status to `pending`.
|
|
48
|
+
|
|
49
|
+
More infos: [Fine-tuning Options](docs/finetuning.md)
|
|
50
|
+
|
|
51
|
+
## Do batch inference
|
|
52
|
+
```python
|
|
53
|
+
|
|
54
|
+
file = client.files.create(
|
|
55
|
+
file=open("mydata.jsonl", "rb"),
|
|
56
|
+
purpose="conversations"
|
|
57
|
+
)
|
|
58
|
+
|
|
59
|
+
job = client.inference.create(
|
|
60
|
+
model=model,
|
|
61
|
+
input_file_id=file['id'],
|
|
62
|
+
max_tokens=1000,
|
|
63
|
+
temperature=1,
|
|
64
|
+
min_tokens=600,
|
|
65
|
+
)
|
|
66
|
+
print(job)
|
|
67
|
+
|
|
68
|
+
job = client.jobs.retrieve(job['id'])
|
|
69
|
+
```
|
|
70
|
+
Wait until job is finished, then get the output:
|
|
71
|
+
|
|
72
|
+
```py
|
|
73
|
+
output_file_id = job['outputs']['file']
|
|
74
|
+
output = client.files.content(output_file_id).decode('utf-8')
|
|
75
|
+
print(output)
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
## Custom jobs
|
|
79
|
+
Maybe you'd like to use autoscaling with queues for workloads that are not currently supported. You can start a pod that is set up like a worker but doesn't start `openweights/worker/main.py` by running:
|
|
80
|
+
```sh
|
|
81
|
+
python openweights/cluster/start_runpod.py A6000 finetuning --dev_mode=true
|
|
82
|
+
```
|
|
83
|
+
Then develop your script and finally create a `CustomJob` like in this [example](example/custom_job).
|
|
84
|
+
|
|
85
|
+
## Deploy a model as a temporary Openai-like API
|
|
86
|
+
|
|
87
|
+
You can deploy models as openai-like APIs in one of the following ways (sorted from highest to lowest level of abstraction)
|
|
88
|
+
- create chat completions via `ow.chat.completions.sync_create` or `.async_create` - this will deploy models when needed. This queues to-be-deployed models for 5 seconds and then deploys them via `ow.multi_deploy`. This client is optimized to not overload the vllm server it is talking to and caches requests on disk when a `seed` parameter is given.
|
|
89
|
+
- pass a list of models to deploy to `ow.multi_deploy` - this takes a list of models or lora adapters, groups them by `base_model`, and deploys all lora adapters of the same base model on one API to save runpod resources. Calls `ow.deploy` for each single deployment job. [Example](example/multi_lora_deploy.py)
|
|
90
|
+
- `ow.deploy` - takes a single model and optionally a list of lora adapters, then creates a job of type `api`. Returns a `openweights.client.temporary_api.TemporaryAPI` object. [Example](example/gradio_ui_with_temporary_api.py)
|
|
91
|
+
|
|
92
|
+
API jobs can never complete, they stop either because they are canceled or failed. API jobs have a timeout 15 minutes in the future when they are being created, and while a `TemporaryAPI` is alive (after `api.up()` and before `api.down()` has been called), it resets the timeout every minute. This ensures that an API is alive while the process that created it is running, at that it will automatically shut down later - but not immediately so that during debugging you don't always have to wait for deployment.
|
|
93
|
+
|
|
94
|
+
|
|
95
|
+
## Using `client.deploy(model)`
|
|
96
|
+
```py
|
|
97
|
+
from openweights import OpenWeights
|
|
98
|
+
|
|
99
|
+
client = OpenWeights()
|
|
100
|
+
|
|
101
|
+
model = 'unsloth/llama-3-8b-Instruct'
|
|
102
|
+
with client.deploy(model) as openai:
|
|
103
|
+
completion = openai.chat.completions.create(
|
|
104
|
+
model=model,
|
|
105
|
+
messages=[{"role": "user", "content": "is 9.11 > 9.9?"}]
|
|
106
|
+
)
|
|
107
|
+
print(completion.choices[0].message)
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
More examples:
|
|
111
|
+
- do a [hyperparameter sweep](example/hparams_sweep.py) and [visualize the results](example/analyze_hparam_sweep.ipynb)
|
|
112
|
+
- [download artifacts](example/download.py) from a job and plot training
|
|
113
|
+
- and [more](example/)
|
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
# Fine-tuning Options
|
|
2
|
+
|
|
3
|
+
OpenWeights supports several fine-tuning approaches for language models, all implemented using the Unsloth library for efficient training.
|
|
4
|
+
|
|
5
|
+
## Supported Training Methods
|
|
6
|
+
|
|
7
|
+
### 1. Supervised Fine-tuning (SFT)
|
|
8
|
+
Standard supervised fine-tuning using conversation data. This is the most basic form of fine-tuning where the model learns to generate responses based on conversation history.
|
|
9
|
+
|
|
10
|
+
```python
|
|
11
|
+
from openweights import OpenWeights
|
|
12
|
+
client = OpenWeights()
|
|
13
|
+
|
|
14
|
+
# Upload a conversations dataset
|
|
15
|
+
with open('conversations.jsonl', 'rb') as file:
|
|
16
|
+
file = client.files.create(file, purpose="conversations")
|
|
17
|
+
|
|
18
|
+
# Start SFT training
|
|
19
|
+
job = client.fine_tuning.create(
|
|
20
|
+
model='unsloth/llama-2-7b-chat',
|
|
21
|
+
training_file=file['id'],
|
|
22
|
+
loss='sft',
|
|
23
|
+
epochs=1,
|
|
24
|
+
learning_rate=2e-5
|
|
25
|
+
)
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
The conversations dataset should be in JSONL format with each line containing a "messages" field:
|
|
29
|
+
```json
|
|
30
|
+
{"messages": [
|
|
31
|
+
{"role": "system", "content": "You are a helpful assistant."},
|
|
32
|
+
{"role": "user", "content": "What is machine learning?"},
|
|
33
|
+
{"role": "assistant", "content": "Machine learning is a branch of artificial intelligence..."}
|
|
34
|
+
]}
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
### 2. Direct Preference Optimization (DPO)
|
|
38
|
+
DPO is a method for fine-tuning language models from preference data without using reward modeling. It directly optimizes the model to prefer chosen responses over rejected ones.
|
|
39
|
+
|
|
40
|
+
```python
|
|
41
|
+
# Upload a preference dataset
|
|
42
|
+
with open('preferences.jsonl', 'rb') as file:
|
|
43
|
+
file = client.files.create(file, purpose="preference")
|
|
44
|
+
|
|
45
|
+
# Start DPO training
|
|
46
|
+
job = client.fine_tuning.create(
|
|
47
|
+
model='unsloth/llama-2-7b-chat',
|
|
48
|
+
training_file=file['id'],
|
|
49
|
+
loss='dpo',
|
|
50
|
+
epochs=1,
|
|
51
|
+
learning_rate=1e-5,
|
|
52
|
+
beta=0.1 # Controls the strength of the preference optimization
|
|
53
|
+
)
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
### 3. Offline Rejection Preference Optimization (ORPO)
|
|
57
|
+
ORPO is similar to DPO but uses a different loss function that has been shown to be more stable in some cases.
|
|
58
|
+
|
|
59
|
+
```python
|
|
60
|
+
# Start ORPO training
|
|
61
|
+
job = client.fine_tuning.create(
|
|
62
|
+
model='unsloth/llama-2-7b-chat',
|
|
63
|
+
training_file=file['id'],
|
|
64
|
+
loss='orpo',
|
|
65
|
+
epochs=1,
|
|
66
|
+
learning_rate=1e-5,
|
|
67
|
+
beta=0.1
|
|
68
|
+
)
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
The preference dataset format for both DPO and ORPO should be:
|
|
72
|
+
```json
|
|
73
|
+
{
|
|
74
|
+
"prompt": [
|
|
75
|
+
{"role": "system", "content": "You are a helpful assistant."},
|
|
76
|
+
{"role": "user", "content": "What is the capital of France?"}
|
|
77
|
+
],
|
|
78
|
+
"chosen": [
|
|
79
|
+
{"role": "assistant", "content": "The capital of France is Paris."}
|
|
80
|
+
],
|
|
81
|
+
"rejected": [
|
|
82
|
+
{"role": "assistant", "content": "I think it's London, but I'm not sure."}
|
|
83
|
+
]
|
|
84
|
+
}
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
## Common Training Parameters
|
|
88
|
+
|
|
89
|
+
All training methods support the following parameters:
|
|
90
|
+
|
|
91
|
+
- `model`: The base model to fine-tune (string)
|
|
92
|
+
- `training_file`: File ID of the training dataset (string)
|
|
93
|
+
- `test_file`: Optional file ID of the test dataset (string)
|
|
94
|
+
- `epochs`: Number of training epochs (int)
|
|
95
|
+
- `learning_rate`: Learning rate or string expression (float or string)
|
|
96
|
+
- `max_seq_length`: Maximum sequence length for training (int, default=2048)
|
|
97
|
+
- `per_device_train_batch_size`: Training batch size per device (int, default=2)
|
|
98
|
+
- `gradient_accumulation_steps`: Number of gradient accumulation steps (int, default=8)
|
|
99
|
+
- `warmup_steps`: Number of warmup steps (int, default=5)
|
|
100
|
+
|
|
101
|
+
### LoRA Parameters
|
|
102
|
+
|
|
103
|
+
All training methods use LoRA (Low-Rank Adaptation) by default with these configurable parameters:
|
|
104
|
+
|
|
105
|
+
- `r`: LoRA attention dimension (int, default=512)
|
|
106
|
+
- `lora_alpha`: LoRA alpha parameter (int, default=16)
|
|
107
|
+
- `lora_dropout`: LoRA dropout rate (float, default=0.0)
|
|
108
|
+
- `target_modules`: List of modules to apply LoRA to (list of strings)
|
|
109
|
+
- `merge_before_push`: Whether to merge LoRA weights into base model before pushing (bool, default=True)
|
|
110
|
+
|
|
111
|
+
## Monitoring Training
|
|
112
|
+
|
|
113
|
+
You can monitor training progress through the logged metrics:
|
|
114
|
+
|
|
115
|
+
```python
|
|
116
|
+
# Get training events
|
|
117
|
+
events = client.events.list(job_id=job['id'])
|
|
118
|
+
|
|
119
|
+
# Get the latest values for specific metrics
|
|
120
|
+
latest = client.events.latest(['loss', 'learning_rate'], job_id=job['id'])
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
## Using the Fine-tuned Model
|
|
124
|
+
|
|
125
|
+
After training completes, you can use the model for inference:
|
|
126
|
+
|
|
127
|
+
```python
|
|
128
|
+
# For merged models (merge_before_push=True)
|
|
129
|
+
with client.deploy(job['outputs']['model']) as openai:
|
|
130
|
+
completion = openai.chat.completions.create(
|
|
131
|
+
model=job['outputs']['model'],
|
|
132
|
+
messages=[{"role": "user", "content": "Hello!"}]
|
|
133
|
+
)
|
|
134
|
+
|
|
135
|
+
# For LoRA adapters (merge_before_push=False)
|
|
136
|
+
with client.deploy(
|
|
137
|
+
model=job['params']['model'],
|
|
138
|
+
lora_adapters=[job['outputs']['model']]
|
|
139
|
+
) as openai:
|
|
140
|
+
completion = openai.chat.completions.create(
|
|
141
|
+
model=job['params']['model'],
|
|
142
|
+
messages=[{"role": "user", "content": "Hello!"}]
|
|
143
|
+
)
|
|
144
|
+
```
|