Skip to content

Commit b08da7f

Browse files
committed
Merge branch 'main' into coder
2 parents 932908f + cf2afd7 commit b08da7f

File tree

20 files changed

+469
-234
lines changed

20 files changed

+469
-234
lines changed

.github/workflows/docs.yml

Lines changed: 81 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ on:
1010
jobs:
1111
build-docs:
1212
name: Build Documentation
13-
runs-on: ubuntu-latest
13+
runs-on: linux.g5.4xlarge.nvidia.gpu
1414
timeout-minutes: 30
1515
steps:
1616
- name: Checkout
@@ -24,7 +24,7 @@ jobs:
2424
miniconda-version: "latest"
2525
activate-environment: test
2626
python-version: '3.10'
27-
auto-activate-base: false
27+
auto-activate: false
2828
- name: Verify conda environment
2929
shell: bash -l {0}
3030
run: |
@@ -36,7 +36,7 @@ jobs:
3636
run: python -m pip install --upgrade pip
3737
- name: Install pytorch
3838
shell: bash -l {0}
39-
run: python -m pip install torch==2.9.0.dev20250826 --extra-index-url https://download.pytorch.org/whl/nightly/cpu
39+
run: python -m pip install torch==2.9.0 --index-url https://download.pytorch.org/whl/test/cu130
4040
- name: Install monarch
4141
shell: bash -l {0}
4242
run: python -m pip install monarch-no-torch==0.1.0.dev20250826 --find-links assets/ci
@@ -51,61 +51,90 @@ jobs:
5151
- name: Build docs
5252
shell: bash -l {0}
5353
working-directory: docs
54-
run: make html --keep-going SPHINXOPTS='-W'
54+
run: |
55+
set +e # Don't exit on error
56+
make html SPHINXOPTS="-WT --keep-going" || echo "Build completed with warnings/errors"
57+
set -e # Re-enable exit on error for subsequent commands
5558
- name: Upload docs artifact
5659
uses: actions/upload-artifact@v4
5760
with:
5861
name: docs
5962
path: docs/build/html/
6063

61-
# doc-preview:
62-
# runs-on: [ubuntu-latest]
63-
# needs: build-docs
64-
# if: ${{ github.event_name == 'pull_request' }}
65-
# steps:
66-
# - name: Checkout
67-
# uses: actions/checkout@v4
68-
# - name: Download artifact
69-
# uses: actions/download-artifact@v4
70-
# with:
71-
# name: docs
72-
# path: docs
73-
# - name: Add noindex to preview docs
74-
# run: |
75-
# echo "Adding noindex meta tag to prevent search engine indexing of preview docs"
76-
# find docs -name "*.html" -print0 | xargs -0 sed -i 's/<head>/<head>\n <meta name="robots" content="noindex">/'
77-
# - name: Upload docs preview
78-
# uses: seemethere/upload-artifact-s3@v5
79-
# if: ${{ github.event_name == 'pull_request' }}
80-
# with:
81-
# retention-days: 14
82-
# s3-bucket: doc-previews
83-
# if-no-files-found: error
84-
# path: docs
85-
# s3-prefix: meta-pytorch/forge/${{ github.event.pull_request.number }}
64+
doc-preview:
65+
runs-on: linux.large
66+
needs: build-docs
67+
if: ${{ github.event_name == 'pull_request' }}
68+
steps:
69+
- name: Checkout
70+
uses: actions/checkout@v4
71+
- name: Download artifact
72+
uses: actions/download-artifact@v4
73+
with:
74+
name: docs
75+
path: docs
76+
- name: Add noindex to preview docs
77+
run: |
78+
echo "Adding noindex meta tag to prevent search engine indexing of preview docs"
79+
find docs -name "*.html" -print0 | xargs -0 sed -i 's/<head>/<head>\n <meta name="robots" content="noindex">/'
80+
- name: Upload docs preview
81+
uses: seemethere/upload-artifact-s3@v5
82+
if: ${{ github.event_name == 'pull_request' }}
83+
with:
84+
retention-days: 14
85+
s3-bucket: doc-previews
86+
if-no-files-found: error
87+
path: docs
88+
s3-prefix: meta-pytorch/forge/${{ github.event.pull_request.number }}
89+
90+
upload:
91+
runs-on: ubuntu-latest
92+
permissions:
93+
# Grant write permission here so that the doc can be pushed to gh-pages branch
94+
contents: write
95+
needs: build-docs
96+
if: github.repository == 'meta-pytorch/forge' && github.event_name == 'push' && (github.ref == 'refs/heads/main' || startsWith(github.ref, 'refs/tags/v') || github.event_name == 'workflow_dispatch')
97+
steps:
98+
- name: Checkout
99+
uses: actions/checkout@v4
100+
with:
101+
ref: gh-pages
102+
persist-credentials: true
103+
- name: Download artifact
104+
uses: actions/download-artifact@v4
105+
with:
106+
name: docs
107+
path: docs
108+
#- name: Add no-index tag
109+
# run: |
110+
# REF_NAME=$(echo "${{ github.ref }}")
111+
# echo "Ref name: ${REF_NAME}"
112+
# if [[ "${{ github.ref }}" == 'refs/heads/main' ]]; then
113+
# find docs -name "*.html" -print0 | xargs -0 sed -i '/<head>/a \ \ <meta name="robots" content="noindex">';
114+
# fi
115+
- name: Move and commit changes
116+
run: |
117+
set -euo pipefail
118+
# Get github.ref for the output doc folder. By default "main"
119+
# If matches a tag like refs/tags/v1.12.0-rc3 or
120+
# refs/tags/v1.12.0 convert to 1.12
121+
GITHUB_REF=${{ github.ref }}
86122
87-
deploy-docs:
88-
needs: build-docs
89-
if: github.ref == 'refs/heads/main'
90-
permissions:
91-
pages: write
92-
id-token: write
93-
environment:
94-
name: github-pages
95-
url: ${{ steps.deployment.outputs.page_url }}
96-
runs-on: ubuntu-latest
97-
steps:
98-
- name: Download build artifact
99-
uses: actions/download-artifact@v4
100-
with:
101-
name: docs
102-
path: .
123+
# Convert refs/tags/v1.12.0rc3 into 1.12.
124+
# Adopted from https://github.com/pytorch/pytorch/blob/main/.github/workflows/_docs.yml#L150C11-L155C13
125+
if [[ "${GITHUB_REF}" =~ ^refs/tags/v([0-9]+\.[0-9]+)\.* ]]; then
126+
TARGET_FOLDER="${BASH_REMATCH[1]}"
127+
else
128+
TARGET_FOLDER="main"
129+
fi
130+
echo "Target Folder: ${TARGET_FOLDER}"
103131
104-
- name: Upload Pages artifact
105-
uses: actions/upload-pages-artifact@v3
106-
with:
107-
path: .
132+
mkdir -p "${TARGET_FOLDER}"
133+
rm -rf "${TARGET_FOLDER}"/*
134+
mv docs/* "${TARGET_FOLDER}"
108135
109-
- name: Deploy to GitHub Pages
110-
id: deployment
111-
uses: actions/deploy-pages@v4
136+
git config user.name 'pytorchbot'
137+
git config user.email '[email protected]'
138+
git add "${TARGET_FOLDER}" || true
139+
git commit -m "auto-generating sphinx docs" || true
140+
git push -f

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -153,6 +153,7 @@ docs/source/generated_examples/
153153
docs/source/gen_modules/
154154
docs/source/generated/
155155
docs/source/sg_execution_times.rst
156+
docs/source/tutorials
156157
# pytorch-sphinx-theme gets installed here
157158
docs/src
158159

apps/grpo/main.py

Lines changed: 8 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -26,20 +26,13 @@
2626
from forge.actors.trainer import RLTrainer
2727
from forge.cli.config import parse
2828
from forge.controller.actor import ForgeActor
29-
from forge.controller.launcher import JOB_NAME_KEY, LAUNCHER_KEY
3029
from forge.controller.provisioner import init_provisioner, shutdown
3130
from forge.data.rewards import MathReward, ThinkingReward
3231
from forge.observability.metric_actors import get_or_create_metric_logger
3332
from forge.observability.metrics import record_metric, Reduce
3433
from forge.observability.perf_tracker import Tracer
3534

36-
from forge.types import (
37-
Launcher,
38-
LauncherConfig,
39-
ProcessConfig,
40-
ProvisionerConfig,
41-
ServiceConfig,
42-
)
35+
from forge.types import LauncherConfig, ProvisionerConfig
4336
from forge.util.ops import compute_logprobs
4437
from monarch.actor import endpoint
4538
from omegaconf import DictConfig
@@ -320,25 +313,20 @@ async def main(cfg: DictConfig):
320313
max_req_tokens = cfg.max_req_tokens
321314
max_res_tokens = cfg.max_res_tokens
322315

323-
# init provisioner
324-
await init_provisioner(
325-
ProvisionerConfig(
326-
launcher_config=LauncherConfig(
327-
launcher=Launcher(cfg.get(LAUNCHER_KEY, Launcher.SLURM.value)),
328-
job_name=cfg.get(JOB_NAME_KEY, None),
329-
services={k: ServiceConfig(**v) for k, v in cfg.services.items()},
330-
actors={k: ProcessConfig(**v) for k, v in cfg.actors.items()},
316+
# ---- Global setups ---- #
317+
if cfg.get("provisioner", None) is not None:
318+
await init_provisioner(
319+
ProvisionerConfig(
320+
launcher_config=LauncherConfig(**cfg.provisioner.launcher)
331321
)
332322
)
333-
)
334-
335-
# initialize before spawning services
336323
metric_logging_cfg = cfg.get("metric_logging", {"console": {"log_per_rank": False}})
337324
mlogger = await get_or_create_metric_logger()
338325
await mlogger.init_backends.call_one(metric_logging_cfg)
326+
await ts.initialize(strategy=ts.ControllerStorageVolumes())
339327

340328
# ---- Setup services ---- #
341-
await ts.initialize(strategy=ts.ControllerStorageVolumes())
329+
342330
(
343331
dataloader,
344332
policy,

apps/grpo/qwen3_32b.yaml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,9 @@ max_res_tokens: 512
1010
model: "Qwen/Qwen3-32B"
1111
off_by_n: 1 # Off by one by default
1212

13+
provisioner:
14+
launcher: slurm
15+
1316
# Main loop configuration
1417
rollout_threads: 1 # Recommended to set equal to policy.num_replicas
1518

docs/requirements.txt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
sphinx==7.2.6
2-
-e git+https://github.com/pytorch/pytorch_sphinx_theme.git@pytorch_sphinx_theme2#egg=pytorch_sphinx_theme2
2+
pytorch-sphinx-theme2==0.1.0
33
docutils>=0.18.1,<0.21
44
sphinx-design==0.6.1
55
sphinxcontrib-mermaid==1.0.0
6+
sphinx-gallery==0.19.0
67
myst-parser #==0.18.1 # if want to contribute in markdown
78
sphinx-sitemap==2.7.1

docs/source/conf.py

Lines changed: 57 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -17,10 +17,33 @@
1717
import pytorch_sphinx_theme2
1818

1919
# Add the source directory to Python path so modules can be imported
20-
sys.path.insert(0, os.path.abspath("../../src"))
20+
sys.path.insert(0, os.path.abspath("../../src/forge"))
21+
22+
23+
# Determine the version path for deployment
24+
def get_version_path():
25+
"""Get the version path based on environment variables or git context."""
26+
# Check if we're in CI/CD and get the target folder
27+
github_ref = os.environ.get("GITHUB_REF", "")
28+
29+
# Convert refs/tags/v1.12.0rc3 into 1.12.
30+
# Matches the logic in .github/workflows/docs.yml
31+
if github_ref.startswith("refs/tags/v"):
32+
import re
33+
34+
match = re.match(r"^refs/tags/v([0-9]+\.[0-9]+)\..*", github_ref)
35+
if match:
36+
return match.group(1) + "/"
37+
38+
# Default to main for main branch or local development
39+
return "main/"
40+
41+
42+
# Set base URL based on deployment context
43+
version_path = get_version_path()
2144

2245
project = "torchforge"
23-
copyright = "2025, PyTorch Contributors"
46+
copyright = ""
2447
author = "PyTorch Contributors"
2548
release = "0.1"
2649

@@ -38,9 +61,12 @@
3861
"sphinx.ext.napoleon",
3962
"sphinx.ext.intersphinx",
4063
"sphinx.ext.viewcode",
64+
"sphinx_gallery.gen_gallery",
4165
]
4266

43-
html_baseurl = "https://meta-pytorch.org/forge/" # needed for sphinx-sitemap
67+
html_baseurl = (
68+
f"https://meta-pytorch.org/forge/{version_path}" # needed for sphinx-sitemap
69+
)
4470
sitemap_locales = [None]
4571
sitemap_excludes = [
4672
"search.html",
@@ -52,7 +78,7 @@
5278
"_templates",
5379
os.path.join(os.path.dirname(pytorch_sphinx_theme2.__file__), "templates"),
5480
]
55-
exclude_patterns = []
81+
exclude_patterns = ["tutorials/index.rst"]
5682

5783
sys.path.insert(0, os.path.abspath("."))
5884
sys.path.insert(0, os.path.abspath("../../src"))
@@ -90,7 +116,7 @@
90116
},
91117
{
92118
"name": "PyPi",
93-
"url": "https://pypi.org/project/forge/",
119+
"url": "https://pypi.org/project/torchforge/",
94120
"icon": "fa-brands fa-python",
95121
},
96122
],
@@ -109,9 +135,21 @@
109135
"github_user": "meta-pytorch",
110136
"github_repo": "forge",
111137
"feedback_url": "https://github.com/meta-pytorch/forge",
138+
"colab_branch": "gh-pages",
112139
"github_version": "main",
113140
"doc_path": "docs/source",
141+
"has_sphinx_gallery": True, # Enable tutorial call-to-action links
142+
}
143+
144+
# For tutorial repository configuration
145+
# Note: github_user and github_repo are combined in the template as "{{ github_user }}/{{ github_repo }}"
146+
# So we keep github_user = "meta-pytorch" and github_repo = "forge" already set above
147+
# and only need to ensure the branch settings are correct
148+
tutorial_repo_config = {
149+
"github_version": "main", # This maps to github_branch in the template
150+
"colab_branch": "gh-pages",
114151
}
152+
html_context.update(tutorial_repo_config)
115153

116154
myst_enable_extensions = [
117155
"colon_fence",
@@ -127,6 +165,17 @@
127165
"exclude-members": "__weakref__",
128166
}
129167

130-
# Autosummary settings
131-
autosummary_generate = True
132-
autosummary_imported_members = True
168+
169+
# -- Sphinx Gallery configuration -------------------------------------------
170+
sphinx_gallery_conf = {
171+
"examples_dirs": "tutorial_sources", # Path to examples directory
172+
"gallery_dirs": "tutorials", # Path to generate gallery
173+
"filename_pattern": ".*", # Include all files
174+
"download_all_examples": False,
175+
"first_notebook_cell": "%matplotlib inline",
176+
"plot_gallery": "True",
177+
"promote_jupyter_magic": True,
178+
"backreferences_dir": None,
179+
"write_computation_times": True,
180+
"show_signature": False,
181+
}
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
Tutorials
2+
=========
3+
4+
This gallery contains tutorials and examples to help you get started with Forge.
5+
Each tutorial demonstrates specific features and use cases with practical examples.

0 commit comments

Comments
 (0)