<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Viswaretas Kotra</title>
    <description>The latest articles on DEV Community by Viswaretas Kotra (@viswaretas_kotra).</description>
    <link>https://dev.to/viswaretas_kotra</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4172307%2F52f79e2f-4ce1-40f8-bb27-0a62c752e52c.png</url>
      <title>DEV Community: Viswaretas Kotra</title>
      <link>https://dev.to/viswaretas_kotra</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/viswaretas_kotra"/>
    <language>en</language>
    <item>
      <title>Nodus vs Google Cloud GPUs: which is cheaper for training?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Thu, 29 Oct 2026 23:12:35 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/nodus-vs-google-cloud-gpus-which-is-cheaper-for-training-3pg5</link>
      <guid>https://dev.to/viswaretas_kotra/nodus-vs-google-cloud-gpus-which-is-cheaper-for-training-3pg5</guid>
      <description>&lt;p&gt;Per GPU-hour, a Google Cloud on-demand H100 costs about four times the Nodus listed rate, and Google Spot VMs cost about two and a half times as much. Spot narrows the gap, but Compute Engine can reclaim those machines at any time and leaves checkpoint and restart logic to you. Nodus lists an NVIDIA H100 at $2.60/hr on its &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;, saves your state when interruptible capacity is reclaimed, and can route work through a connected GCP project so you spend Google credits before Nodus capacity.&lt;/p&gt;

&lt;p&gt;We build Nodus. Every Google Cloud fact below links to Google's own pricing page or docs, the arithmetic is shown, and one section covers where Google Cloud is the better choice.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do Google Cloud and Nodus GPU prices compare?
&lt;/h2&gt;

&lt;p&gt;Google Cloud prices accelerator-optimized VMs as a full machine: GPUs, vCPUs, memory and local SSD bundled together. The A3 High machine type gives you eight NVIDIA H100 GPUs, 208 vCPUs, 1,871 GB of memory and 6,000 GB of SSD. Nodus lists the GPU hour on its own, with CPU and memory priced separately on the same page.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;GPU&lt;/th&gt;
&lt;th&gt;Google Cloud on-demand&lt;/th&gt;
&lt;th&gt;Google Cloud Spot&lt;/th&gt;
&lt;th&gt;Nodus listed rate&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;8 x H100 SXM (A3 High)&lt;/td&gt;
&lt;td&gt;$88.49/hr ($11.06/GPU)&lt;/td&gt;
&lt;td&gt;$52.70/hr ($6.59/GPU)&lt;/td&gt;
&lt;td&gt;$20.80/hr ($2.60/GPU)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;8 x H100 SXM (A3 Mega)&lt;/td&gt;
&lt;td&gt;$93.40/hr ($11.68/GPU)&lt;/td&gt;
&lt;td&gt;$45.60/hr ($5.70/GPU)&lt;/td&gt;
&lt;td&gt;$20.80/hr ($2.60/GPU)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;8 x H200 SXM (A3 Ultra)&lt;/td&gt;
&lt;td&gt;$84.81/hr ($10.60/GPU)&lt;/td&gt;
&lt;td&gt;$50.87/hr ($6.36/GPU)&lt;/td&gt;
&lt;td&gt;$28.74/hr ($3.59/GPU)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;8 x A100 40 GB (A2 Standard)&lt;/td&gt;
&lt;td&gt;$29.39/hr ($3.67/GPU)&lt;/td&gt;
&lt;td&gt;$16.75/hr ($2.09/GPU)&lt;/td&gt;
&lt;td&gt;$7.23/hr ($0.904/GPU)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 29, 2026. Google Cloud rates from the &lt;a href="https://cloud.google.com/products/compute/pricing/accelerator-optimized" rel="noopener noreferrer"&gt;accelerator-optimized pricing page&lt;/a&gt; for us-central1 (Iowa). Nodus rates from the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fn96uigr5wvqkwtem7ncj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fn96uigr5wvqkwtem7ncj.png" alt="Per H100-hour: Google Cloud on-demand $11.06, Google Cloud Spot $6.59, Nodus $2.60." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;At list prices, Nodus is about 76% cheaper than Google Cloud on-demand and 61% cheaper than Spot per H100-hour.&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  What does the same training job cost on each?
&lt;/h2&gt;

&lt;p&gt;We priced the same 8 x H100 run for 10 hours, the worked example we use across our comparison posts.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform and capacity&lt;/th&gt;
&lt;th&gt;Hourly rate&lt;/th&gt;
&lt;th&gt;80 GPU-hours&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Google Cloud A3 High, on-demand&lt;/td&gt;
&lt;td&gt;$88.49/hr&lt;/td&gt;
&lt;td&gt;$884.90&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Google Cloud A3 High, Spot&lt;/td&gt;
&lt;td&gt;$52.70/hr&lt;/td&gt;
&lt;td&gt;$527.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Nodus&lt;/td&gt;
&lt;td&gt;$20.80/hr&lt;/td&gt;
&lt;td&gt;$208.00&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 29, 2026. Google Cloud: &lt;a href="https://cloud.google.com/products/compute/pricing/accelerator-optimized" rel="noopener noreferrer"&gt;accelerator-optimized pricing&lt;/a&gt;, us-central1. Nodus: &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;The Nodus run costs less than a quarter of the GCP on-demand price and about 39% of the Spot price for the same GPU-hours. One caveat keeps this fair: Google's price includes 208 vCPUs and 1,871 GB of memory, while the Nodus figure is the GPU line only. Nodus lists CPU and memory separately (4 vCPU with 16 GiB is $0.1054/hr), so a job that needs a large host adds to the Nodus side.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffhh8zc7fevi5ji2kpi8b.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffhh8zc7fevi5ji2kpi8b.png" alt="8 x H100 for 10 hours: Google Cloud on-demand $884.90, Google Cloud Spot $527.00, Nodus $208.00." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The same 80 H100-hours cost $677 less on Nodus than on Google Cloud on-demand.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Google Cloud's Spot rate looks closer, but the &lt;a href="https://cloud.google.com/compute/docs/instances/spot" rel="noopener noreferrer"&gt;Spot VM docs&lt;/a&gt; give a best-effort shutdown period of up to 30 seconds, and the run does not resume by itself. You write the checkpoint code, save to Cloud Storage and relaunch. On Nodus, an interruptible run whose machine is reclaimed gets a replacement with its &lt;code&gt;/nodus/state&lt;/code&gt; directory restored, so you save to that path and Nodus handles the restart. That pattern is covered in &lt;a href="https://www.nodus-compute.ai/blog/resume-training-after-spot-preemption/" rel="noopener noreferrer"&gt;How do you make spot GPU training survive preemption?&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;
  
  
  Can you use both Google Cloud and Nodus?
&lt;/h2&gt;

&lt;p&gt;Yes, and if you hold Google credits it is often the cheapest setup. Nodus can connect a GCP project read-only to show its instances and spend, and, as a separate Beta step, run your single-node Jobs in that project first so they spend your Google Cloud credits before Nodus capacity.&lt;/p&gt;

&lt;p&gt;The read-only connection is an OAuth grant limited to read-only scopes (&lt;code&gt;compute.readonly&lt;/code&gt;, &lt;code&gt;bigquery.readonly&lt;/code&gt; and &lt;code&gt;cloud-platform.read-only&lt;/code&gt;). Viewing is free and starts no machines. Running work is an explicit upgrade with a monthly credit limit. Nodus then creates its own network and a service account with roles that can only touch machines it named, and launches in us-central1, us-east1, us-east4 or us-west1.&lt;/p&gt;

&lt;p&gt;When the project is full or out of credit, the default is to continue on Nodus capacity at Nodus rates. You can instead make Jobs wait for your approval or wait for your account. Once the owner setup script has finished, the CLI step is one line, copied from the docs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;nodus cloud connect gcp gcp-lab &lt;span class="nt"&gt;--credit-limit&lt;/span&gt; 500 &lt;span class="nt"&gt;--gcp-project&lt;/span&gt; lab-ml-prod
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each attempt on the job page shows whether it ran in your project or on Nodus capacity. Multi-node runs and Sandboxes use Nodus capacity, and the console shows the routing terms before you enable it. The full steps and permissions are in &lt;a href="https://www.nodus-compute.ai/docs/guides/pools/cloud-accounts/" rel="noopener noreferrer"&gt;Connect your cloud accounts&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Is Google Cloud Spot stable enough for training?
&lt;/h2&gt;

&lt;p&gt;Spot is stable enough only if your code checkpoints and restarts. Google's &lt;a href="https://cloud.google.com/compute/docs/instances/spot" rel="noopener noreferrer"&gt;Spot VM overview&lt;/a&gt; says Compute Engine can preempt Spot VMs at any time, recommends them for fault-tolerant workloads, and gives a best-effort shutdown period of up to 30 seconds. Compute Engine does not manage your checkpoint.&lt;/p&gt;

&lt;p&gt;For a 10-hour fine-tune, one lost run without a checkpoint is 10 hours of GPU time and $527 of Spot spend wasted. The safe pattern is to save model, optimizer and step every N minutes and again when you receive the termination signal. On Nodus, you write to &lt;code&gt;/nodus/state&lt;/code&gt; and Nodus restores it on a replacement attempt. On GCP, you write to Cloud Storage and write the code that detects and reloads the checkpoint.&lt;/p&gt;

&lt;p&gt;Spot discounts also do not combine with commitments. Google's &lt;a href="https://cloud.google.com/compute/gpus-pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt; says Spot prices are final: "Spot prices apply to all Spot VMs (and preemptible VMs), so Spot VMs (and preemptible VMs) cannot receive CUDs or SUDs."&lt;/p&gt;

&lt;h2&gt;
  
  
  Where is Google Cloud the better choice?
&lt;/h2&gt;

&lt;p&gt;Google Cloud is the better choice in four situations, and we would tell a friend to stay in each of them.&lt;/p&gt;

&lt;h3&gt;
  
  
  You already have Google credits or commitments
&lt;/h3&gt;

&lt;p&gt;Startup credits, enterprise agreements and committed-use discounts change the math. On Google's pricing page, a one-year resource commitment on A3 High is $61.38/hr and a three-year commitment is $38.86/hr, or $4.86 per GPU-hour. That is still above the Nodus rate but locked in for three years. Credits are also the case where using both wins: connect the project and Nodus spends them first.&lt;/p&gt;

&lt;h3&gt;
  
  
  Your data lives in Google Cloud Storage
&lt;/h3&gt;

&lt;p&gt;Training next to your data avoids moving it. Sending datasets out of Google Cloud incurs internet egress charges (&lt;a href="https://cloud.google.com/vpc/network-pricing" rel="noopener noreferrer"&gt;network pricing&lt;/a&gt;), which matter if you retrain often on large data.&lt;/p&gt;

&lt;h3&gt;
  
  
  You want TPUs
&lt;/h3&gt;

&lt;p&gt;TPUs are only available on Google Cloud, and Nodus does not offer them. If your stack is built on JAX and TPUs, this comparison does not apply.&lt;/p&gt;

&lt;h3&gt;
  
  
  Compliance requires Google Cloud
&lt;/h3&gt;

&lt;p&gt;Some teams must keep data and compute inside a specific cloud for contractual or regulatory reasons. Then the per-hour price is secondary.&lt;/p&gt;

&lt;p&gt;If none of these apply, Nodus is the cheaper choice for GPU training and handles recovery when interruptible capacity is reclaimed. For comparisons with other providers, see &lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-lambda/" rel="noopener noreferrer"&gt;Nodus vs Lambda&lt;/a&gt; and &lt;a href="https://www.nodus-compute.ai/blog/runpod-alternatives-2026/" rel="noopener noreferrer"&gt;RunPod alternatives for AI training&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do you move a training job from Google Cloud to Nodus?
&lt;/h2&gt;

&lt;p&gt;For a simple PyTorch job, install the CLI, add a budget and run the same command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
nodus login

&lt;span class="c"&gt;# 8 x H100, a $40 spending cap, detached&lt;/span&gt;
nodus run &lt;span class="nt"&gt;--gpu&lt;/span&gt; H100:8 &lt;span class="nt"&gt;--max-cost&lt;/span&gt; 40 &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="nt"&gt;--&lt;/span&gt; torchrun train.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;--gpu H100:8&lt;/code&gt; form and the &lt;code&gt;--max-cost&lt;/code&gt; cap come from the &lt;a href="https://www.nodus-compute.ai/docs/reference/cli/nodus_run/" rel="noopener noreferrer"&gt;&lt;code&gt;nodus run&lt;/code&gt; reference&lt;/a&gt;; add &lt;code&gt;--interruptible&lt;/code&gt; to allow interruptible capacity.&lt;/p&gt;

&lt;p&gt;Checkpoint code that saves to a local directory works on Nodus if you point it at &lt;code&gt;/nodus/state&lt;/code&gt;. Nodus snapshots that directory periodically and restores it on a replacement attempt. The full pattern is in the &lt;a href="https://www.nodus-compute.ai/docs/guides/checkpoints/" rel="noopener noreferrer"&gt;checkpoint guide&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;If you run Vertex AI custom training today, keep your training script and replace the Cloud Storage checkpoint path with &lt;code&gt;/nodus/state&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Does work in my connected GCP project show up on my Google bill?
&lt;/h3&gt;

&lt;p&gt;Yes. Machines Nodus starts in your project are billed by Google to that project, against its credits, and Nodus tracks them against the monthly credit limit you set. That limit is spent at Nodus's list estimate, which can differ from Google's bill, so the docs advise setting it a little below the credit you hold.&lt;/p&gt;

&lt;h3&gt;
  
  
  Which regions does Nodus use in a connected GCP project?
&lt;/h3&gt;

&lt;p&gt;Nodus launches in us-central1, us-east1, us-east4 and us-west1. If a GPU quota is used up, it skips that GPU model in that region for an hour and runs the work elsewhere.&lt;/p&gt;

&lt;h3&gt;
  
  
  What happens if my GCP Spot VM is preempted mid-training?
&lt;/h3&gt;

&lt;p&gt;On Google Cloud alone, the VM shuts down after a shutdown period of up to 30 seconds. You restart it or launch a new one and reload your checkpoint from Cloud Storage yourself. On Nodus with interruptible capacity, the platform launches a replacement machine and restores your &lt;code&gt;/nodus/state&lt;/code&gt; directory automatically.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is Google Cloud's DWS Flex-start cheaper than Nodus?
&lt;/h3&gt;

&lt;p&gt;DWS Flex-start lists an A3 High at $38.32/hr ($4.79/GPU-hr), lower than on-demand but still above the Nodus rate of $2.60/GPU-hr. Flex-start works through resize requests that wait for capacity rather than starting at once (&lt;a href="https://cloud.google.com/compute/docs/instance-groups/about-resize-requests-mig" rel="noopener noreferrer"&gt;Flex-start docs&lt;/a&gt;).&lt;/p&gt;

&lt;h3&gt;
  
  
  How do Nodus and Vertex AI compare for managed training?
&lt;/h3&gt;

&lt;p&gt;Vertex AI keeps training inside Google Cloud, next to your data and IAM. Nodus restores &lt;code&gt;/nodus/state&lt;/code&gt; on a replacement attempt for you, and can use your connected GCP project as its first place to run.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-google-cloud-gpus/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>gcp</category>
      <category>gpu</category>
      <category>machinelearning</category>
      <category>mlops</category>
    </item>
    <item>
      <title>Can you use serverless GPUs for long training runs?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Thu, 29 Oct 2026 18:17:21 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/can-you-use-serverless-gpus-for-long-training-runs-1ka</link>
      <guid>https://dev.to/viswaretas_kotra/can-you-use-serverless-gpus-for-long-training-runs-1ka</guid>
      <description>&lt;p&gt;You can, up to a point: Modal caps a single function execution at 24 hours, RunPod Serverless caps a job at 7 days, and on both a preempted or failed run starts over unless your own code saved a checkpoint. Nodus runs long training as a Job or TrainingJob with an optional time limit, saves your state directory automatically, and resumes from the latest checkpoint when capacity is reclaimed. Our rule: serverless is fine for training that finishes well inside one execution and is cheap to repeat; past that, use a platform that owns the checkpoint.&lt;/p&gt;

&lt;h2&gt;
  
  
  How long can a serverless GPU function run?
&lt;/h2&gt;

&lt;p&gt;Each serverless platform puts a hard ceiling on one execution, and the defaults are much lower than the maximums.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;Default limit per execution&lt;/th&gt;
&lt;th&gt;Maximum&lt;/th&gt;
&lt;th&gt;What happens at the limit&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Modal&lt;/td&gt;
&lt;td&gt;5 minutes&lt;/td&gt;
&lt;td&gt;24 hours&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;FunctionTimeoutError&lt;/code&gt; after any retries&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Serverless&lt;/td&gt;
&lt;td&gt;10 minutes&lt;/td&gt;
&lt;td&gt;7 days&lt;/td&gt;
&lt;td&gt;The job fails and the worker stops&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Nodus Job or TrainingJob&lt;/td&gt;
&lt;td&gt;No limit unless you set &lt;code&gt;timeout&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;You can raise or remove it on a running Job&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;DeadlineExceeded&lt;/code&gt;; time spent suspended does not count&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Sources: &lt;a href="https://modal.com/docs/guide/timeouts" rel="noopener noreferrer"&gt;Modal timeouts&lt;/a&gt;, &lt;a href="https://docs.runpod.io/serverless/endpoints/endpoint-configurations" rel="noopener noreferrer"&gt;RunPod endpoint settings&lt;/a&gt;, &lt;a href="https://www.nodus-compute.ai/docs/guides/jobs/" rel="noopener noreferrer"&gt;Nodus Jobs guide&lt;/a&gt;. Checked October 29, 2026.&lt;/p&gt;

&lt;p&gt;So a 30-hour fine-tune does not fit in one Modal call at all. It fits in one RunPod Serverless job only if you raise the execution timeout from its 10-minute default, which is easy to forget until the first job dies at minute ten.&lt;/p&gt;

&lt;h2&gt;
  
  
  What happens when a long serverless run is interrupted?
&lt;/h2&gt;

&lt;p&gt;The platform restarts the work, but your progress only survives if your code wrote it somewhere first. Modal's &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemption guide&lt;/a&gt; says all Modal Functions are preemptible by default, that a preempted Function is restarted on the same input, and that training Functions should checkpoint because the chance of interruption grows with run time. GPU Functions cannot opt out of preemption.&lt;/p&gt;

&lt;p&gt;Here is what that costs. Take a 30-hour run on one H100 that is interrupted at hour 20:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Without checkpoints, the restart begins at step 0, so you pay for 20 + 30 = 50 GPU-hours.&lt;/li&gt;
&lt;li&gt;With a checkpoint every hour, you lose at most one hour, so you pay for at most 31 GPU-hours.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;At Modal's H100 rate of $0.001097 per second (about $3.95 per hour), those 20 lost hours are $78.98 of repeated work. The fix is not exotic, but it is code you have to write, test and keep correct: save model, optimizer and step state, then detect a restart and load it.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fb4e1cn4c6j858eo0076k.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fb4e1cn4c6j858eo0076k.png" alt="A 30-hour run interrupted at hour 20 bills 50 GPU-hours with no checkpoints, at most 31 GPU-hours with hourly checkpoints, and 30 GPU-hours with no interruption." width="800" height="304"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;One interruption without checkpoints makes a 30-hour run bill 50 GPU-hours.&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  How does Nodus keep a multi-day training run going?
&lt;/h2&gt;

&lt;p&gt;Nodus treats checkpointing as the platform's job. Your program writes what it needs to continue under &lt;code&gt;/nodus/state&lt;/code&gt;, and Nodus copies that directory while the run is going. With the default &lt;code&gt;interval: auto&lt;/code&gt;, the &lt;a href="https://www.nodus-compute.ai/docs/guides/checkpoints/" rel="noopener noreferrer"&gt;checkpoint guide&lt;/a&gt; says the cadence follows how often the capacity is interrupted and how long a save takes, with at least four checkpoints over the expected run. Nodus also checkpoints when the capacity gives notice that it is about to be reclaimed, then starts the next attempt with the directory restored and &lt;code&gt;NODUS_RESTORED=1&lt;/code&gt; set.&lt;/p&gt;

&lt;p&gt;The managed &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;TrainingJob runtimes&lt;/a&gt; do the save and restore for you, including optimizer, scheduler and RNG state. This is the SFT example from the docs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1beta1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TrainingJob&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-sft&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;runtime&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/sft&lt;/span&gt;
  &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf://Qwen/Qwen3-0.6B@c1899de289a04d12100db370d81485cdf75e47ca&lt;/span&gt;
    &lt;span class="na"&gt;secret&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf-token&lt;/span&gt;            &lt;span class="c1"&gt;# only for gated repositories&lt;/span&gt;
  &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;volume&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-chats&lt;/span&gt;       &lt;span class="c1"&gt;# a Volume holding chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;format&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;JSONL&lt;/span&gt;
    &lt;span class="na"&gt;columns&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;question&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;completion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;answer&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;parameters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2000&lt;/span&gt;
    &lt;span class="na"&gt;lora&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;16&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;alpha&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;32&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;20.00"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;maxCostUSD&lt;/code&gt; cap is the other half of running long jobs safely. When the cap is reached, the run is suspended rather than failed, and raising the cap resumes the same run from its checkpoint. For a broader look at which platforms do this for you, see &lt;a href="https://www.nodus-compute.ai/blog/automatic-checkpointing-and-resume-for-training/" rel="noopener noreferrer"&gt;Which GPU platforms checkpoint and resume training for you?&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  What does a 30-hour H100 fine-tune cost on each option?
&lt;/h2&gt;

&lt;p&gt;At list prices, Nodus is the cheapest of the four for the same 30 GPU-hours, and it is the only one where the restart logic is not your code.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Option&lt;/th&gt;
&lt;th&gt;H100 list rate&lt;/th&gt;
&lt;th&gt;30 GPU-hours&lt;/th&gt;
&lt;th&gt;Fits in one run?&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Nodus Job or TrainingJob&lt;/td&gt;
&lt;td&gt;$2.60/hr&lt;/td&gt;
&lt;td&gt;$78.00&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal Function&lt;/td&gt;
&lt;td&gt;$3.95/hr ($0.001097/s)&lt;/td&gt;
&lt;td&gt;$118.48&lt;/td&gt;
&lt;td&gt;No, 24-hour cap&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Pod (H100 SXM)&lt;/td&gt;
&lt;td&gt;$3.99/hr&lt;/td&gt;
&lt;td&gt;$119.70&lt;/td&gt;
&lt;td&gt;Yes, not serverless&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Serverless (H100 PRO)&lt;/td&gt;
&lt;td&gt;$5.39/hr&lt;/td&gt;
&lt;td&gt;$161.70&lt;/td&gt;
&lt;td&gt;Yes, if the timeout is raised&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 29, 2026: Nodus H100 SXM listed at $2.60/hr on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt; (GPU only; Modal bills CPU and memory separately), &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;RunPod pricing&lt;/a&gt; for Pods and Serverless.&lt;/p&gt;

&lt;p&gt;The math is 30 times each hourly rate. On those numbers the Nodus run costs 34% less than the Modal run, before counting any repeated hours from an interruption.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fpka9ztagfux5x29zq18f.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fpka9ztagfux5x29zq18f.png" alt="For 30 H100 GPU-hours: Nodus $78.00, Modal $118.48, RunPod Pod $119.70, RunPod Serverless $161.70." width="800" height="328"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Same 30 GPU-hours, list prices: the gap is the hourly rate before any lost work.&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  When is serverless the right place to train?
&lt;/h2&gt;

&lt;p&gt;Serverless training makes sense when the run is short, cheap to repeat, or already part of a serverless app. A LoRA fine-tune of a small model that takes two hours fits inside Modal's 24-hour cap with room to spare. An interruption there costs at most two hours, so writing restart logic may not be worth it.&lt;/p&gt;

&lt;p&gt;Use this decision rule. If the run would take less than a few hours and a full restart is cheap, train where your app already lives. If it takes longer than one execution allows, or one lost run would cost more than you would spend writing and testing checkpoint code, use a platform that checkpoints for you.&lt;/p&gt;
&lt;h2&gt;
  
  
  Where is Modal or RunPod the better choice?
&lt;/h2&gt;

&lt;p&gt;Modal is the better choice when your training code is already a Modal app and runs fit in 24 hours. You keep one deployment model for training and inference, and its Python-first workflow avoids writing manifests. Modal also publishes a &lt;a href="https://modal.com/docs/examples/long-training" rel="noopener noreferrer"&gt;long training example&lt;/a&gt; that shows the checkpoint pattern if you want to stay.&lt;/p&gt;

&lt;p&gt;RunPod Serverless is the better choice when one job can take days but you want queue-based workers that scale down when idle. Its 7-day execution limit is far longer than Modal's. RunPod Pods suit teams that want a plain GPU machine and are happy to handle restarts themselves.&lt;/p&gt;

&lt;p&gt;Nodus is the better choice when runs are long, you want them on the cheapest capacity that will finish them, and you would rather the platform own checkpoints, recovery and the spending cap. We cover the platform-level comparison in &lt;a href="https://www.nodus-compute.ai/blog/best-serverless-gpu-platforms-2026/" rel="noopener noreferrer"&gt;What are the best serverless GPU platforms in 2026?&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you move a long training run to Nodus?
&lt;/h2&gt;

&lt;p&gt;If you use one of the managed runtimes, save the manifest above as &lt;code&gt;sft.yaml&lt;/code&gt;, check the estimate, then apply it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml &lt;span class="nt"&gt;--dry-run&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; yaml     &lt;span class="c"&gt;# status.estimate: cost to completion, first hold, start time&lt;/span&gt;
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus logs job/support-sft &lt;span class="nt"&gt;-f&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;For your own training script, point its save and load paths at &lt;code&gt;/nodus/state&lt;/code&gt; and run it as a Job with &lt;code&gt;nodus run --checkpoint /nodus/state&lt;/code&gt;. The &lt;a href="https://www.nodus-compute.ai/docs/guides/checkpoints/" rel="noopener noreferrer"&gt;checkpoint guide&lt;/a&gt; has a complete Python example.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Can I chain several Modal calls to train past 24 hours?
&lt;/h3&gt;

&lt;p&gt;Yes. Each call loads the last checkpoint from a Volume, trains until close to the limit, saves, and the next call continues. You own the orchestration, the save format and the edge cases, such as a preemption that lands mid-save.&lt;/p&gt;

&lt;h3&gt;
  
  
  Does the 24-hour Modal limit include time waiting for a GPU?
&lt;/h3&gt;

&lt;p&gt;No. Modal's timeout measures execution time only, not scheduling, and it applies per execution attempt when retries are configured.&lt;/p&gt;

&lt;h3&gt;
  
  
  How long does Nodus keep checkpoints after a run finishes?
&lt;/h3&gt;

&lt;p&gt;Checkpoint settings take a &lt;code&gt;retainAfterFinish&lt;/code&gt; value, shown as &lt;code&gt;168h&lt;/code&gt; in the docs example, after which only the final checkpoint is kept. &lt;code&gt;nodus describe job/NAME&lt;/code&gt; shows the latest one.&lt;/p&gt;

&lt;h3&gt;
  
  
  Does a Nodus TrainingJob need my code to handle checkpoints?
&lt;/h3&gt;

&lt;p&gt;Not with the managed runtimes such as &lt;code&gt;nodus/sft&lt;/code&gt;, &lt;code&gt;nodus/dpo&lt;/code&gt; and &lt;code&gt;nodus/grpo-lora&lt;/code&gt;; they save full recovery state themselves. Custom code only needs to write and read its files under &lt;code&gt;/nodus/state&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/serverless-gpu-for-training/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>ai</category>
      <category>serverless</category>
      <category>gpu</category>
    </item>
    <item>
      <title>What are the best serverless GPU platforms in 2026?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Thu, 29 Oct 2026 15:48:48 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/what-are-the-best-serverless-gpu-platforms-in-2026-5fof</link>
      <guid>https://dev.to/viswaretas_kotra/what-are-the-best-serverless-gpu-platforms-in-2026-5fof</guid>
      <description>&lt;p&gt;The best serverless GPU platform in 2026 depends on whether someone is waiting for the GPU: Modal or RunPod Serverless for endpoints a user waits on, and Nodus for training, fine-tuning and batch jobs that run for hours. Nodus lists an NVIDIA H100 at $2.60/hr on its &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt; and restores your latest checkpoint on a new machine when capacity is reclaimed, so a long job costs less and survives an interruption. Baseten, Replicate, Cerebrium and Google Cloud Run GPUs each fit a narrower case, and the decision rules in this post say which.&lt;/p&gt;

&lt;p&gt;We build Nodus, so weigh that. Every outside number links to the company's own page, and there is a section on where each of the others is the better pick.&lt;/p&gt;

&lt;h2&gt;
  
  
  What makes a GPU platform serverless?
&lt;/h2&gt;

&lt;p&gt;A serverless GPU platform starts your container on a GPU when work arrives, bills while it runs and lets the GPU go when things are quiet. The platforms differ in the details that decide the bill: how fast a cold worker gets ready, how long an idle worker stays billed, and how long one run may last.&lt;/p&gt;

&lt;p&gt;Those details split the field in two. Endpoint platforms tune for start time, because a person is waiting on the first token or image. Job platforms tune for price per GPU-hour and for finishing, because a run that dies at hour eight wastes eight hours of GPU time.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do the main serverless GPU platforms compare?
&lt;/h2&gt;

&lt;p&gt;The table lists what each company publishes on its own pages. Start times are the vendor's own claims, measured in different ways, so treat them as a guide rather than a benchmark.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;Built for&lt;/th&gt;
&lt;th&gt;NVIDIA H100&lt;/th&gt;
&lt;th&gt;NVIDIA L4&lt;/th&gt;
&lt;th&gt;Billing&lt;/th&gt;
&lt;th&gt;Start time the vendor states&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;Python functions, web endpoints, batch&lt;/td&gt;
&lt;td&gt;$0.001097/s ($3.95/hr)&lt;/td&gt;
&lt;td&gt;$0.000222/s ($0.80/hr)&lt;/td&gt;
&lt;td&gt;Per second; idle containers billed for 60 s by default&lt;/td&gt;
&lt;td&gt;Sub-second starts on large custom images (&lt;a href="https://modal.com/" rel="noopener noreferrer"&gt;homepage&lt;/a&gt;)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://www.runpod.io/serverless-gpu" rel="noopener noreferrer"&gt;RunPod Serverless&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;Container endpoints&lt;/td&gt;
&lt;td&gt;$5.39/hr flex worker (H100 PRO)&lt;/td&gt;
&lt;td&gt;$0.75/hr flex worker (24 GB class, includes L4)&lt;/td&gt;
&lt;td&gt;Per second, rounded up; 5 s idle timeout by default (&lt;a href="https://docs.runpod.io/serverless/pricing" rel="noopener noreferrer"&gt;docs&lt;/a&gt;)&lt;/td&gt;
&lt;td&gt;Under 200 ms with FlashBoot&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://www.baseten.co/pricing/" rel="noopener noreferrer"&gt;Baseten&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;Production model serving and training&lt;/td&gt;
&lt;td&gt;$0.10833/min ($6.50/hr)&lt;/td&gt;
&lt;td&gt;$0.01414/min ($0.85/hr)&lt;/td&gt;
&lt;td&gt;Per minute, including deploy and scaling time&lt;/td&gt;
&lt;td&gt;"Fast cold starts", no figure&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://replicate.com/pricing" rel="noopener noreferrer"&gt;Replicate&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;Public models by API, custom models with Cog&lt;/td&gt;
&lt;td&gt;$0.001525/s ($5.49/hr)&lt;/td&gt;
&lt;td&gt;Not listed&lt;/td&gt;
&lt;td&gt;Per second; most private models also pay for setup and idle time&lt;/td&gt;
&lt;td&gt;Not stated&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://www.cerebrium.ai/pricing" rel="noopener noreferrer"&gt;Cerebrium&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;LLM, voice and image apps&lt;/td&gt;
&lt;td&gt;$0.000944/s ($3.40/hr)&lt;/td&gt;
&lt;td&gt;$0.000222/s ($0.80/hr)&lt;/td&gt;
&lt;td&gt;Per second; CPU and memory billed separately&lt;/td&gt;
&lt;td&gt;Not stated&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://cloud.google.com/run/docs/configuring/services/gpu" rel="noopener noreferrer"&gt;Google Cloud Run GPUs&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;Containers on Google Cloud&lt;/td&gt;
&lt;td&gt;Not offered (L4 and RTX PRO 6000 only)&lt;/td&gt;
&lt;td&gt;$0.0001867/s ($0.67/hr) (&lt;a href="https://cloud.google.com/run/pricing" rel="noopener noreferrer"&gt;pricing&lt;/a&gt;)&lt;/td&gt;
&lt;td&gt;Per second, instance-based; an L4 needs at least 4 vCPU and 16 GiB&lt;/td&gt;
&lt;td&gt;About 5 s&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;Training, fine-tuning, batch, Python Functions&lt;/td&gt;
&lt;td&gt;$2.60/hr&lt;/td&gt;
&lt;td&gt;$0.43/hr&lt;/td&gt;
&lt;td&gt;Prepaid credit; each run holds funds before it starts&lt;/td&gt;
&lt;td&gt;A cold and warm start estimate per Function, before you run&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 29, 2026. Hourly figures in brackets convert the listed per-second or per-minute rate; Modal, Cerebrium and Cloud Run bill CPU and memory on top of the GPU, and Cloud Run's L4 rate is the non-zonal-redundancy price. RunPod's endpoint docs show lower per-second rates for some tiers; we used the rates on its pricing page.&lt;/p&gt;

&lt;h2&gt;
  
  
  Which serverless GPU platform should you pick for each workload?
&lt;/h2&gt;

&lt;p&gt;Match the platform to who is waiting and for how long.&lt;/p&gt;

&lt;h3&gt;
  
  
  Someone is waiting on the response
&lt;/h3&gt;

&lt;p&gt;Pick RunPod Serverless or Modal. RunPod states sub-200 ms cold starts with FlashBoot, deploys any container, and by default keeps an idle worker for only 5 seconds before it scales down. Modal fits better when your service is Python: it states sub-second starts on large custom images and bills per second, with a 60-second keep-alive that you can change.&lt;/p&gt;

&lt;p&gt;Pick Baseten if you want a managed inference stack and per-minute billing is fine for your traffic. Pick Cloud Run if the rest of your app already lives on Google Cloud and an L4 or RTX PRO 6000 is enough. Google states instances start in about 5 seconds.&lt;/p&gt;

&lt;h3&gt;
  
  
  Traffic is steady all day
&lt;/h3&gt;

&lt;p&gt;Skip scale-to-zero and pay for warm capacity on purpose. Serverless rates price in the freedom to drop to zero, which you never use if the GPU is busy around the clock. RunPod offers always-on active workers with discounts through sales, and a Nodus Function's &lt;code&gt;min_workers&lt;/code&gt; setting keeps workers warm at the Function's worker rate. Compare that monthly bill with a reserved option before you commit.&lt;/p&gt;

&lt;h3&gt;
  
  
  The job runs for hours
&lt;/h3&gt;

&lt;p&gt;Pick Nodus. For training, fine-tuning and continued pretraining, the price of a GPU-hour and what happens on an interruption matter far more than a fast first request. Your script writes its state to &lt;code&gt;/nodus/state&lt;/code&gt;. Nodus checkpoints it at least four times over the expected run time and restores the latest copy into a new attempt if the machine is lost.&lt;/p&gt;

&lt;p&gt;The endpoint platforms can run long jobs too, within limits they publish. Modal caps one execution at &lt;a href="https://modal.com/docs/guide/timeouts" rel="noopener noreferrer"&gt;24 hours&lt;/a&gt; and makes Functions &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemptible by default&lt;/a&gt;, restarting an interrupted one on the same input. RunPod Serverless gives each endpoint a &lt;a href="https://docs.runpod.io/serverless/endpoints/endpoint-configurations" rel="noopener noreferrer"&gt;10-minute execution timeout&lt;/a&gt; by default, configurable up to 7 days, and one GPU per worker unless you raise it.&lt;/p&gt;

&lt;h3&gt;
  
  
  A batch job where nobody waits
&lt;/h3&gt;

&lt;p&gt;Embedding a corpus or scoring a dataset overnight has the same economics as training, so choose on price per GPU-hour and on resuming, not on cold starts. On Nodus, a Job with &lt;code&gt;Restartable&lt;/code&gt; continuity keeps the progress counter you report, so a replacement attempt can skip the items already done. A Function's &lt;code&gt;.map()&lt;/code&gt; fans one function out over thousands of inputs. Modal is a good fit too if your code already runs there: its &lt;a href="https://modal.com/docs/guide/batch-processing" rel="noopener noreferrer"&gt;batch processing guide&lt;/a&gt; scales functions to thousands of parallel containers.&lt;/p&gt;

&lt;h3&gt;
  
  
  You only need to call an open model
&lt;/h3&gt;

&lt;p&gt;You may not need a GPU platform at all. Baseten's Model APIs, Replicate's public models and Nodus Inference (Beta), which speaks the OpenAI API format, charge per token or per prediction, so you never size a worker.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does the same GPU work cost on each platform?
&lt;/h2&gt;

&lt;p&gt;At list prices, a 10-hour job on one H100 ranges from $26.00 on Nodus to $65.00 on Baseten. We priced a LoRA fine-tune that needs 10 hours on one NVIDIA H100, which is 36,000 GPU-seconds or 600 GPU-minutes, at each platform's listed H100 rate from the table:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Nodus: 10 h × $2.60 = $26.00&lt;/li&gt;
&lt;li&gt;Cerebrium: 36,000 s × $0.000944 = $33.98&lt;/li&gt;
&lt;li&gt;Modal: 36,000 s × $0.001097 = $39.49&lt;/li&gt;
&lt;li&gt;RunPod Serverless: 10 h × $5.39 = $53.90&lt;/li&gt;
&lt;li&gt;Replicate: 36,000 s × $0.001525 = $54.90&lt;/li&gt;
&lt;li&gt;Baseten: 600 min × $0.10833 = $65.00&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F9pu6jcbp2dabfwvce92r.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F9pu6jcbp2dabfwvce92r.png" alt="Cost of 10 H100-hours at list GPU rates: Nodus $26.00, Cerebrium $33.98, Modal $39.49, RunPod Serverless $53.90, Replicate $54.90, Baseten $65.00." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The same 10 H100-hours cost 34% less on Nodus than on Modal at list rates, before Modal adds CPU and memory.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;This counts the GPU line only: Modal and Cerebrium add CPU and memory on top, and cold starts and idle windows are seconds on a 10-hour job. The ratios hold per GPU-hour, so eight GPUs scale the same way.&lt;/p&gt;

&lt;p&gt;For a small model served on an L4, the gap is smaller in dollars but similar in shape. Nodus lists the L4 at $0.43/hr, against $0.67 on Cloud Run before its required CPU and memory, $0.75 on RunPod Serverless, $0.80 on Modal and Cerebrium, and $0.85 on Baseten.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F4kdd6fmdbrqebecrzz48.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F4kdd6fmdbrqebecrzz48.png" alt="Listed L4 rate per hour: Nodus $0.43, Cloud Run $0.67, RunPod Serverless $0.75, Modal $0.80, Cerebrium $0.80, Baseten $0.85." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;On an L4 the price spread is cents per hour, so cold-start behavior usually decides an endpoint, not the rate.&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  What happens to the bill when a long run is interrupted?
&lt;/h2&gt;

&lt;p&gt;An interruption costs whatever work you have to redo, and that can outweigh any rate difference. Take the same 10-hour job, lose the machine at hour 8, and price every case at $2.60/hr so only the recovery changes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;No interruption: 10 GPU-hours = $26.00&lt;/li&gt;
&lt;li&gt;Checkpoint every 30 minutes: at most 0.5 hours redone, 10.5 GPU-hours = $27.30&lt;/li&gt;
&lt;li&gt;No checkpoint: 8 hours lost plus a 10-hour rerun, 18 GPU-hours = $46.80&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fksekiipdw0ekspvqkk6t.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fksekiipdw0ekspvqkk6t.png" alt="Cost of a 10-hour H100 job at $2.60/hr: $26.00 with no interruption, $27.30 if lost at hour 8 with 30-minute checkpoints, $46.80 if lost at hour 8 with no checkpoint." width="800" height="304"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Without a checkpoint, one lost machine at hour 8 nearly doubles the bill.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Any platform here can resume if your code saves to persistent storage and reloads it on start, as &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;Modal's preemption guide&lt;/a&gt; recommends for training; the difference is who does the plumbing. On a reclaim notice, Nodus asks your program for an urgent checkpoint and prepares a replacement machine. The replacement starts only once the old one is provably gone, so two copies never write the same checkpoint (&lt;a href="https://www.nodus-compute.ai/docs/concepts/attempts-and-recovery/" rel="noopener noreferrer"&gt;attempts and recovery&lt;/a&gt;). If the old machine comes back first, the replacement is released and you are not charged for it.&lt;/p&gt;

&lt;p&gt;Our &lt;a href="https://www.nodus-compute.ai/blog/resume-training-after-spot-preemption/" rel="noopener noreferrer"&gt;guide to surviving spot preemption&lt;/a&gt; walks through the checkpoint code.&lt;/p&gt;
&lt;h2&gt;
  
  
  Can Nodus serve a latency-sensitive endpoint?
&lt;/h2&gt;

&lt;p&gt;Partly, and we would not pick it first for that today. Nodus Functions scale with demand: &lt;code&gt;min_workers&lt;/code&gt; defaults to 0, so a Function scales to zero, and &lt;code&gt;max_workers&lt;/code&gt; goes up to 1,000. An idle worker leaves after its &lt;code&gt;scaledown_window&lt;/code&gt;, 1 minute by default and up to 20 (&lt;a href="https://www.nodus-compute.ai/docs/guides/functions/scaling/" rel="noopener noreferrer"&gt;scaling docs&lt;/a&gt;). Before you deploy, &lt;code&gt;.estimate()&lt;/code&gt; reports the expected cold and warm start bands for that Function.&lt;/p&gt;

&lt;p&gt;What Nodus does not publish is a fixed cold-start figure, and hosted Inference is still in Beta. If first-request latency is the metric your product lives or dies on, start with RunPod Serverless or Modal, which publish start times, and test Nodus against them with your own model.&lt;/p&gt;
&lt;h2&gt;
  
  
  Where are Modal, RunPod and the others the better choice?
&lt;/h2&gt;

&lt;p&gt;Each of them beats Nodus somewhere specific.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Modal is the better choice for Python web endpoints that need quick container starts and per-second billing, and its Starter plan includes &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;$30 of compute credit a month&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;RunPod Serverless is the better choice when cold start is everything: it &lt;a href="https://www.runpod.io/serverless-gpu" rel="noopener noreferrer"&gt;states&lt;/a&gt; sub-200 ms starts with FlashBoot, and deploys straight from GitHub with rollbacks.&lt;/li&gt;
&lt;li&gt;Baseten is the better choice for teams that want a managed production inference platform; its &lt;a href="https://www.baseten.co/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt; lists SOC 2 Type II and HIPAA compliance and a self-hosted option on Enterprise.&lt;/li&gt;
&lt;li&gt;Replicate is the better choice for calling public models through an API without deploying anything, and its &lt;a href="https://replicate.com/pricing" rel="noopener noreferrer"&gt;fast-booting fine-tunes&lt;/a&gt; bill only active time.&lt;/li&gt;
&lt;li&gt;Cloud Run is the better choice if you already run on Google Cloud and an L4 or RTX PRO 6000 is enough, with &lt;a href="https://cloud.google.com/run/docs/configuring/services/gpu" rel="noopener noreferrer"&gt;no GPU reservation&lt;/a&gt; to manage.&lt;/li&gt;
&lt;li&gt;Cerebrium has the lowest per-second H100 rate among the endpoint platforms in our table, though &lt;a href="https://www.cerebrium.ai/pricing" rel="noopener noreferrer"&gt;CPU and memory&lt;/a&gt; are billed on top.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;For a deeper head-to-head on the two most common picks, see &lt;a href="https://www.nodus-compute.ai/blog/modal-vs-runpod/" rel="noopener noreferrer"&gt;Modal vs RunPod&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you move a long job from an endpoint platform to Nodus?
&lt;/h2&gt;

&lt;p&gt;Keep your training script and make it save to and load from &lt;code&gt;/nodus/state&lt;/code&gt;. Then install the CLI, sign in, and run the same script with a spend cap. Add &lt;code&gt;--dry-run&lt;/code&gt; first to see the estimate without starting paid compute. The commands are copied from the Nodus docs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
nodus login
nodus run &lt;span class="nt"&gt;--gpu&lt;/span&gt; H100 &lt;span class="nt"&gt;--image&lt;/span&gt; nodus/pytorch &lt;span class="nt"&gt;--checkpoint&lt;/span&gt; /nodus/state &lt;span class="nt"&gt;--max-cost&lt;/span&gt; 40 &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="nt"&gt;--&lt;/span&gt; python train.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The $40 cap leaves headroom over the $26.00 the job costs at the listed rate, and &lt;code&gt;nodus describe job/NAME&lt;/code&gt; shows each attempt, the latest checkpoint and the cost so far.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Is a serverless GPU cheaper than a dedicated one?
&lt;/h3&gt;

&lt;p&gt;Only when the GPU would otherwise sit idle. &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal's own pricing FAQ&lt;/a&gt; makes the same point: per-hour serverless rates can look higher, and the savings come from spiky or unpredictable traffic. If your GPU is busy most of the day, a lower hourly rate or reserved capacity wins.&lt;/p&gt;

&lt;h3&gt;
  
  
  Do you pay for cold starts on serverless GPUs?
&lt;/h3&gt;

&lt;p&gt;Usually, yes, for the part where your code loads. &lt;a href="https://docs.runpod.io/serverless/pricing" rel="noopener noreferrer"&gt;RunPod's docs&lt;/a&gt; bill from worker start until your handler is ready, which is mostly loading the model into GPU memory, while image pulls and cached model downloads happen unbilled. &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal&lt;/a&gt; bills application load time too, so smaller weights and lazy imports cut both latency and cost.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can you fine-tune a model on a serverless GPU platform?
&lt;/h3&gt;

&lt;p&gt;Yes. Nodus runs fine-tuning as a Job that resumes from its latest checkpoint, or through managed TrainingJobs (Beta) on the GPU you pick. Modal and RunPod Serverless also run training code, within the timeouts above.&lt;/p&gt;

&lt;h3&gt;
  
  
  What happens on Nodus if credit runs out mid-run?
&lt;/h3&gt;

&lt;p&gt;Nodus is prepaid and renews a funded hold on your balance every 5 minutes while work runs. When a renewal cannot be funded, the run stops gracefully inside time already paid for, keeps what it saved, and can resume once you add credit.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/best-serverless-gpu-platforms-2026/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>serverless</category>
      <category>gpu</category>
      <category>machinelearning</category>
      <category>cloud</category>
    </item>
    <item>
      <title>What is the cheapest way to fine-tune Llama on an H100?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Thu, 29 Oct 2026 01:40:56 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/what-is-the-cheapest-way-to-fine-tune-llama-on-an-h100-2ba3</link>
      <guid>https://dev.to/viswaretas_kotra/what-is-the-cheapest-way-to-fine-tune-llama-on-an-h100-2ba3</guid>
      <description>&lt;p&gt;The cheapest way to fine-tune Llama on one H100 is the lightest method that fits (LoRA for Llama 3.1 8B, QLoRA for a 70B), a checkpoint every few minutes and billing only while the job runs. Nodus lists the H100 SXM at $2.60/hr on its pricing page, stops billing when the job finishes and restores the latest checkpoint on a new machine if the GPU is reclaimed. In our worked example, that keeps a 50-million-token Llama 3.1 8B LoRA run at $8.35, where an idle hour or one unprotected preemption pushes the same run to $10.95 or $15.50.&lt;/p&gt;

&lt;p&gt;We build Nodus, so weigh that. Memory and speed figures below come from Hugging Face, torchtune and Unsloth, other platforms' prices link to their own pages, and every cost shows its arithmetic.&lt;/p&gt;

&lt;h2&gt;
  
  
  Which fine-tuning method fits Llama on one H100?
&lt;/h2&gt;

&lt;p&gt;LoRA and QLoRA fit the 8B comfortably, and only QLoRA fits a 70B. The figures are Hugging Face's own estimates from its &lt;a href="https://huggingface.co/blog/llama31" rel="noopener noreferrer"&gt;Llama 3.1 launch post&lt;/a&gt;, which describes them as approximate:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Method&lt;/th&gt;
&lt;th&gt;Llama 3.1 8B&lt;/th&gt;
&lt;th&gt;Llama 3.1 70B&lt;/th&gt;
&lt;th&gt;Fits one H100 80 GB?&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Full fine-tuning&lt;/td&gt;
&lt;td&gt;60 GB&lt;/td&gt;
&lt;td&gt;500 GB&lt;/td&gt;
&lt;td&gt;8B only, with memory-saving settings&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;LoRA (16-bit base)&lt;/td&gt;
&lt;td&gt;16 GB&lt;/td&gt;
&lt;td&gt;160 GB&lt;/td&gt;
&lt;td&gt;8B yes, 70B no&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;QLoRA (4-bit base)&lt;/td&gt;
&lt;td&gt;6 GB&lt;/td&gt;
&lt;td&gt;48 GB&lt;/td&gt;
&lt;td&gt;Both&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Figl5c19jt0ozr5l9dfti.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Figl5c19jt0ozr5l9dfti.png" alt="Approximate training memory from Hugging Face: Llama 3.1 8B needs 6 GB for QLoRA, 16 GB for LoRA and 60 GB for full fine-tuning; Llama 3.1 70B needs 48 GB, 160 GB and 500 GB." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;On one 80 GB H100, the 70B has exactly one option: QLoRA.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The full fine-tuning figure deserves a second look. The textbook cost of mixed-precision training with the AdamW optimizer is 16 bytes per parameter, as laid out in the &lt;a href="https://arxiv.org/abs/1910.02054" rel="noopener noreferrer"&gt;ZeRO paper&lt;/a&gt;. Llama 3.1 8B has 8,030,261,248 parameters, so that is 128 GB before activations. Hugging Face's lower 60 GB, and torchtune's 18.9 GiB on a 24 GB RTX 4090 in its &lt;a href="https://github.com/pytorch/torchtune" rel="noopener noreferrer"&gt;README&lt;/a&gt;, depend on lower-precision optimizer states and other memory savers.&lt;/p&gt;

&lt;p&gt;For the 70B, Unsloth reports that QLoRA of Llama 3.3 70B fits in 41 GB in its &lt;a href="https://unsloth.ai/blog/llama3-3" rel="noopener noreferrer"&gt;Llama 3.3 post&lt;/a&gt;. A 16-bit LoRA needs two or more H100s, which our &lt;a href="https://www.nodus-compute.ai/blog/vram-needed-for-70b-model/" rel="noopener noreferrer"&gt;70B VRAM guide&lt;/a&gt; works through in detail.&lt;/p&gt;
&lt;h2&gt;
  
  
  Is QLoRA cheaper than LoRA for Llama 3.1 8B on an H100?
&lt;/h2&gt;

&lt;p&gt;Usually not. QLoRA saves memory, and on an 80 GB card the 8B does not need the saving, while the 4-bit base can slow every step.&lt;/p&gt;

&lt;p&gt;torchtune measured both on the same hardware. For Llama 3.1 8B on an RTX 4090, LoRA trained at 3,083 tokens per second and QLoRA at 2,413, so QLoRA needed 28% more GPU time (3,083 / 2,413 = 1.28). For Llama 3.2 3B on an A100, the gap was small: 8,210 against 8,035 tokens per second. These are torchtune's numbers on those GPUs, not H100 measurements.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fgxw6iycn8byoe7xa5t1o.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fgxw6iycn8byoe7xa5t1o.png" alt="torchtune throughput: Llama 3.1 8B on an RTX 4090 trained at 3,083 tokens/s with LoRA and 2,413 with QLoRA; Llama 3.2 3B on an A100 trained at 8,210 and 8,035 tokens/s." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;QLoRA's slowdown ranged from 2% to 22% in torchtune's tests, and you pay for every extra second.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;GPU time is the bill, so the method that fits with the most headroom and runs fastest is the cheap one. For an 8B on an H100, that is 16-bit LoRA. Measure both on 100 steps if your sequences are long, because the trade can shift.&lt;/p&gt;
&lt;h2&gt;
  
  
  What does a Llama fine-tune cost per finished run?
&lt;/h2&gt;

&lt;p&gt;It costs the hourly rate times every hour you are billed, not only the training hours. We use one formula:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;cost per finished run = rate x (training tokens / tokens per second / 3,600 + startup + idle + redone hours)&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Here is a worked example, built from stated assumptions rather than a measured run. The job is a LoRA fine-tune of Llama 3.1 8B: 25 million tokens of data, 2 epochs, so 50 million training tokens.&lt;/p&gt;

&lt;p&gt;For speed we use torchtune's 4,699 tokens per second for Llama 3.1 8B LoRA on one RTX A6000. We found no published H100 figure for this exact setup, so the A6000 number is a stand-in: replace it with the tokens per second you measure. We also assume 15 minutes of billed startup and teardown, as in our &lt;a href="https://www.nodus-compute.ai/blog/lowest-cost-h100-and-b200-hours/" rel="noopener noreferrer"&gt;H100 and B200 cost-per-job post&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Training takes 50,000,000 / 4,699 = 10,641 seconds, or 2.96 hours. At $2.60/hr that is $7.70 of training plus $0.65 of startup, before anything goes wrong:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Scenario&lt;/th&gt;
&lt;th&gt;Billed hours&lt;/th&gt;
&lt;th&gt;Cost&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Clean run, billing stops when the job ends&lt;/td&gt;
&lt;td&gt;2.96 + 0.25 = 3.21&lt;/td&gt;
&lt;td&gt;$8.35&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Machine left on for 1 hour after training&lt;/td&gt;
&lt;td&gt;3.21 + 1 = 4.21&lt;/td&gt;
&lt;td&gt;$10.95&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Preempted at 2.5 hours, no usable checkpoint&lt;/td&gt;
&lt;td&gt;3.21 + 2.5 redone + 0.25 restart = 5.96&lt;/td&gt;
&lt;td&gt;$15.50&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Preempted at 2.5 hours, checkpoint every 10 minutes&lt;/td&gt;
&lt;td&gt;3.21 + at most 0.17 redone + 0.25 restart = 3.63&lt;/td&gt;
&lt;td&gt;$9.44&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The rate is listed at $2.60/hr on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt; for the H100 SXM 80 GB. Prices checked October 28, 2026.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F48htusp3by451lkdmar0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F48htusp3by451lkdmar0.png" alt="Cost per finished Llama 3.1 8B LoRA run at $2.60/hr: $8.35 for a clean run, $10.95 with one idle hour, $15.50 after a preemption with no checkpoint, and $9.44 after a preemption with 10-minute checkpoints." width="800" height="368"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;One preemption without a checkpoint adds $7.15 to the run; with 10-minute checkpoints it adds $1.09.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The lesson for Llama on an H100 is that the waste lines are bigger than any rate difference you can shop for. A one-hour idle tail adds $2.60, or 31% of this run. A lost run nearly doubles it.&lt;/p&gt;
&lt;h2&gt;
  
  
  Why are LoRA checkpoints cheap enough to save every few minutes?
&lt;/h2&gt;

&lt;p&gt;Because LoRA trains a tiny fraction of the model, its recovery checkpoint is small. Llama 3.1 8B has 32 layers, a hidden size of 4,096, key and value projections of 1,024 and an MLP size of 14,336, per the model config (we read an &lt;a href="https://huggingface.co/unsloth/Llama-3.1-8B-Instruct/blob/main/config.json" rel="noopener noreferrer"&gt;ungated copy&lt;/a&gt; on Hugging Face). A rank-16 adapter on all seven linear layers adds 16 x (in + out) parameters per layer:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;16 x [(4,096 + 4,096) x 2 + (4,096 + 1,024) x 2 + (4,096 + 14,336) x 3] = 1,310,720 per layer&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Over 32 layers that is 41,943,040 trainable parameters, 0.52% of the model. A full fine-tune has to save optimizer state for all 8 billion parameters, so frequent checkpoints get expensive. With LoRA they barely register, which is why the 10-minute row in the table above is realistic.&lt;/p&gt;

&lt;p&gt;Nodus resumes from full checkpoints with optimizer, scheduler and RNG state, as the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt; describes. On a reclaim notice it also asks the job for an urgent checkpoint, and a checkpoint committed during that notice counts, per the &lt;a href="https://www.nodus-compute.ai/docs/concepts/attempts-and-recovery/" rel="noopener noreferrer"&gt;attempts and recovery docs&lt;/a&gt;. Our &lt;a href="https://www.nodus-compute.ai/blog/resume-training-after-spot-preemption/" rel="noopener noreferrer"&gt;spot preemption guide&lt;/a&gt; covers the same pattern for your own scripts.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you run a Llama LoRA job on Nodus?
&lt;/h2&gt;

&lt;p&gt;First, get access to the weights. Llama models on Hugging Face are gated: you accept Meta's license on the model page, such as &lt;a href="https://huggingface.co/meta-llama/Llama-3.1-8B-Instruct" rel="noopener noreferrer"&gt;meta-llama/Llama-3.1-8B-Instruct&lt;/a&gt;, then use a Hugging Face token from that account. The terms are in the &lt;a href="https://www.llama.com/llama3_1/license/" rel="noopener noreferrer"&gt;Llama 3.1 Community License&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Then install the CLI, sign in and store the token as a Secret. These commands are copied from the Nodus &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training&lt;/a&gt; and &lt;a href="https://www.nodus-compute.ai/docs/guides/secrets/" rel="noopener noreferrer"&gt;secrets&lt;/a&gt; docs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="go"&gt;nodus secret create hf-token --from-literal HF_TOKEN=hf_xxx
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The manifest below is the LoRA example from the training guide with four changes: the Llama model pinned to its current Hugging Face commit, &lt;code&gt;method&lt;/code&gt;, &lt;code&gt;epochs&lt;/code&gt;, and one H100 under &lt;code&gt;resources&lt;/code&gt;. The managed &lt;code&gt;sft&lt;/code&gt; runtime publishes presets only for Qwen models, so a Llama run names its GPU. TrainingJobs are Beta, and we have not run this exact manifest, so start with the dry run.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1beta1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TrainingJob&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;llama-8b-lora&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;runtime&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/sft&lt;/span&gt;
  &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf://meta-llama/Llama-3.1-8B-Instruct@0e9e39f249a16976918f6564b8830bc894c89659&lt;/span&gt;
    &lt;span class="na"&gt;secret&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf-token&lt;/span&gt;            &lt;span class="c1"&gt;# only for gated repositories&lt;/span&gt;
  &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;volume&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-chats&lt;/span&gt;       &lt;span class="c1"&gt;# a Volume holding chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;format&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;JSONL&lt;/span&gt;
    &lt;span class="na"&gt;columns&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;question&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;completion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;answer&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;parameters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;method&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;LoRA&lt;/span&gt;
    &lt;span class="na"&gt;epochs&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt;
    &lt;span class="na"&gt;lora&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;16&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;alpha&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;32&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;resources&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;gpu&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;type&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;h100-sxm-80g&lt;/span&gt;&lt;span class="pi"&gt;],&lt;/span&gt; &lt;span class="nv"&gt;count&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;1&lt;/span&gt;&lt;span class="pi"&gt;}}&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;20.00"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml &lt;span class="nt"&gt;--dry-run&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; yaml     &lt;span class="c"&gt;# status.estimate: cost to completion, first hold, start time&lt;/span&gt;
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The runtime saves a recovery checkpoint every &lt;code&gt;saveSteps&lt;/code&gt; steps (200 by default), so set it to land roughly every 10 minutes once you know your step time. &lt;code&gt;nodus describe tj/llama-8b-lora&lt;/code&gt; shows tokens per second while it trains, which is the number to put into the formula above. The &lt;code&gt;maxCostUSD&lt;/code&gt; cap suspends the job at a checkpoint if spending reaches it, per the &lt;a href="https://www.nodus-compute.ai/docs/reference/runtimes/sft/" rel="noopener noreferrer"&gt;sft runtime reference&lt;/a&gt; and the &lt;a href="https://www.nodus-compute.ai/docs/guides/billing/budgets/" rel="noopener noreferrer"&gt;budgets docs&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where are Modal or RunPod the cheaper choice?
&lt;/h2&gt;

&lt;p&gt;Both can beat Nodus on this run, depending on how you work.&lt;/p&gt;

&lt;p&gt;Modal includes $30 a month of free compute on its Starter plan, and charges $0.001097 per second for an H100, or $3.9492/hr, according to &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal's pricing page&lt;/a&gt;. The clean run above bills 3.21 hours, which is $12.68 at that rate. That fits inside the monthly credit, so an occasional small Llama fine-tune can cost you nothing out of pocket on Modal. Modal restarts a preempted function on the same input, and you write the checkpoints yourself, per its &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemption docs&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;RunPod lists the H100 SXM at $2.69/hr on Community Cloud and $3.99/hr on Secure Cloud on its &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;. If you stop the Pod the moment training ends, the clean run costs $8.63 on Community Cloud, 28 cents more than our example. Pods are billed by the second until they stop, per &lt;a href="https://docs.runpod.io/pods/pricing" rel="noopener noreferrer"&gt;RunPod's Pod pricing docs&lt;/a&gt;, so one forgotten hour makes it $11.32. RunPod also offers a form-driven Axolotl fine-tuning flow in its &lt;a href="https://docs.runpod.io/fine-tune" rel="noopener noreferrer"&gt;fine-tuning docs&lt;/a&gt;, and a Pod gives you a full machine to work in interactively.&lt;/p&gt;

&lt;p&gt;Pick Modal if your runs are small and occasional, or your code already runs as Modal functions. Pick RunPod if you want a machine you drive by hand and you reliably shut it down. Pick Nodus if your runs are long enough that idle time and preemption are the real cost. Our &lt;a href="https://www.nodus-compute.ai/blog/best-platform-to-fine-tune-open-source-llms/" rel="noopener noreferrer"&gt;fine-tuning platform comparison&lt;/a&gt; covers per-token APIs as well.&lt;/p&gt;

&lt;h2&gt;
  
  
  Which setup should you pick?
&lt;/h2&gt;

&lt;p&gt;Use this rule, in order:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Llama 3.1 8B: 16-bit LoRA on one H100. Do not pay QLoRA's slowdown for memory you have. If you do not need an H100's speed, a 24 GB card is cheaper; our &lt;a href="https://www.nodus-compute.ai/blog/fine-tune-with-unsloth-on-cloud-gpu/" rel="noopener noreferrer"&gt;Unsloth guide&lt;/a&gt; shows the break-even.&lt;/li&gt;
&lt;li&gt;A 70B Llama on one H100: QLoRA. A 16-bit LoRA needs two or more GPUs.&lt;/li&gt;
&lt;li&gt;Full fine-tuning: only after LoRA has measurably fallen short. For comparison, the Nodus &lt;code&gt;sft&lt;/code&gt; runtime's preset for a full fine-tune of Qwen3-8B is 8 x H100.&lt;/li&gt;
&lt;li&gt;Every run: billing that stops when training stops, a checkpoint at least every 10 minutes, and 100 measured steps before you commit the full budget.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Can I use a fine-tuned Llama commercially?
&lt;/h3&gt;

&lt;p&gt;Yes for most companies, under the Llama 3.1 Community License. If you distribute the model or a product built on it, the license requires "Built with Llama" to be displayed and the model's name to start with "Llama". Companies above 700 million monthly active users need a separate license from Meta.&lt;/p&gt;

&lt;h3&gt;
  
  
  How long a context can I fine-tune a 70B Llama on with one 80 GB GPU?
&lt;/h3&gt;

&lt;p&gt;Unsloth reports up to 89,000 tokens of context for Llama 3.3 70B QLoRA on an 80 GB GPU with its long-context settings, against 6,900 with Hugging Face plus Flash Attention 2. Context length drives activation memory, so it is often what pushes a 70B run off a single GPU.&lt;/p&gt;

&lt;h3&gt;
  
  
  Should I pick a B200 instead of an H100 for Llama fine-tuning?
&lt;/h3&gt;

&lt;p&gt;Only if it finishes faster than its price ratio. The B200 is listed at $5.50/hr on the Nodus pricing page, 2.1 times the H100's $2.60, so it has to train more than 2.1 times faster to cost less per finished run.&lt;/p&gt;

&lt;h3&gt;
  
  
  Does Nodus pick the GPU if I leave &lt;code&gt;resources&lt;/code&gt; out?
&lt;/h3&gt;

&lt;p&gt;For Llama, the &lt;code&gt;sft&lt;/code&gt; runtime falls back to its default: one RTX 4090, L40S, RTX A6000 or A100 80 GB. That suits QLoRA of an 8B but not a 70B, so name the H100 explicitly when you need 80 GB.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/cheapest-way-to-fine-tune-llama-on-h100/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>llm</category>
      <category>gpu</category>
      <category>ai</category>
    </item>
    <item>
      <title>What are the best Together AI alternatives for fine-tuning?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Wed, 28 Oct 2026 23:08:00 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/what-are-the-best-together-ai-alternatives-for-fine-tuning-oj1</link>
      <guid>https://dev.to/viswaretas_kotra/what-are-the-best-together-ai-alternatives-for-fine-tuning-oj1</guid>
      <description>&lt;p&gt;For teams leaving Together AI's fine-tuning API, the strongest alternatives are Nodus for per-GPU-hour billing with managed recipes, Fireworks AI for another per-token API, and Modal or RunPod for running your own trainer. Nodus lists an NVIDIA H100 at $2.60/hr, runs SFT, DPO and GRPO recipes on a GPU you pick, and resumes a run from its latest checkpoint if a machine is lost. Together AI bills per training token instead, so the cheaper option depends on how many GPU-hours your job really takes.&lt;/p&gt;

&lt;p&gt;This post prices one realistic LoRA job both ways, shows the arithmetic once, and links every outside number to the company's own page. We make Nodus, so we also say plainly where Together AI is the better choice.&lt;/p&gt;

&lt;h2&gt;
  
  
  Who are Together AI's main competitors for fine-tuning?
&lt;/h2&gt;

&lt;p&gt;They fall into two groups: managed APIs that charge per token, and platforms that charge for GPU time. Together AI and Fireworks AI are in the first group. Nodus, Modal and RunPod are in the second.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;What you run&lt;/th&gt;
&lt;th&gt;How fine-tuning is billed&lt;/th&gt;
&lt;th&gt;Example listed price&lt;/th&gt;
&lt;th&gt;Serving the result&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Together AI&lt;/td&gt;
&lt;td&gt;Managed fine-tuning API, LoRA or full&lt;/td&gt;
&lt;td&gt;Per 1M training and evaluation tokens, minimum charge per job&lt;/td&gt;
&lt;td&gt;$0.34 per 1M tokens, LoRA SFT on Llama 3.1 8B&lt;/td&gt;
&lt;td&gt;Dedicated endpoint billed per minute, or download the weights&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Nodus&lt;/td&gt;
&lt;td&gt;Managed TrainingJob recipes (SFT, DPO, ORPO, KTO, distillation, GRPO), or your own script&lt;/td&gt;
&lt;td&gt;Per GPU-hour from prepaid credits, with a dollar cap per job&lt;/td&gt;
&lt;td&gt;$2.60/hr for an H100 SXM, $0.793/hr for an L40S&lt;/td&gt;
&lt;td&gt;Download outputs with &lt;code&gt;nodus cp&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Fireworks AI&lt;/td&gt;
&lt;td&gt;Managed fine-tuning API, LoRA or full parameter&lt;/td&gt;
&lt;td&gt;Per 1M training tokens, by model size&lt;/td&gt;
&lt;td&gt;$0.50 per 1M tokens, LoRA SFT up to 16B&lt;/td&gt;
&lt;td&gt;On-demand (dedicated) deployment&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal&lt;/td&gt;
&lt;td&gt;Your own trainer as Python functions&lt;/td&gt;
&lt;td&gt;Per GPU-second&lt;/td&gt;
&lt;td&gt;$0.001097/s for an H100&lt;/td&gt;
&lt;td&gt;Your own code&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod&lt;/td&gt;
&lt;td&gt;An Axolotl fine-tuning pod, or a pod you control&lt;/td&gt;
&lt;td&gt;Per hour, billed by the second&lt;/td&gt;
&lt;td&gt;$3.99/hr for an H100 SXM&lt;/td&gt;
&lt;td&gt;Your own code&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 28, 2026 on &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;Together AI pricing&lt;/a&gt;, the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, &lt;a href="https://fireworks.ai/pricing" rel="noopener noreferrer"&gt;Fireworks AI pricing&lt;/a&gt;, &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt; and &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;RunPod pricing&lt;/a&gt;. Serving details come from Together AI's &lt;a href="https://docs.together.ai/docs/fine-tuning/deployment" rel="noopener noreferrer"&gt;deployment docs&lt;/a&gt;, Fireworks AI's &lt;a href="https://docs.fireworks.ai/fine-tuning/fine-tuning-models" rel="noopener noreferrer"&gt;SFT guide&lt;/a&gt;, the Nodus &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt; and RunPod's &lt;a href="https://docs.runpod.io/fine-tune" rel="noopener noreferrer"&gt;fine-tuning docs&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;If you came here from a broader search, our guide to &lt;a href="https://www.nodus-compute.ai/blog/best-platform-to-fine-tune-open-source-llms/" rel="noopener noreferrer"&gt;the best platform to fine-tune open-source LLMs&lt;/a&gt; compares more options. This post is for teams already on Together AI who want to know what switching would cost.&lt;/p&gt;

&lt;h2&gt;
  
  
  How does Together AI bill a fine-tuning job?
&lt;/h2&gt;

&lt;p&gt;Together AI charges for every token the job processes, including repeats. Its &lt;a href="https://docs.together.ai/docs/fine-tuning/pricing" rel="noopener noreferrer"&gt;fine-tuning pricing docs&lt;/a&gt; give the formula:&lt;/p&gt;

&lt;p&gt;total tokens = (epochs × training dataset tokens) + (evaluations × validation dataset tokens)&lt;/p&gt;

&lt;p&gt;The rate per 1M tokens depends on the model size, the method (SFT or DPO) and whether you train LoRA or full weights. Each job pays at least a minimum charge, $4.00 for most models on the &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;. A fine-tuned model served on a dedicated endpoint is billed per minute on top of that, until you stop the endpoint.&lt;/p&gt;

&lt;p&gt;One detail catches people out. The same docs say that if you turn packing off, training tokens are counted as dataset length × &lt;code&gt;max_seq_length&lt;/code&gt;, not the tokens you actually have. A file of short chat turns can then bill as if every row were full length. Leave packing on unless you have a reason not to.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does the same fine-tuning job cost per token and per GPU-hour?
&lt;/h2&gt;

&lt;p&gt;Take a typical support-bot job: LoRA SFT on Llama 3.1 8B, a 20M-token training set, 3 epochs, and a 0.5M-token validation set evaluated 3 times. The sizes are our assumption; swap in your own.&lt;/p&gt;

&lt;p&gt;Together AI counts (3 × 20M) + (3 × 0.5M) = 61.5M tokens. At $0.34 per 1M for LoRA, that is 61.5 × $0.34 = $20.91. The same tokens as a full fine-tune, at $0.38 per 1M, cost $23.37.&lt;/p&gt;

&lt;p&gt;An hourly platform has no token meter, so the useful question is how many GPU-hours $20.91 buys. If the job finishes inside that time, hourly is cheaper. We divided $20.91 by each listed rate.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;GPU and platform&lt;/th&gt;
&lt;th&gt;Listed rate&lt;/th&gt;
&lt;th&gt;GPU-hours for $20.91&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;L40S, Nodus&lt;/td&gt;
&lt;td&gt;$0.793/hr&lt;/td&gt;
&lt;td&gt;26.4 h&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;A100 80GB, Nodus&lt;/td&gt;
&lt;td&gt;$1.09/hr&lt;/td&gt;
&lt;td&gt;19.2 h&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;A100 80GB, Modal&lt;/td&gt;
&lt;td&gt;$0.000694/s, or $2.4984/hr&lt;/td&gt;
&lt;td&gt;8.4 h&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100 SXM, Nodus&lt;/td&gt;
&lt;td&gt;$2.60/hr&lt;/td&gt;
&lt;td&gt;8.0 h&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100, Modal&lt;/td&gt;
&lt;td&gt;$0.001097/s, or $3.9492/hr&lt;/td&gt;
&lt;td&gt;5.3 h&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Rates from the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt; and &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt;, checked October 28, 2026. These are GPU line items only; storage and any separate CPU or memory charges are left out.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Faq2dv7amzd7x0ljwq4j1.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Faq2dv7amzd7x0ljwq4j1.png" alt="GPU-hours that cost the same as a $20.91 Together AI LoRA job, at listed rates checked October 28, 2026: Nodus L40S 26.4 h, Nodus A100 80GB 19.2 h, Modal A100 80GB 8.4 h, Nodus H100 8.0 h and Modal H100 5.3 h." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The same $20.91 buys 26.4 hours of an L40S on Nodus, so a slower GPU still has a lot of room to finish first.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The L40S row matters because an 8B LoRA does not need an H100. The Nodus &lt;a href="https://www.nodus-compute.ai/docs/reference/runtimes/sft/" rel="noopener noreferrer"&gt;&lt;code&gt;sft&lt;/code&gt; runtime&lt;/a&gt; presets put a QLoRA run on Qwen3-8B on one L40S, RTX A6000 or A100 80GB. A cheaper card with more hours to spare is often the better bet than the fastest one.&lt;/p&gt;

&lt;p&gt;Model size moves both sides. The same 61.5M tokens on Llama 3.3 70B cost 61.5 × $2.03 = $124.85 as a LoRA job on Together AI. That buys 48.0 H100-hours on Nodus, or 8 H100s for 6 hours.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you tell which side of the line your job is on?
&lt;/h2&gt;

&lt;p&gt;Measure, then multiply. Run a short trial on the GPU you plan to use, read its training speed, and work out how long the full job would take.&lt;/p&gt;

&lt;p&gt;On Nodus, &lt;code&gt;nodus describe tj/&amp;lt;name&amp;gt;&lt;/code&gt; shows the step, loss and tokens per second while the job runs, per the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt;. Then:&lt;/p&gt;

&lt;p&gt;hours = total tokens ÷ (tokens per second × 3,600)&lt;/p&gt;

&lt;p&gt;Multiply the hours by the hourly rate and compare it with total tokens × the Together AI rate. For the H100 above, the job has to average about 2,124 tokens per second to finish 61.5M tokens inside 8.0 hours. Our &lt;a href="https://www.nodus-compute.ai/blog/best-platform-to-fine-tune-open-source-llms/" rel="noopener noreferrer"&gt;break-even table&lt;/a&gt; gives the same threshold for other GPUs.&lt;/p&gt;

&lt;p&gt;The rule we use: if your trial says the job finishes inside the GPU-hours its token bill would buy, move it to an hourly platform. If it is close, stay where you are, because a migration costs engineering time too.&lt;/p&gt;
&lt;h2&gt;
  
  
  Is Fireworks AI cheaper than Together AI for fine-tuning?
&lt;/h2&gt;

&lt;p&gt;At the list prices we checked, no. Fireworks AI is the closest like-for-like alternative, since it also charges per training token, but its rates were higher for every model size we compared.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Model size&lt;/th&gt;
&lt;th&gt;Together AI, LoRA SFT&lt;/th&gt;
&lt;th&gt;Fireworks AI, LoRA SFT&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Llama 3.1 8B (Fireworks: up to 16B)&lt;/td&gt;
&lt;td&gt;$0.34 per 1M&lt;/td&gt;
&lt;td&gt;$0.50 per 1M&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Qwen3.5 27B (Fireworks: 16.1B to 80B)&lt;/td&gt;
&lt;td&gt;$1.05 per 1M&lt;/td&gt;
&lt;td&gt;$3.00 per 1M&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Llama 3.3 70B (Fireworks: 16.1B to 80B)&lt;/td&gt;
&lt;td&gt;$2.03 per 1M&lt;/td&gt;
&lt;td&gt;$3.00 per 1M&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices from &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;Together AI pricing&lt;/a&gt; and &lt;a href="https://fireworks.ai/pricing" rel="noopener noreferrer"&gt;Fireworks AI pricing&lt;/a&gt;, checked October 28, 2026. Fireworks AI prices by size bracket, so its bracket rate is shown against each Together AI model.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F2rh1pwthfc22gpon47lc.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F2rh1pwthfc22gpon47lc.png" alt="Price per 1M training tokens for LoRA SFT, checked October 28, 2026: Together AI $0.34 for Llama 3.1 8B, $1.05 for Qwen3.5 27B and $2.03 for Llama 3.3 70B; Fireworks AI $0.50 up to 16B and $3.00 from 16.1B to 80B." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Per-token rates climb with model size on both APIs, which is where an hourly GPU tends to pull ahead.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Our 61.5M-token job would cost 61.5 × $0.50 = $30.75 as a LoRA job on Fireworks AI. Fireworks AI does have reasons to pick it anyway. Its pricing page says fine-tuned models are served for the same price as base models, and it lists a Serverless Training API for LoRA on its launch models with no provisioning and no idle cost.&lt;/p&gt;
&lt;h2&gt;
  
  
  What happens when a fine-tuning run fails or is cut short?
&lt;/h2&gt;

&lt;p&gt;Together AI is generous here, and it is worth knowing before you switch. Its &lt;a href="https://docs.together.ai/docs/fine-tuning/pricing" rel="noopener noreferrer"&gt;pricing docs&lt;/a&gt; say a job that fails is fully refunded, and a job you cancel or stop early pays only for completed steps.&lt;/p&gt;

&lt;p&gt;On an hourly platform you pay for the GPU time used, so what matters is how much work a failure throws away. On Nodus, the managed runtimes write full checkpoints with optimizer, scheduler and RNG state, and a new attempt on another machine starts from the latest one. Each TrainingJob also has a &lt;code&gt;maxCostUSD&lt;/code&gt; cap. When the cap is reached the run is suspended rather than failed, and raising the cap resumes it from its checkpoint.&lt;/p&gt;

&lt;p&gt;Modal's &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemption guide&lt;/a&gt; says a preempted function restarts on the same input and recommends checkpoints for long training. With Modal or a RunPod pod, writing and loading those checkpoints is your code's job.&lt;/p&gt;
&lt;h2&gt;
  
  
  Where is Together AI the better choice?
&lt;/h2&gt;

&lt;p&gt;Stay on Together AI if any of these describe you. They are real advantages, not consolation prizes.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;You fine-tune very large models. Together AI's pricing page lists fine-tuning for DeepSeek-V3.1, Kimi K2.6 and GLM-5.2, and you never size a cluster. On Nodus, a model without a runtime preset gets the default single-GPU resources unless you request more.&lt;/li&gt;
&lt;li&gt;You want full fine-tuning of a small model. Together AI charges $0.38 per 1M tokens for full SFT on Llama 3.1 8B, barely above LoRA. The Nodus preset for a full Qwen3-8B run is 8 H100s, which costs 8 × $2.60 = $20.80 per hour.&lt;/li&gt;
&lt;li&gt;You serve the model on Together AI. Training, hosting and inference sit in one product, and its deployment docs also let you download merged weights or the adapter with &lt;code&gt;tg fine-tuning download&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;Your jobs are small and occasional. The token formula is easy to predict before you start, and a failed job costs nothing.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Together AI also sells GPU time directly. Its &lt;a href="https://docs.together.ai/docs/post-training/pricing" rel="noopener noreferrer"&gt;post-training docs&lt;/a&gt; describe a product billed per GPU-minute for custom loops and GRPO, so a Together AI team that wants hourly billing has an in-house option to price as well.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you move a Together AI fine-tuning job to Nodus?
&lt;/h2&gt;

&lt;p&gt;If your Together AI file uses the instruction format, one &lt;code&gt;prompt&lt;/code&gt; and one &lt;code&gt;completion&lt;/code&gt; per line as described in its &lt;a href="https://docs.together.ai/docs/fine-tuning/data-preparation" rel="noopener noreferrer"&gt;data preparation docs&lt;/a&gt;, it maps directly onto the Nodus &lt;code&gt;sft&lt;/code&gt; runtime. Install the CLI, sign in, and upload the file to a Volume. The commands come from the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt; and the &lt;a href="https://www.nodus-compute.ai/docs/guides/volumes/" rel="noopener noreferrer"&gt;Volumes guide&lt;/a&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus create volume support-chats &lt;span class="nt"&gt;--size&lt;/span&gt; 100Gi
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus volume put support-chats ./chats.jsonl /chats.jsonl
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then describe the job. This is the training guide's LoRA example with the column names set to Together AI's field names:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1beta1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TrainingJob&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-sft&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;runtime&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/sft&lt;/span&gt;
  &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf://Qwen/Qwen3-0.6B@c1899de289a04d12100db370d81485cdf75e47ca&lt;/span&gt;
  &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;volume&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-chats&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;format&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;JSONL&lt;/span&gt;
    &lt;span class="na"&gt;columns&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;completion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;completion&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;parameters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2000&lt;/span&gt;
    &lt;span class="na"&gt;lora&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;16&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;alpha&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;32&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;20.00"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml &lt;span class="nt"&gt;--dry-run&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; yaml
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The dry run prices the job before anything runs, and &lt;code&gt;maxCostUSD&lt;/code&gt; caps it at $20. Pin your own base model to a 40-character Hugging Face commit, as the guide recommends. TrainingJobs are in Beta, so fields can change before v1.&lt;/p&gt;

&lt;p&gt;Teams running their own trainer instead of a managed recipe should read our &lt;a href="https://www.nodus-compute.ai/blog/modal-alternatives-for-training-2026/" rel="noopener noreferrer"&gt;Modal alternatives for training&lt;/a&gt; and &lt;a href="https://www.nodus-compute.ai/blog/runpod-alternatives-2026/" rel="noopener noreferrer"&gt;RunPod alternatives&lt;/a&gt; posts.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Can I connect my Together AI account to Nodus?
&lt;/h3&gt;

&lt;p&gt;No. The Nodus &lt;a href="https://www.nodus-compute.ai/docs/guides/pools/cloud-accounts/" rel="noopener noreferrer"&gt;cloud accounts guide&lt;/a&gt; lists the accounts you can connect, such as AWS, GCP, Azure, Lambda, Nebius and RunPod, and Together AI is not among them. Move the dataset and run the job on Nodus instead.&lt;/p&gt;

&lt;h3&gt;
  
  
  Does Together AI count my validation set in the bill?
&lt;/h3&gt;

&lt;p&gt;Yes. Validation tokens are multiplied by the number of evaluations and added to the training tokens. Evaluating a large validation set often can add noticeably to a small job.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can I fine-tune with Unsloth instead of a managed recipe?
&lt;/h3&gt;

&lt;p&gt;Yes, as your own script on an hourly GPU. Our &lt;a href="https://www.nodus-compute.ai/blog/fine-tune-with-unsloth-on-cloud-gpu/" rel="noopener noreferrer"&gt;Unsloth on a cloud GPU guide&lt;/a&gt; walks through it on Nodus with checkpoints that survive a lost machine.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can a coding agent start the fine-tune for me?
&lt;/h3&gt;

&lt;p&gt;On Nodus, &lt;code&gt;nodus mcp install claude&lt;/code&gt; adds the Nodus MCP server to Claude Code, and any TrainingJob the agent launches is still bound by its &lt;code&gt;maxCostUSD&lt;/code&gt; cap.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/together-ai-alternatives-for-fine-tuning/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>ai</category>
      <category>llm</category>
      <category>finetuning</category>
    </item>
    <item>
      <title>What infrastructure do background coding agents need?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Wed, 28 Oct 2026 20:38:51 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/what-infrastructure-do-background-coding-agents-need-2d1n</link>
      <guid>https://dev.to/viswaretas_kotra/what-infrastructure-do-background-coding-agents-need-2d1n</guid>
      <description>&lt;p&gt;A background coding agent needs seven pieces of infrastructure: an isolated sandbox per task, scoped access to the repo and secrets, compute that can run for hours with GPUs when the task needs them, a spend cap the agent cannot raise, logs and status it can poll, checkpoint and resume, and automatic cleanup. Nodus covers the compute side of that list through one MCP server: CPU Sandboxes, GPU Jobs that resume from checkpoints, Budgets that block new work, and logs the agent can read. Your git host and the agent loop itself come from elsewhere.&lt;/p&gt;

&lt;p&gt;Most background agent guides stop at the sandbox, where the agent edits code and runs tests. The expensive part starts when the agent launches something long, like a fine-tune that runs overnight while nobody watches.&lt;/p&gt;

&lt;h2&gt;
  
  
  What are the seven components, and which ones does Nodus cover?
&lt;/h2&gt;

&lt;p&gt;Nodus covers all seven at least in part, and the gaps are specific: no GPU Sandboxes, no git hosting and no loop for your coding agent. We built this map from the current Nodus docs and checked every row against the linked page.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Component&lt;/th&gt;
&lt;th&gt;Why the agent needs it&lt;/th&gt;
&lt;th&gt;What Nodus provides today&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Isolated sandbox per task&lt;/td&gt;
&lt;td&gt;Runs model-written code away from your laptop and other tasks&lt;/td&gt;
&lt;td&gt;
&lt;a href="https://www.nodus-compute.ai/docs/guides/sandboxes/" rel="noopener noreferrer"&gt;Sandboxes&lt;/a&gt;: CPU only, no outbound network by default, &lt;code&gt;maxCostUSD&lt;/code&gt;, idle stop&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Repo and secrets access&lt;/td&gt;
&lt;td&gt;Clones private code and calls APIs without pasting keys&lt;/td&gt;
&lt;td&gt;
&lt;a href="https://www.nodus-compute.ai/docs/guides/secrets/" rel="noopener noreferrer"&gt;Secrets&lt;/a&gt; redacted from logs; a &lt;a href="https://www.nodus-compute.ai/docs/guides/connections/" rel="noopener noreferrer"&gt;GitHub Connection&lt;/a&gt; clones one repo with a short-lived read-only token&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Long-running compute and GPUs&lt;/td&gt;
&lt;td&gt;Training, evals and builds that outlive a chat session&lt;/td&gt;
&lt;td&gt;
&lt;a href="https://www.nodus-compute.ai/docs/guides/jobs/" rel="noopener noreferrer"&gt;Jobs&lt;/a&gt; on a named GPU or a minimum GPU memory, with a &lt;code&gt;timeout&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;A cap the agent can't raise&lt;/td&gt;
&lt;td&gt;Stops a loop or a wrong GPU count before it costs a weekend&lt;/td&gt;
&lt;td&gt;
&lt;a href="https://www.nodus-compute.ai/docs/guides/billing/budgets/" rel="noopener noreferrer"&gt;Budgets&lt;/a&gt; with &lt;code&gt;action: Block&lt;/code&gt;, plus &lt;code&gt;maxCostUSD&lt;/code&gt; per run&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Status and logs it can poll&lt;/td&gt;
&lt;td&gt;Lets the agent check progress instead of guessing&lt;/td&gt;
&lt;td&gt;MCP &lt;code&gt;wait&lt;/code&gt;, &lt;code&gt;logs&lt;/code&gt;, &lt;code&gt;describe&lt;/code&gt; and &lt;code&gt;events&lt;/code&gt;; &lt;a href="https://www.nodus-compute.ai/docs/guides/webhooks/" rel="noopener noreferrer"&gt;webhooks&lt;/a&gt; such as &lt;code&gt;job.succeeded&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Checkpoint and resume&lt;/td&gt;
&lt;td&gt;A lost machine or a cap costs minutes, not the whole run&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;recovery.continuity: Checkpointed&lt;/code&gt; restores &lt;code&gt;/nodus/state&lt;/code&gt; on new capacity&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Cleanup&lt;/td&gt;
&lt;td&gt;Nothing forgotten keeps billing&lt;/td&gt;
&lt;td&gt;Sandbox &lt;code&gt;maxLifetime&lt;/code&gt; and &lt;code&gt;onIdle: Delete&lt;/code&gt;; Job &lt;code&gt;ttlSecondsAfterFinished&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Docs checked October 28, 2026.&lt;/p&gt;

&lt;p&gt;GPU Sandboxes are not available yet: the &lt;a href="https://www.nodus-compute.ai/docs/guides/sandboxes/" rel="noopener noreferrer"&gt;Sandboxes page&lt;/a&gt; says a spec with &lt;code&gt;resources.gpu&lt;/code&gt; is refused. So the agent edits and tests in a CPU Sandbox, and anything that needs a GPU goes out as a Job.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why does every task need its own sandbox?
&lt;/h2&gt;

&lt;p&gt;A separate sandbox per task keeps one agent's mistakes out of everything else. Model-written code can delete files, fork processes or try to reach the network, and you want that contained.&lt;/p&gt;

&lt;p&gt;On Nodus, each Sandbox runs on CPU machines Nodus operates, in its own network namespace with a default-deny firewall, its own cgroup limits and a non-root user, per the &lt;a href="https://www.nodus-compute.ai/docs/concepts/sandboxes-isolation/" rel="noopener noreferrer"&gt;isolation page&lt;/a&gt;. Egress is &lt;code&gt;Deny&lt;/code&gt; unless you choose &lt;code&gt;AllowList&lt;/code&gt; or &lt;code&gt;Open&lt;/code&gt;. Creating a Sandbox with the same name and spec returns the existing one, which is how an agent reconnects after its own restart.&lt;/p&gt;

&lt;p&gt;The same page is clear about the limit: anything you put in a Sandbox is readable by the code running there. Give it only the credentials its task needs, and keep egress closed unless the work needs the network.&lt;/p&gt;

&lt;h2&gt;
  
  
  How should the agent get repo and secret access?
&lt;/h2&gt;

&lt;p&gt;Give the agent short-lived, narrow credentials, never your personal token. The GitHub side of this is well understood: &lt;a href="https://docs.github.com/en/apps/overview" rel="noopener noreferrer"&gt;GitHub's own docs&lt;/a&gt; prefer GitHub Apps because they use fine-grained permissions and short-lived tokens.&lt;/p&gt;

&lt;p&gt;Nodus follows that pattern for reads. A &lt;code&gt;GitHub&lt;/code&gt; Connection installs the Nodus GitHub App, and a Sandbox clones a pinned commit with a token that can only read that one repository and never appears in the Sandbox's files or environment. Secrets are stored once, never returned by the API, and redacted from logs. A command that pastes a secret's literal value into &lt;code&gt;env&lt;/code&gt; is refused with &lt;code&gt;SecretValueInEnv&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;What Nodus does not do is host your code or open pull requests. Pushing a branch and opening the PR stays with your git host and whatever identity your agent uses there.&lt;/p&gt;

&lt;h2&gt;
  
  
  Where does the long-running GPU work run?
&lt;/h2&gt;

&lt;p&gt;Long GPU work runs as a Job, not inside the agent's session. A Job takes an image, a command, a GPU, a &lt;code&gt;timeout&lt;/code&gt; and a &lt;code&gt;maxCostUSD&lt;/code&gt;, then runs to completion while the agent does something else.&lt;/p&gt;

&lt;p&gt;The agent creates it through the Nodus MCP server. The first &lt;code&gt;apply&lt;/code&gt; call returns a dry run with the estimated cost and an &lt;code&gt;etag&lt;/code&gt;, and nothing is created until a second call with &lt;code&gt;confirmed: true&lt;/code&gt; and the same &lt;code&gt;etag&lt;/code&gt;, as the &lt;a href="https://www.nodus-compute.ai/docs/guides/mcp/" rel="noopener noreferrer"&gt;MCP guide&lt;/a&gt; describes. Connecting Claude Code to the hosted server is one command from the &lt;a href="https://www.nodus-compute.ai/connect/" rel="noopener noreferrer"&gt;connect page&lt;/a&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;claude mcp add &lt;span class="nt"&gt;--scope&lt;/span&gt; user &lt;span class="nt"&gt;--transport&lt;/span&gt; http nodus https://api-next.nodus-compute.ai/mcp
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then run &lt;code&gt;/mcp&lt;/code&gt; in Claude Code, choose nodus and sign in. The &lt;a href="https://www.nodus-compute.ai/blog/give-claude-code-codex-cursor-gpus-mcp/" rel="noopener noreferrer"&gt;MCP setup post&lt;/a&gt; covers Codex and Cursor too.&lt;/p&gt;

&lt;h2&gt;
  
  
  How much should the agent be allowed to spend overnight?
&lt;/h2&gt;

&lt;p&gt;Set the per-run cap at the listed rate times GPUs times expected hours, plus about 20% headroom, and put a blocking Budget around all agent work. This is the rule we use, and here is the math for one run.&lt;/p&gt;

&lt;p&gt;Say the agent launches a fine-tune at 6 pm that should take 8 hours on one NVIDIA H100. The H100 is listed at $2.60/hr on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, so the expected cost is 8 x $2.60 = $20.80. With 20% headroom, 8 x $2.60 x 1.2 = $24.96, so the cap is $25. That cap allows about 9.6 hours of H100 time (9.6 x $2.60 = $24.96).&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Job&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;overnight-finetune&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;image&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/pytorch&lt;/span&gt;
  &lt;span class="na"&gt;command&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;python&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;train.py&lt;/span&gt;&lt;span class="pi"&gt;]&lt;/span&gt;
  &lt;span class="na"&gt;resources&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;gpu&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;H100&lt;/span&gt;
  &lt;span class="na"&gt;timeout&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;10h&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;25.00"&lt;/span&gt;
  &lt;span class="na"&gt;recovery&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;continuity&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Checkpointed&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now suppose the script hangs and nothing stops it. By 6 pm the next day, 24 hours in, it has cost 24 x $2.60 = $62.40. Left until 9 am Monday, a Friday evening launch runs 63 hours and costs 63 x $2.60 = $163.80. With the cap, it checkpoints and suspends with reason &lt;code&gt;MaxCostReached&lt;/code&gt; at $25.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Flxmhenwad7b4px3aqqs1.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Flxmhenwad7b4px3aqqs1.png" alt="Cumulative cost of one H100 job left running: uncapped it reaches $20.80 at 8 hours, $62.40 at 24 hours and $163.80 at 63 hours, while a $25 maxCostUSD cap stops it near $24.96 at 9.6 hours." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;A hung overnight job costs the cap, not the weekend.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;timeout: 10h&lt;/code&gt; is a second guard: 10 x $2.60 = $26, so the $25 cap fires first. Whichever limit is reached first stops the run.&lt;/p&gt;

&lt;p&gt;The cap is not the ceiling the agent can't move, though. The &lt;a href="https://www.nodus-compute.ai/docs/guides/billing/budgets/" rel="noopener noreferrer"&gt;Budgets docs&lt;/a&gt; say anyone can raise a run's &lt;code&gt;maxCostUSD&lt;/code&gt; at any time, but not lower it, so an agent with write access to Jobs can raise its own cap. The hard ceiling is a Budget with &lt;code&gt;action: Block&lt;/code&gt;, created by you, with the agent's MCP grant leaving out the scope to change Budgets. A monthly $500 Budget over everything the agent launches allows 24 such runs (24 x $20.80 = $499.20) before new work is refused with &lt;code&gt;402 BudgetExceeded&lt;/code&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Budget&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;agent-monthly&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;limitUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;500.00"&lt;/span&gt;
  &lt;span class="na"&gt;period&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Monthly&lt;/span&gt;
  &lt;span class="na"&gt;scope&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;selector&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="na"&gt;matchLabels&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;nodus.dev/launched-by&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;mcp&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;action&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Block&lt;/span&gt;
  &lt;span class="na"&gt;thresholds&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;50&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;80&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;100&lt;/span&gt;&lt;span class="pi"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Everything created through the MCP &lt;code&gt;apply&lt;/code&gt; flow carries the label &lt;code&gt;nodus.dev/launched-by: mcp&lt;/code&gt;, so this Budget covers agent work and nothing else. The &lt;a href="https://www.nodus-compute.ai/blog/ai-agent-gpu-spending-limits/" rel="noopener noreferrer"&gt;spending limits post&lt;/a&gt; walks through the grant and key setup step by step.&lt;/p&gt;

&lt;h2&gt;
  
  
  How does the cap change with the GPU the agent picks?
&lt;/h2&gt;

&lt;p&gt;The same $25 buys very different amounts of time depending on the GPU, so derive the cap from the GPU, not from habit. Here is what one 8-hour run costs and how long a $25 cap lasts at each listed rate.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;GPU&lt;/th&gt;
&lt;th&gt;Listed rate&lt;/th&gt;
&lt;th&gt;8-hour run&lt;/th&gt;
&lt;th&gt;Hours a $25 cap buys&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;NVIDIA L4&lt;/td&gt;
&lt;td&gt;$0.43/hr&lt;/td&gt;
&lt;td&gt;$3.44&lt;/td&gt;
&lt;td&gt;58.1&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;NVIDIA A100 80 GB&lt;/td&gt;
&lt;td&gt;$1.09/hr&lt;/td&gt;
&lt;td&gt;$8.72&lt;/td&gt;
&lt;td&gt;22.9&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;NVIDIA H100&lt;/td&gt;
&lt;td&gt;$2.60/hr&lt;/td&gt;
&lt;td&gt;$20.80&lt;/td&gt;
&lt;td&gt;9.6&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;NVIDIA H200&lt;/td&gt;
&lt;td&gt;$3.593/hr&lt;/td&gt;
&lt;td&gt;$28.74&lt;/td&gt;
&lt;td&gt;7.0&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;NVIDIA B200&lt;/td&gt;
&lt;td&gt;$5.50/hr&lt;/td&gt;
&lt;td&gt;$44.00&lt;/td&gt;
&lt;td&gt;4.5&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 28, 2026 on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;. Hours are $25 divided by the hourly rate.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fkbtehqeakxmh1v0ysjw3.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fkbtehqeakxmh1v0ysjw3.png" alt="Hours of GPU time a $25 cap buys at listed Nodus rates: L4 58.1 hours, A100 80 GB 22.9 hours, H100 9.6 hours, H200 7.0 hours and B200 4.5 hours." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;A $25 cap covers more than two days on an L4 and under five hours on a B200.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;If an agent asks for an H200 or a B200 for the 8-hour job, a $25 cap suspends it before it finishes. That is the point of computing the cap from the request: a mismatch shows up in the estimate, before any money is spent.&lt;/p&gt;

&lt;h2&gt;
  
  
  How does the agent know what happened while it was away?
&lt;/h2&gt;

&lt;p&gt;The agent should poll status and read logs, not trust its memory of what it launched. Through MCP, &lt;code&gt;wait&lt;/code&gt; blocks up to 60 seconds for a state, &lt;code&gt;logs&lt;/code&gt; reads up to 2,000 lines, and &lt;code&gt;describe&lt;/code&gt; and &lt;code&gt;events&lt;/code&gt; show why something stopped. Logs are kept after the machine is gone, per the &lt;a href="https://www.nodus-compute.ai/docs/guides/logs/" rel="noopener noreferrer"&gt;logs guide&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;For a person, or an agent loop that sleeps between turns, webhooks are cheaper than polling. Events include &lt;code&gt;job.succeeded&lt;/code&gt;, &lt;code&gt;job.failed&lt;/code&gt;, &lt;code&gt;job.restored&lt;/code&gt; and &lt;code&gt;job.max_cost_reached&lt;/code&gt;. One caution from the MCP guide applies here: log output comes back marked as untrusted, and the agent must treat it as data, not instructions.&lt;/p&gt;

&lt;h2&gt;
  
  
  What happens when a machine is lost or the cap is hit?
&lt;/h2&gt;

&lt;p&gt;With checkpointing on, both cost minutes instead of the whole run. Your program writes its state to &lt;code&gt;/nodus/state&lt;/code&gt; (the path is also in &lt;code&gt;NODUS_STATE_DIR&lt;/code&gt;), and Nodus saves and restores that directory when capacity is reclaimed or the run moves. A Job that hits its cap also checkpoints, and raising &lt;code&gt;maxCostUSD&lt;/code&gt; resumes it from there.&lt;/p&gt;

&lt;p&gt;This is what lets an agent schedule GPU work on cheaper interruptible capacity without babysitting it. The &lt;a href="https://www.nodus-compute.ai/blog/automatic-checkpointing-and-resume-for-training/" rel="noopener noreferrer"&gt;checkpointing post&lt;/a&gt; shows what to save and how often.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does Nodus not cover?
&lt;/h2&gt;

&lt;p&gt;Nodus does not run your coding agent's loop, host your code or review your pull requests. Those come from other tools.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The agent loop: &lt;a href="https://code.claude.com/docs/en/overview" rel="noopener noreferrer"&gt;Claude Code&lt;/a&gt;, &lt;a href="https://developers.openai.com/codex/cloud" rel="noopener noreferrer"&gt;Codex Cloud&lt;/a&gt;, where each task gets its own workspace and keeps going while your computer sleeps, or &lt;a href="https://cursor.com/docs/cloud-agent" rel="noopener noreferrer"&gt;Cursor Cloud Agents&lt;/a&gt;, which run in isolated cloud VMs and support MCP servers.&lt;/li&gt;
&lt;li&gt;Git hosting and pull requests: your git host, ideally through an app with fine-grained, short-lived tokens.&lt;/li&gt;
&lt;li&gt;GPU inside the sandbox: not available on Nodus yet; send GPU work out as a Job.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Nodus also has &lt;a href="https://www.nodus-compute.ai/docs/guides/agents/" rel="noopener noreferrer"&gt;Agents&lt;/a&gt;, in Beta, where each run works in its own sandbox and survives restarts by replaying recorded steps. It is separate from connecting an outside coding agent over MCP. If you want the agent to go from a prompt to a trained model, the &lt;a href="https://www.nodus-compute.ai/blog/claude-code-train-model-from-prompt/" rel="noopener noreferrer"&gt;Claude Code training walkthrough&lt;/a&gt; shows the full loop.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Can the agent create GPU Sandboxes on Nodus?
&lt;/h3&gt;

&lt;p&gt;Not yet. The Sandboxes docs say a spec with &lt;code&gt;resources.gpu&lt;/code&gt; is refused, so run tests in a CPU Sandbox and submit GPU work as a Job with its own cap.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can an agent lower or remove a cap to save money?
&lt;/h3&gt;

&lt;p&gt;No. A run's &lt;code&gt;maxCostUSD&lt;/code&gt; can be raised but not lowered, and on a Sandbox a lower cap or no cap counts as a different spec. To stop spend early, suspend or cancel the run.&lt;/p&gt;

&lt;h3&gt;
  
  
  What happens to agent work when the Budget runs out?
&lt;/h3&gt;

&lt;p&gt;New work in scope is refused with &lt;code&gt;402 BudgetExceeded&lt;/code&gt;. Running work in scope checkpoints and stops gracefully, then resumes when you raise the limit or the next month starts.&lt;/p&gt;

&lt;h3&gt;
  
  
  How do I disconnect an agent that misbehaves?
&lt;/h3&gt;

&lt;p&gt;Delete its grant with &lt;code&gt;nodus delete oauthgrant &amp;lt;name&amp;gt;&lt;/code&gt; or in Console, Settings, Connected agents. The client stops working within 30 seconds, even with a token it already holds.&lt;/p&gt;

&lt;h3&gt;
  
  
  Do finished Jobs keep costing anything?
&lt;/h3&gt;

&lt;p&gt;Compute billing stops when a Job finishes. Jobs from &lt;code&gt;nodus run&lt;/code&gt; are deleted after 30 days by default, and deleting a Job deletes its outputs, so download results first.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/infrastructure-for-background-coding-agents/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>agents</category>
      <category>devops</category>
      <category>mcp</category>
    </item>
    <item>
      <title>What is the best platform to fine-tune open-source LLMs?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Wed, 28 Oct 2026 18:08:31 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/what-is-the-best-platform-to-fine-tune-open-source-llms-50a7</link>
      <guid>https://dev.to/viswaretas_kotra/what-is-the-best-platform-to-fine-tune-open-source-llms-50a7</guid>
      <description>&lt;p&gt;The best platform to fine-tune an open-source LLM is usually the one that charges least per finished run. Of the hourly platforms we priced, Nodus lists the lowest NVIDIA H100 rate at $2.60/hr and resumes a run from its latest checkpoint if a machine is lost. Together AI is the better pick if you would rather pay per training token and never choose a GPU, and Modal, RunPod or AWS SageMaker suit teams that already run their own trainer there.&lt;/p&gt;

&lt;p&gt;No single platform wins every job, so this guide gives you rules instead of a ranking. Every fact about another company links to its own pricing page or docs, and since we build Nodus, every cost below shows its arithmetic so you can check us.&lt;/p&gt;

&lt;h2&gt;
  
  
  Which fine-tuning platform should you pick?
&lt;/h2&gt;

&lt;p&gt;Pick by how much of the training stack you want to own, then by price. These are the rules we would give a friend.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Choose Nodus if you want managed recipes (SFT with full, LoRA or QLoRA, plus DPO, ORPO, KTO, distillation and GRPO) on a GPU you can choose, a price estimate before anything runs, a hard dollar cap per job and automatic resume after a lost machine.&lt;/li&gt;
&lt;li&gt;Choose Together AI if you want a fine-tuning API priced per token, your base model is in its catalog or on the Hugging Face Hub, and you plan to serve the result on its endpoints.&lt;/li&gt;
&lt;li&gt;Choose Modal if your training code already runs as Modal functions and you are happy to write your own checkpoint and resume logic.&lt;/li&gt;
&lt;li&gt;Choose RunPod if you want a console form that launches an Axolotl fine-tuning pod, or a GPU pod you control end to end.&lt;/li&gt;
&lt;li&gt;Choose AWS SageMaker if your data, credits and compliance reviews already live in AWS, and an 8-GPU instance is the size of job you run.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Hugging Face AutoTrain is no longer a candidate for new work. Its &lt;a href="https://huggingface.co/docs/autotrain/index" rel="noopener noreferrer"&gt;docs&lt;/a&gt; say the project is no longer maintained and bugs will not be fixed; our &lt;a href="https://www.nodus-compute.ai/blog/hugging-face-autotrain-alternatives/" rel="noopener noreferrer"&gt;AutoTrain alternatives&lt;/a&gt; post covers what to move to.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do Nodus, Together AI, Modal, RunPod and SageMaker compare?
&lt;/h2&gt;

&lt;p&gt;They split into a managed API that prices tokens and platforms that price GPU time. That split decides most of what follows.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;What you run&lt;/th&gt;
&lt;th&gt;How you pay&lt;/th&gt;
&lt;th&gt;Listed H100 price&lt;/th&gt;
&lt;th&gt;If the GPU is lost&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Nodus&lt;/td&gt;
&lt;td&gt;Managed TrainingJob recipes, or your own script as a Job&lt;/td&gt;
&lt;td&gt;Prepaid credits, hourly price per GPU&lt;/td&gt;
&lt;td&gt;$2.60/hr (H100 SXM)&lt;/td&gt;
&lt;td&gt;Resumes from the latest full checkpoint (optimizer, scheduler and RNG state)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Together AI&lt;/td&gt;
&lt;td&gt;Fine-tuning API, LoRA or full&lt;/td&gt;
&lt;td&gt;Per 1M training tokens, minimum charge per job&lt;/td&gt;
&lt;td&gt;Not applicable&lt;/td&gt;
&lt;td&gt;Not stated on the pricing page&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal&lt;/td&gt;
&lt;td&gt;Your own trainer as Python functions&lt;/td&gt;
&lt;td&gt;Per second&lt;/td&gt;
&lt;td&gt;$0.001097/s, or $3.9492/hr&lt;/td&gt;
&lt;td&gt;Restarts the function on the same input; you write the checkpoints&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod&lt;/td&gt;
&lt;td&gt;Axolotl fine-tuning pod, or your own pod&lt;/td&gt;
&lt;td&gt;Per second&lt;/td&gt;
&lt;td&gt;$2.69/hr Community Cloud, $3.99/hr Secure Cloud (H100 SXM)&lt;/td&gt;
&lt;td&gt;Not stated in its fine-tuning docs&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;AWS SageMaker&lt;/td&gt;
&lt;td&gt;Training jobs with your own container or script&lt;/td&gt;
&lt;td&gt;Per instance-hour&lt;/td&gt;
&lt;td&gt;$63.296/hr for ml.p5.48xlarge (8 x H100)&lt;/td&gt;
&lt;td&gt;With managed spot training and checkpoints, copies them back from S3 and resumes&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 28, 2026 on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;Together AI pricing&lt;/a&gt;, &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt;, &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;RunPod pricing&lt;/a&gt; and the &lt;a href="https://pricing.us-east-1.amazonaws.com/offers/v1.0/aws/AmazonSageMaker/current/us-east-1/index.csv" rel="noopener noreferrer"&gt;AWS price list for SageMaker&lt;/a&gt; (US East, N. Virginia). Behavior on a lost GPU comes from the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;Nodus training guide&lt;/a&gt;, &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;Modal's preemption docs&lt;/a&gt;, &lt;a href="https://docs.runpod.io/fine-tune" rel="noopener noreferrer"&gt;RunPod's fine-tuning docs&lt;/a&gt; and &lt;a href="https://docs.aws.amazon.com/sagemaker/latest/dg/model-managed-spot-training.html" rel="noopener noreferrer"&gt;SageMaker's managed spot training docs&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does a full fine-tune on 8 H100s cost on each platform?
&lt;/h2&gt;

&lt;p&gt;At listed rates, the same 80 H100-hours cost $208.00 on Nodus and $632.96 on SageMaker, with RunPod and Modal in between. We picked 8 x H100 because that is the preset the Nodus &lt;a href="https://www.nodus-compute.ai/docs/reference/runtimes/sft/" rel="noopener noreferrer"&gt;&lt;code&gt;sft&lt;/code&gt; runtime&lt;/a&gt; uses for a full fine-tune of Qwen3-8B, and we assumed a 10-hour run. The duration is our assumption, not a measurement; scale it to your own job.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;Listed rate&lt;/th&gt;
&lt;th&gt;8 GPUs x 10 hours&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Nodus, H100 SXM&lt;/td&gt;
&lt;td&gt;$2.60 per GPU-hour&lt;/td&gt;
&lt;td&gt;80 x $2.60 = $208.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Community Cloud, H100 SXM&lt;/td&gt;
&lt;td&gt;$2.69 per GPU-hour&lt;/td&gt;
&lt;td&gt;80 x $2.69 = $215.20&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal, H100&lt;/td&gt;
&lt;td&gt;$0.001097 per GPU-second&lt;/td&gt;
&lt;td&gt;80 x 3,600 x $0.001097 = $315.94&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Secure Cloud, H100 SXM&lt;/td&gt;
&lt;td&gt;$3.99 per GPU-hour&lt;/td&gt;
&lt;td&gt;80 x $3.99 = $319.20&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;AWS SageMaker, ml.p5.48xlarge&lt;/td&gt;
&lt;td&gt;$63.296 per instance-hour&lt;/td&gt;
&lt;td&gt;10 x $63.296 = $632.96&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;These are GPU line items only. Storage, egress and any separate CPU or memory charges are left out for every platform, and SageMaker's figure is the whole 8-GPU instance.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx2gww05md1y0dz945t04.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx2gww05md1y0dz945t04.png" alt="Listed cost of a 10-hour run on 8 NVIDIA H100 GPUs, checked October 28, 2026: Nodus $208.00, RunPod Community Cloud $215.20, Modal $315.94, RunPod Secure Cloud $319.20 and AWS SageMaker ml.p5.48xlarge $632.96." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;At list prices, the same 80 H100-hours cost about a third as much on Nodus as on a SageMaker training instance.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;SageMaker's own &lt;a href="https://docs.aws.amazon.com/sagemaker/latest/dg/model-managed-spot-training.html" rel="noopener noreferrer"&gt;managed spot training docs&lt;/a&gt; say spot can cut that cost by up to 90%. The same page says managed spot never falls back to on-demand: if spot capacity is unavailable, the job waits until its maximum wait time and then stops.&lt;/p&gt;
&lt;h2&gt;
  
  
  Is paying per token cheaper than paying per GPU-hour for a LoRA run?
&lt;/h2&gt;

&lt;p&gt;The answer turns on one number you can measure: training tokens per second. Below the break-even speed, Together AI's per-token price is cheaper; above it, an hourly GPU is.&lt;/p&gt;

&lt;p&gt;Here is the rule we worked out. Together AI lists LoRA fine-tuning of Llama 3.1 8B and Qwen3.5 9B at $0.34 per 1M training tokens, with a $4.00 minimum per job, on its &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;. An H100 on Nodus is $2.60/hr. Dividing one by the other gives the break-even:&lt;/p&gt;

&lt;p&gt;$2.60 / $0.34 per 1M tokens = 7.65M tokens per hour, or 7,647,059 / 3,600 = 2,124 tokens per second.&lt;/p&gt;

&lt;p&gt;If your LoRA run trains faster than about 2,124 tokens per second on one H100, the Nodus hour costs less than the same tokens at Together AI. The same division for the other hourly rates in this post gives the bars below.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;GPU and platform&lt;/th&gt;
&lt;th&gt;Listed hourly rate&lt;/th&gt;
&lt;th&gt;Break-even vs $0.34 per 1M tokens&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;RTX 4090, Nodus&lt;/td&gt;
&lt;td&gt;$0.29&lt;/td&gt;
&lt;td&gt;237 tokens/s&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;L40S, Nodus&lt;/td&gt;
&lt;td&gt;$0.793&lt;/td&gt;
&lt;td&gt;648 tokens/s&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100, Nodus&lt;/td&gt;
&lt;td&gt;$2.60&lt;/td&gt;
&lt;td&gt;2,124 tokens/s&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100 SXM, RunPod Community Cloud&lt;/td&gt;
&lt;td&gt;$2.69&lt;/td&gt;
&lt;td&gt;2,198 tokens/s&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100, Modal&lt;/td&gt;
&lt;td&gt;$3.9492&lt;/td&gt;
&lt;td&gt;3,226 tokens/s&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Nodus rates are from the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;, checked October 28, 2026, alongside the RunPod and Modal pages linked above.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fm634ah2lbf2p24jzvysk.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fm634ah2lbf2p24jzvysk.png" alt="Training speed above which an hourly GPU beats Together AI's $0.34 per 1M tokens for LoRA: Nodus RTX 4090 237 tokens/s, Nodus L40S 648, Nodus H100 2,124, RunPod Community H100 2,198 and Modal H100 3,226." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;A cheaper GPU lowers the bar: a small LoRA job only has to beat 237 tokens per second on an RTX 4090.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;You do not have to guess your speed. A short Nodus run reports it: &lt;code&gt;nodus describe tj/&amp;lt;name&amp;gt;&lt;/code&gt; shows the step, loss and tokens per second, per the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt;. Run a few hundred steps, read the number, and compare it with the break-even for the GPU you used. Remember that Together AI also bills evaluation tokens, and small jobs pay at least the minimum charge.&lt;/p&gt;
&lt;h2&gt;
  
  
  Do you need automatic checkpoints and resume?
&lt;/h2&gt;

&lt;p&gt;For any run longer than an hour, yes, because a lost GPU otherwise means paying twice for the same steps. The platforms differ in who writes the checkpoint and who restarts from it.&lt;/p&gt;

&lt;p&gt;On Nodus, the managed runtimes write full checkpoints with optimizer, scheduler and RNG state, and a new attempt on another machine starts from the latest one. Each TrainingJob also carries a &lt;code&gt;maxCostUSD&lt;/code&gt; cap, and a dry run prices the job before it starts. Modal's &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemption docs&lt;/a&gt; say a preempted function restarts on the same input, recommend checkpointing long training yourself, and note that the &lt;code&gt;nonpreemptible&lt;/code&gt; option is not supported for GPU functions. SageMaker restores checkpoints from S3 when you turn on managed spot training and configure a checkpoint path.&lt;/p&gt;

&lt;p&gt;Recovery is also where a fine-tune quietly gets expensive. Our &lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-modal-fine-tuning-benchmark/" rel="noopener noreferrer"&gt;fine-tuning benchmark against Modal&lt;/a&gt; was a pilot with one small model on one NVIDIA L4. Both platforms returned identical trained weights, Nodus charged 67% less for the successful run, and including a failed Nodus attempt the total was still 24.7% lower.&lt;/p&gt;
&lt;h2&gt;
  
  
  Where are Together AI, Modal, RunPod or SageMaker the better choice?
&lt;/h2&gt;

&lt;p&gt;Each of them beats Nodus for a specific kind of team, and the reasons are concrete.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Together AI, when you do not want to size hardware at all. Its &lt;a href="https://docs.together.ai/docs/fine-tuning-overview" rel="noopener noreferrer"&gt;fine-tuning docs&lt;/a&gt; cover upload, training, hosting and inference in one product, and its pricing page lists fine-tuning for very large models such as DeepSeek-V3.1 and Kimi K2.6. On Nodus, a model without a runtime preset gets the default single-GPU resources unless you set larger ones yourself.&lt;/li&gt;
&lt;li&gt;Modal, when your inference and data jobs already run as Modal functions and you want training in the same codebase. Its &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt; also offers $30 a month in free compute, which covers small experiments.&lt;/li&gt;
&lt;li&gt;RunPod, when you want a form instead of a config file. Its &lt;a href="https://docs.runpod.io/fine-tune" rel="noopener noreferrer"&gt;fine-tuning page&lt;/a&gt; takes a Hugging Face model ID and dataset ID and launches an Axolotl pod. Its Community Cloud H100 is within 9 cents an hour of the Nodus rate.&lt;/li&gt;
&lt;li&gt;AWS SageMaker, when the deciding factor is AWS itself: existing credits, data that must stay in your account, or a security review that already approved SageMaker. Note that Nodus can also &lt;a href="https://www.nodus-compute.ai/docs/guides/pools/cloud-accounts/" rel="noopener noreferrer"&gt;run work in your own AWS account&lt;/a&gt;, GCP project or Azure subscription (Beta).&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Nodus has limits too. TrainingJobs are in Beta, so fields can change before v1, and runs start from the CLI or the Python SDK rather than a web form.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you start a fine-tune on Nodus?
&lt;/h2&gt;

&lt;p&gt;Install the SDK, sign in, and call a recipe with a GPU and a dollar cap. The commands and the recipe call are copied from the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt; and the Python recipe reference.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;sft&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;finetune&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sft&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Qwen/Qwen3-1.7B&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;nodus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Volume&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;from_name&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;support-chats&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
                   &lt;span class="n"&gt;lora&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;finetune&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;LoRA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;16&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;max_steps&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2000&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;run&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;gpu&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;H100&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;max_cost&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Run it after &lt;code&gt;import nodus&lt;/code&gt; and &lt;code&gt;from nodus.recipes import finetune&lt;/code&gt;, with your JSONL data already in a Volume named &lt;code&gt;support-chats&lt;/code&gt;. Nothing runs until &lt;code&gt;.run()&lt;/code&gt;, and &lt;code&gt;max_cost=20&lt;/code&gt; caps the job at $20. The same job as a YAML TrainingJob, with &lt;code&gt;nodus apply -f sft.yaml --dry-run -o yaml&lt;/code&gt; to see the estimate first, is in the training guide.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  What is the best platform to train AI models from scratch?
&lt;/h3&gt;

&lt;p&gt;The same price rules apply, but the deciding factor shifts to multi-node support and recovery across machines. Nodus runs pretraining with the same &lt;code&gt;sft&lt;/code&gt; runtime using &lt;code&gt;task: Pretrain&lt;/code&gt;, including from a fresh initialization, and the 8 x H100 cost comparison above scales linearly with the number of machines.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is LoRA enough, or do I need full fine-tuning?
&lt;/h3&gt;

&lt;p&gt;Start with LoRA. Together AI's own docs call it the right choice for most use cases because it is faster and cheaper, and say full fine-tuning can outperform it when the base model's behavior needs to shift substantially. Full fine-tuning also moves you up a GPU class: the Nodus preset for a full Qwen3-8B run is 8 x H100.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can I keep the fine-tuned weights?
&lt;/h3&gt;

&lt;p&gt;On Nodus, the adapter or full model is written as job outputs that you download with &lt;code&gt;nodus cp&lt;/code&gt;, and each file is checked against a recorded sha256. Together AI's docs say you can serve a fine-tuned model on a dedicated endpoint or download it.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can a coding agent launch the fine-tune for me?
&lt;/h3&gt;

&lt;p&gt;Yes. &lt;code&gt;nodus mcp install claude&lt;/code&gt; adds the Nodus MCP server to Claude Code, and any TrainingJob the agent starts is still bound by its &lt;code&gt;maxCostUSD&lt;/code&gt; cap.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/best-platform-to-fine-tune-open-source-llms/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>llm</category>
      <category>ai</category>
      <category>cloud</category>
    </item>
    <item>
      <title>How do you fine-tune with Unsloth on a cloud GPU?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Wed, 28 Oct 2026 15:42:14 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/how-do-you-fine-tune-with-unsloth-on-a-cloud-gpu-4m3f</link>
      <guid>https://dev.to/viswaretas_kotra/how-do-you-fine-tune-with-unsloth-on-a-cloud-gpu-4m3f</guid>
      <description>&lt;p&gt;Pick the smallest GPU that fits your model in Unsloth's VRAM table, save the trainer's checkpoints to a directory that survives a restart, and run your script as a batch job with a spending cap. Nodus runs that script on an RTX 4090 listed at $0.29/hr or an H100 at $2.60/hr, and restores the checkpoint directory on a new machine if the GPU is reclaimed. A preemption then costs you minutes of training, not the whole run.&lt;/p&gt;

&lt;p&gt;We build Nodus, so weigh that. Unsloth facts below link to Unsloth's own docs, other platforms' prices link to their pricing pages, and every cost figure shows its math.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does Unsloth change about fine-tuning?
&lt;/h2&gt;

&lt;p&gt;Unsloth makes the same fine-tune need a much smaller GPU. Its &lt;a href="https://github.com/unslothai/unsloth" rel="noopener noreferrer"&gt;GitHub README&lt;/a&gt; says it trains LLMs 2x faster with 70% less VRAM and no accuracy loss. The core package is Apache 2.0, so commercial use is fine.&lt;/p&gt;

&lt;p&gt;The memory saving matters more than the speed for your bill. By Unsloth's own table, a 14B model needs 33 GB for 16-bit LoRA but 8.5 GB with 4-bit QLoRA. That moves it from a 48 GB L40S, listed at $0.793/hr on the Nodus pricing page, to a 24 GB RTX 4090 at $0.29/hr.&lt;/p&gt;

&lt;p&gt;Unsloth plugs into Hugging Face TRL's &lt;code&gt;SFTTrainer&lt;/code&gt;. That detail is what makes cloud runs easy to recover, because the Trainer already knows how to save and resume.&lt;/p&gt;

&lt;h2&gt;
  
  
  Which GPU do you need for your model size?
&lt;/h2&gt;

&lt;p&gt;Use Unsloth's own &lt;a href="https://unsloth.ai/docs/get-started/fine-tuning-for-beginners/unsloth-requirements" rel="noopener noreferrer"&gt;VRAM requirements table&lt;/a&gt; and add headroom. Unsloth calls these numbers "the absolute minimum", and longer sequences or bigger batches need more.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Model size&lt;/th&gt;
&lt;th&gt;QLoRA (4-bit) minimum&lt;/th&gt;
&lt;th&gt;LoRA (16-bit) minimum&lt;/th&gt;
&lt;th&gt;A GPU that fits QLoRA with headroom&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;3B&lt;/td&gt;
&lt;td&gt;3.5 GB&lt;/td&gt;
&lt;td&gt;8 GB&lt;/td&gt;
&lt;td&gt;NVIDIA L4 or RTX 4090 (24 GB)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;8B&lt;/td&gt;
&lt;td&gt;6 GB&lt;/td&gt;
&lt;td&gt;22 GB&lt;/td&gt;
&lt;td&gt;RTX 4090 or L4 (24 GB)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;14B&lt;/td&gt;
&lt;td&gt;8.5 GB&lt;/td&gt;
&lt;td&gt;33 GB&lt;/td&gt;
&lt;td&gt;RTX 4090 or L4 (24 GB)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;32B&lt;/td&gt;
&lt;td&gt;26 GB&lt;/td&gt;
&lt;td&gt;76 GB&lt;/td&gt;
&lt;td&gt;L40S or RTX A6000 (48 GB)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;70B&lt;/td&gt;
&lt;td&gt;41 GB&lt;/td&gt;
&lt;td&gt;164 GB&lt;/td&gt;
&lt;td&gt;L40S (48 GB) for short sequences, A100 80 GB or H100 for room&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fl1ble53pdl85fizp3bge.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fl1ble53pdl85fizp3bge.png" alt="Unsloth minimum VRAM by model size: QLoRA needs 3.5 GB for 3B, 6 GB for 8B, 8.5 GB for 14B, 26 GB for 32B and 41 GB for 70B; 16-bit LoRA needs 8, 22, 33, 76 and 164 GB." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;QLoRA keeps every model up to 70B on a single GPU; 16-bit LoRA needs an 80 GB card at 32B and several cards at 70B.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Our rule: start with QLoRA on a 24 GB card for anything up to 14B. Switch to 16-bit LoRA only when you have measured a quality gap that matters to you. On Nodus you can also skip naming a GPU and set &lt;code&gt;resources.gpu.minMemory&lt;/code&gt; in the Job spec, and Nodus picks any accelerator with at least that much memory.&lt;/p&gt;
&lt;h2&gt;
  
  
  Is a bigger GPU ever cheaper per finished run?
&lt;/h2&gt;

&lt;p&gt;Yes, but only if it finishes proportionally faster. Divide the bigger card's hourly price by the smaller card's to get the speedup it must deliver just to break even. Here is that ratio against an RTX 4090 at Nodus list prices:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;GPU&lt;/th&gt;
&lt;th&gt;Listed on the Nodus pricing page&lt;/th&gt;
&lt;th&gt;Speedup needed vs RTX 4090&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;RTX 4090 (24 GB)&lt;/td&gt;
&lt;td&gt;$0.29/hr&lt;/td&gt;
&lt;td&gt;1.0x&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;L4 (24 GB)&lt;/td&gt;
&lt;td&gt;$0.43/hr&lt;/td&gt;
&lt;td&gt;1.5x&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;L40S (48 GB)&lt;/td&gt;
&lt;td&gt;$0.793/hr&lt;/td&gt;
&lt;td&gt;2.7x&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;A100 80 GB&lt;/td&gt;
&lt;td&gt;$1.09/hr&lt;/td&gt;
&lt;td&gt;3.8x&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100 SXM 80 GB&lt;/td&gt;
&lt;td&gt;$2.60/hr&lt;/td&gt;
&lt;td&gt;9.0x&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 28, 2026 on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fbrn1kg704fgdimkvetah.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fbrn1kg704fgdimkvetah.png" alt="Speedup a GPU needs over an RTX 4090 to cost the same per finished run: L4 1.5x, L40S 2.7x, A100 80 GB 3.8x, H100 9.0x." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;An H100 has to train 9x faster than an RTX 4090 before it saves money on the same job.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;We have not benchmarked Unsloth across these cards, so measure it yourself. Run 50 steps on two GPUs, compare seconds per step, and multiply by the hourly price. Unless the H100 comes close to 9x faster on your job, the cheaper card finishes it for less. Pay for the H100 when you need the result sooner or the model does not fit anywhere smaller.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you make an Unsloth script resume after a restart?
&lt;/h2&gt;

&lt;p&gt;Point the Trainer's &lt;code&gt;output_dir&lt;/code&gt; at the Nodus state directory and resume from the newest checkpoint on start. The script below is Unsloth's &lt;a href="https://github.com/unslothai/notebooks" rel="noopener noreferrer"&gt;Llama 3.1 8B Alpaca notebook&lt;/a&gt; with those two changes, plus a callback that saves when Nodus asks.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;unsloth&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;FastLanguageModel&lt;/span&gt;  &lt;span class="c1"&gt;# import first so its patches apply
&lt;/span&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;datasets&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;load_dataset&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;transformers.trainer_utils&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;get_last_checkpoint&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;trl&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;SFTConfig&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;SFTTrainer&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;nodus&lt;/span&gt;

&lt;span class="n"&gt;STATE&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;NODUS_STATE_DIR&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/nodus/state&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;OUTPUTS&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;NODUS_OUTPUTS_DIR&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/nodus/outputs&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;tokenizer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;FastLanguageModel&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;from_pretrained&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;model_name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;unsloth/Llama-3.1-8B&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;max_seq_length&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2048&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;load_in_4bit&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;FastLanguageModel&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get_peft_model&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;16&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lora_alpha&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;16&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lora_dropout&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;bias&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;none&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;target_modules&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;q_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;k_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;v_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;o_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                    &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;gate_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;up_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;down_proj&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="n"&gt;use_gradient_checkpointing&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;unsloth&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;random_state&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;3407&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;prompt&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;### Instruction:&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;{}&lt;/span&gt;&lt;span class="se"&gt;\n\n&lt;/span&gt;&lt;span class="s"&gt;### Input:&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;{}&lt;/span&gt;&lt;span class="se"&gt;\n\n&lt;/span&gt;&lt;span class="s"&gt;### Response:&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;{}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;fmt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ex&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;text&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;prompt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;format&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;tokenizer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;eos_token&lt;/span&gt;
                     &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="nf"&gt;zip&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ex&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;instruction&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="n"&gt;ex&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;input&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="n"&gt;ex&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;output&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;])]}&lt;/span&gt;
&lt;span class="n"&gt;dataset&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;load_dataset&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;unsloth/alpaca-cleaned&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;split&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;train&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;map&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;batched&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;trainer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;SFTTrainer&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;tokenizer&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;tokenizer&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;train_dataset&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;dataset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;dataset_text_field&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;text&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;max_seq_length&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2048&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;callbacks&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;nodus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;checkpoint&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;HFTrainerCallback&lt;/span&gt;&lt;span class="p"&gt;()],&lt;/span&gt;
    &lt;span class="n"&gt;args&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nc"&gt;SFTConfig&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="n"&gt;output_dir&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;STATE&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;save_steps&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;200&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;save_total_limit&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;per_device_train_batch_size&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;gradient_accumulation_steps&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;num_train_epochs&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;learning_rate&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;2e-4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;warmup_steps&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;optim&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;adamw_8bit&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;logging_steps&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;seed&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;3407&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;report_to&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;none&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;

&lt;span class="n"&gt;last&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;get_last_checkpoint&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;STATE&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;path&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;isdir&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;STATE&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="bp"&gt;None&lt;/span&gt;
&lt;span class="n"&gt;trainer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;train&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;resume_from_checkpoint&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;last&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;save_pretrained&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;OUTPUTS&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;/lora-adapter&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;tokenizer&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;save_pretrained&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;OUTPUTS&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;/lora-adapter&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Three lines do the recovery work. &lt;code&gt;output_dir=STATE&lt;/code&gt; puts Trainer's checkpoints where Nodus snapshots them. &lt;code&gt;get_last_checkpoint&lt;/code&gt; finds the newest &lt;code&gt;checkpoint-N&lt;/code&gt; folder after a restore, and stays &lt;code&gt;None&lt;/code&gt; on a first start.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;HFTrainerCallback&lt;/code&gt; comes from the Nodus SDK and makes Trainer save at the end of the current step when Nodus asks, including when the capacity gives notice that it is about to be reclaimed. Outside Nodus the SDK calls do nothing, so the same file runs on your laptop or in Colab.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;save_total_limit=2&lt;/code&gt; keeps the directory small. With QLoRA each checkpoint holds the adapter and optimizer state, not a copy of the 8B base model.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do you launch it as a Nodus Job?
&lt;/h2&gt;

&lt;p&gt;Install the CLI, sign in, and run from the folder that holds &lt;code&gt;train.py&lt;/code&gt;. These flags come from the &lt;a href="https://www.nodus-compute.ai/docs/guides/checkpoints/" rel="noopener noreferrer"&gt;Nodus checkpoints guide&lt;/a&gt; and the &lt;code&gt;nodus run&lt;/code&gt; reference:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus run &lt;span class="nt"&gt;--name&lt;/span&gt; unsloth-llama8b &lt;span class="nt"&gt;--gpu&lt;/span&gt; L4 &lt;span class="nt"&gt;--image&lt;/span&gt; nodus/pytorch &lt;span class="se"&gt;\&lt;/span&gt;
&lt;span class="go"&gt;    --checkpoint /nodus/state --interruptible \
    --max-cost 10 --timeout 24h -d \
    -- sh -c "pip install unsloth nodus-compute &amp;amp;&amp;amp; python train.py"
&lt;/span&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus logs &lt;span class="nt"&gt;-f&lt;/span&gt; job/unsloth-llama8b
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus &lt;span class="nb"&gt;cp &lt;/span&gt;job/unsloth-llama8b:outputs/lora-adapter/adapter_model.safetensors &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;An L4 fits this 8B QLoRA run with room to spare; &lt;code&gt;nodus get gpus&lt;/code&gt; lists the other types and their current rates, including the RTX 4090. &lt;code&gt;--interruptible&lt;/code&gt; lets Nodus use interruptible capacity, which is exactly the case the checkpoint setup covers.&lt;/p&gt;

&lt;p&gt;Add &lt;code&gt;--dry-run&lt;/code&gt; first to see the cost estimate without starting anything. &lt;code&gt;--max-cost 10&lt;/code&gt; is a cap, not a quote: at the cap the Job saves its state and suspends until you raise it. Everything under &lt;code&gt;/nodus/outputs&lt;/code&gt; is collected when the Job succeeds, so copy &lt;code&gt;adapter_config.json&lt;/code&gt; the same way. Installing Unsloth at start adds install time to every attempt, including restored ones. For repeat runs, pin the versions, push your own image to a registry and pass it to &lt;code&gt;--image&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does a preemption cost with and without checkpoints?
&lt;/h2&gt;

&lt;p&gt;Say a 10-hour QLoRA run on one H100 is reclaimed at hour 6. At $2.60/hr the whole run costs $26.00.&lt;/p&gt;

&lt;p&gt;Without checkpoints you start over and pay the first 6 hours twice, an extra $15.60. With &lt;code&gt;save_steps&lt;/code&gt; set so Trainer saves about every 30 minutes, the most you redo is 30 minutes, or $1.30. The Nodus callback usually shrinks that further, because Nodus asks for a save when the capacity gives notice. The &lt;a href="https://www.nodus-compute.ai/blog/automatic-checkpointing-and-resume-for-training/" rel="noopener noreferrer"&gt;checkpointing comparison&lt;/a&gt; covers which other platforms restore a run like this for you.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does the same run cost on other platforms?
&lt;/h2&gt;

&lt;p&gt;At list prices, 10 hours on one H100 SXM is cheapest on Nodus, with RunPod's Community Cloud close behind:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Platform&lt;/th&gt;
&lt;th&gt;H100 SXM hourly rate&lt;/th&gt;
&lt;th&gt;10 hours&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Nodus&lt;/td&gt;
&lt;td&gt;$2.60/hr&lt;/td&gt;
&lt;td&gt;$26.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Community Cloud&lt;/td&gt;
&lt;td&gt;$2.69/hr&lt;/td&gt;
&lt;td&gt;$26.90&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal&lt;/td&gt;
&lt;td&gt;$3.949/hr&lt;/td&gt;
&lt;td&gt;$39.49&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Secure Cloud&lt;/td&gt;
&lt;td&gt;$3.99/hr&lt;/td&gt;
&lt;td&gt;$39.90&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 28, 2026: &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;RunPod pricing&lt;/a&gt;, &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fw3f79ea0oo7lql5u41gd.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fw3f79ea0oo7lql5u41gd.png" alt="Cost of 10 hours on one H100 SXM: Nodus $26.00, RunPod Community Cloud $26.90, Modal $39.49, RunPod Secure Cloud $39.90." width="800" height="328"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The rate gap is small next to the GPU choice: the same 10 hours on an RTX 4090 at $0.29/hr is $2.90.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The hourly rate is only part of it. A &lt;a href="https://docs.runpod.io/pods/overview" rel="noopener noreferrer"&gt;RunPod Pod&lt;/a&gt; gives you a machine where you run and restart the script yourself. &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;Modal restarts a preempted function&lt;/a&gt; on the same input and asks you to add your own checkpoints. If you already work in either, Unsloth runs there too, and the script above works there apart from the state path and the Nodus callback.&lt;/p&gt;

&lt;h2&gt;
  
  
  When is Colab or your own GPU enough?
&lt;/h2&gt;

&lt;p&gt;For learning Unsloth and short experiments, start in Google Colab. Unsloth's README links a free Colab notebook for each of its featured models. The catch is that &lt;a href="https://research.google.com/colaboratory/faq.html" rel="noopener noreferrer"&gt;Colab's FAQ&lt;/a&gt; says free resources are not guaranteed, idle VMs are deleted, and lifetimes and GPU types vary over time.&lt;/p&gt;

&lt;p&gt;A 24 GB card you already own is enough for QLoRA up to 14B by Unsloth's table. It costs nothing per hour and your data never leaves the machine. Move to a cloud job when the run has to finish overnight without you watching it, when the model outgrows your card, or when you want several runs at once.&lt;/p&gt;

&lt;p&gt;If you would rather not maintain a training script, the managed &lt;code&gt;nodus/sft&lt;/code&gt; runtime in &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;Nodus Training (Beta)&lt;/a&gt; does full, LoRA or QLoRA fine-tuning from a JSONL file. It is not Unsloth, so you give up Unsloth's kernels for less code.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Does Unsloth work on multiple GPUs?
&lt;/h3&gt;

&lt;p&gt;Unsloth's README says it supports multi-GPU setups. For most QLoRA jobs up to 70B, one GPU is enough by its own VRAM table, and a single card avoids the communication overhead entirely.&lt;/p&gt;

&lt;h3&gt;
  
  
  Do I need a Hugging Face token?
&lt;/h3&gt;

&lt;p&gt;Only for gated models. Unsloth publishes copies of many open models under its &lt;a href="https://huggingface.co/unsloth" rel="noopener noreferrer"&gt;Hugging Face organization&lt;/a&gt;. For a gated one, store your token as a Nodus Secret and pass it with &lt;code&gt;--secret&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can I use Unsloth's Docker image instead of pip?
&lt;/h3&gt;

&lt;p&gt;Unsloth publishes an &lt;a href="https://unsloth.ai/docs/get-started/install/docker" rel="noopener noreferrer"&gt;official Docker image&lt;/a&gt;, &lt;code&gt;unsloth/unsloth&lt;/code&gt;, built mainly for running Jupyter and Unsloth Studio locally. Nodus runs prebuilt public registry images, but test the image's startup command before a long run.&lt;/p&gt;

&lt;h3&gt;
  
  
  How do I keep a large dataset from uploading on every run?
&lt;/h3&gt;

&lt;p&gt;Put it in a Nodus Volume once with &lt;code&gt;nodus volume put&lt;/code&gt;, then mount it with &lt;code&gt;--volume NAME:/data:ro&lt;/code&gt;. Only the code folder uploads with each run.&lt;/p&gt;

&lt;h3&gt;
  
  
  What do I do with the adapter afterwards?
&lt;/h3&gt;

&lt;p&gt;Load it back with &lt;code&gt;FastLanguageModel.from_pretrained&lt;/code&gt; pointed at the adapter folder, or merge it into 16-bit weights with Unsloth's &lt;code&gt;save_pretrained_merged&lt;/code&gt;. The &lt;a href="https://www.nodus-compute.ai/blog/vram-needed-for-70b-model/" rel="noopener noreferrer"&gt;VRAM guide&lt;/a&gt; covers what serving the merged model needs.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/fine-tune-with-unsloth-on-cloud-gpu/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>python</category>
      <category>llm</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>How do you train a PyTorch model on multiple GPUs?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Wed, 28 Oct 2026 01:38:50 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/how-do-you-train-a-pytorch-model-on-multiple-gpus-493o</link>
      <guid>https://dev.to/viswaretas_kotra/how-do-you-train-a-pytorch-model-on-multiple-gpus-493o</guid>
      <description>&lt;p&gt;Wrap your model in DistributedDataParallel (DDP) if it fits on one GPU, or shard it with FSDP if it doesn't, and start one process per GPU with &lt;code&gt;torchrun&lt;/code&gt;. On Nodus, &lt;code&gt;nodus run --gpu H100:8 -- torchrun train.py&lt;/code&gt; runs that script on all eight GPUs of one machine with no launcher flags, and &lt;code&gt;--nodes 2 --launcher torchrun&lt;/code&gt; spreads it across two machines. Fill one machine before you add a second: the second machine buys wall-clock time, not a cheaper run.&lt;/p&gt;

&lt;p&gt;This post walks through the three decisions in order: which wrapper, how to launch it, and when more than one machine is worth paying for. The code follows the PyTorch tutorials and the Nodus docs; the memory and cost figures are our own arithmetic, shown in full so you can redo it for your model.&lt;/p&gt;

&lt;h2&gt;
  
  
  Should you use DataParallel, DDP or FSDP?
&lt;/h2&gt;

&lt;p&gt;Use DDP by default and skip &lt;code&gt;nn.DataParallel&lt;/code&gt;. The &lt;a href="https://docs.pytorch.org/tutorials/intermediate/ddp_tutorial.html" rel="noopener noreferrer"&gt;PyTorch DDP tutorial&lt;/a&gt; explains why: DataParallel is a single process with many threads, so it fights the Python GIL and only works on one machine, while DDP runs one process per GPU and works across machines too.&lt;/p&gt;

&lt;p&gt;DDP gives every GPU a full copy of the model. Each one trains on a different slice of the batch, then an all-reduce averages the gradients so every copy stays identical. That is simple and fast, but it means the whole training state has to fit on each GPU.&lt;/p&gt;

&lt;p&gt;FSDP removes that limit. The &lt;a href="https://docs.pytorch.org/tutorials/intermediate/FSDP_tutorial.html" rel="noopener noreferrer"&gt;PyTorch FSDP tutorial&lt;/a&gt; describes it as sharding model parameters, gradients and optimizer states across GPUs, which "makes it feasible to train models that cannot fit on a single GPU." Each GPU holds only its shard and gathers a layer's full weights just before it needs them.&lt;/p&gt;

&lt;p&gt;The decision rule we use: if the model, its gradients and the optimizer state fit on one GPU with room for activations, use DDP. If they don't, use FSDP. If even FSDP is tight, look at LoRA before you add hardware.&lt;/p&gt;

&lt;h2&gt;
  
  
  How much memory does each GPU need with DDP and FSDP?
&lt;/h2&gt;

&lt;p&gt;Full training with Adam in mixed precision costs about 16 bytes per parameter before activations. That figure comes from the &lt;a href="https://arxiv.org/abs/1910.02054" rel="noopener noreferrer"&gt;ZeRO paper&lt;/a&gt;: 2 bytes for 16-bit weights, 2 for gradients and 12 for the FP32 master weights plus Adam's two moments. DDP keeps all 16 bytes on every GPU. FSDP with full sharding divides them by the number of GPUs.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Model&lt;/th&gt;
&lt;th&gt;Model state per GPU with DDP&lt;/th&gt;
&lt;th&gt;FSDP on 8 GPUs&lt;/th&gt;
&lt;th&gt;FSDP on 16 GPUs&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;1B parameters&lt;/td&gt;
&lt;td&gt;16 GB&lt;/td&gt;
&lt;td&gt;2 GB&lt;/td&gt;
&lt;td&gt;1 GB&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;8B parameters&lt;/td&gt;
&lt;td&gt;128 GB&lt;/td&gt;
&lt;td&gt;16 GB&lt;/td&gt;
&lt;td&gt;8 GB&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;70B parameters&lt;/td&gt;
&lt;td&gt;1,120 GB&lt;/td&gt;
&lt;td&gt;140 GB&lt;/td&gt;
&lt;td&gt;70 GB&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The math is parameters x 16 bytes, divided by the GPU count for FSDP. Activations, temporary all-gather buffers and the CUDA context come on top, so treat these as floors.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fqj7gxschak1ffaszqdjr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fqj7gxschak1ffaszqdjr.png" alt="Model state per GPU for full training with Adam: 1B with DDP 16 GB, 1B with FSDP on 8 GPUs 2 GB, 8B with DDP 128 GB, 8B with FSDP on 8 GPUs 16 GB, 70B with FSDP on 8 GPUs 140 GB, 70B with FSDP on 16 GPUs 70 GB." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;On 80 GB GPUs, an 8B model needs FSDP and a 70B model needs more than one 8-GPU machine of them.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Read it against an 80 GB NVIDIA H100. A 1B model fits comfortably with DDP. An 8B model does not fit at 128 GB, but drops to 16 GB per GPU with FSDP on one 8-GPU machine. A full 70B run needs 140 GB per GPU even when sharded over 8 GPUs, so on H100s it needs two machines.&lt;/p&gt;

&lt;p&gt;Even then, 70 GB on each of 16 GPUs leaves little room for activations. That is why our &lt;a href="https://www.nodus-compute.ai/blog/vram-needed-for-70b-model/" rel="noopener noreferrer"&gt;VRAM guide for 70B models&lt;/a&gt; points full 70B fine-tuning at one machine with 8 NVIDIA B200s instead: a bigger single machine beats a second small one.&lt;/p&gt;
&lt;h2&gt;
  
  
  What does a DDP training script look like?
&lt;/h2&gt;

&lt;p&gt;Four changes turn a single-GPU script into a DDP script: start a process group, pin each process to its GPU, wrap the model, and give each process its own slice of the data. This sketch follows the DDP tutorial's pattern:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;

&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;torch&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;torch.distributed&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;dist&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;torch.nn.parallel&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;DistributedDataParallel&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;DDP&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;torch.utils.data&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;DataLoader&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;torch.utils.data.distributed&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;DistributedSampler&lt;/span&gt;

&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;init_process_group&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;nccl&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;local_rank&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;int&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;environ&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;LOCAL_RANK&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
&lt;span class="n"&gt;torch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;cuda&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;set_device&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;local_rank&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;DDP&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;build_model&lt;/span&gt;&lt;span class="p"&gt;().&lt;/span&gt;&lt;span class="nf"&gt;cuda&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;local_rank&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;device_ids&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;local_rank&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
&lt;span class="n"&gt;sampler&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;DistributedSampler&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;dataset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;loader&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;DataLoader&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;dataset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;batch_size&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;32&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sampler&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;sampler&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;opt&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;torch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;optim&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;AdamW&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parameters&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;lr&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;1e-4&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;epoch&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="nf"&gt;range&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;epochs&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;sampler&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;set_epoch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;epoch&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;loader&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;loss&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;loss_fn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;model&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;cuda&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;local_rank&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;cuda&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;local_rank&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
        &lt;span class="n"&gt;opt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;zero_grad&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="n"&gt;loss&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;backward&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="n"&gt;opt&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;step&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

&lt;span class="n"&gt;dist&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;destroy_process_group&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;build_model&lt;/code&gt;, &lt;code&gt;dataset&lt;/code&gt;, &lt;code&gt;epochs&lt;/code&gt; and &lt;code&gt;loss_fn&lt;/code&gt; are yours. Two lines are easy to miss. &lt;a href="https://docs.pytorch.org/docs/stable/data.html#torch.utils.data.distributed.DistributedSampler" rel="noopener noreferrer"&gt;&lt;code&gt;DistributedSampler&lt;/code&gt;&lt;/a&gt; stops every GPU from training on the same examples, and &lt;code&gt;sampler.set_epoch(epoch)&lt;/code&gt; reshuffles each epoch; without it, PyTorch's own docstring warns, the same ordering is used every time.&lt;/p&gt;

&lt;p&gt;The batch size above is per GPU. On 8 GPUs the effective batch is 8 x 32 = 256, so revisit your learning rate when you scale out.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do you switch the same script to FSDP?
&lt;/h2&gt;

&lt;p&gt;Replace the DDP wrapper with &lt;code&gt;fully_shard&lt;/code&gt; from FSDP2, applied to each transformer block first and then to the whole model. The FSDP tutorial uses exactly this order:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;torch.distributed.fsdp&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;fully_shard&lt;/span&gt;

&lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;build_model&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;layer&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;layers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="nf"&gt;fully_shard&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;layer&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="nf"&gt;fully_shard&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;opt&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;torch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;optim&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;AdamW&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parameters&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;lr&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mf"&gt;1e-4&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Sharding per block matters. It lets FSDP gather one block's weights, run it and free them again, so only one block is ever whole on a GPU. Create the optimizer after sharding so it sees the sharded parameters. The data loading and training loop stay the same as the DDP version.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do you launch it on one machine with several GPUs?
&lt;/h2&gt;

&lt;p&gt;Run the script under &lt;code&gt;torchrun&lt;/code&gt;, which starts one process per GPU and sets &lt;code&gt;RANK&lt;/code&gt;, &lt;code&gt;LOCAL_RANK&lt;/code&gt; and &lt;code&gt;WORLD_SIZE&lt;/code&gt; for each. On your own machine you pass &lt;code&gt;--nproc-per-node&lt;/code&gt;. On Nodus you ask for the GPUs and leave the flags off:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;nodus run &lt;span class="nt"&gt;--gpu&lt;/span&gt; H100:8 &lt;span class="nt"&gt;--max-cost&lt;/span&gt; 250 &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="nt"&gt;--&lt;/span&gt; torchrun train.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The Nodus GPU guide explains why no flags are needed: Nodus sets &lt;code&gt;PET_NPROC_PER_NODE&lt;/code&gt; to the GPU count, so &lt;code&gt;torchrun&lt;/code&gt; starts one process per GPU, and &lt;code&gt;/dev/shm&lt;/code&gt; is already sized for NCCL. &lt;code&gt;--max-cost&lt;/code&gt; caps the spend in dollars, here just above the $208.00 estimate worked out below, and the same guide shows a &lt;code&gt;--dry-run&lt;/code&gt; that prints the estimate before anything starts.&lt;/p&gt;

&lt;h2&gt;
  
  
  When is a second machine worth it?
&lt;/h2&gt;

&lt;p&gt;Add a machine when one machine cannot hold the job or cannot finish it in time. More GPUs rarely make a run cheaper, because the gradient traffic between machines is slower than inside one, so each GPU does a little less useful work.&lt;/p&gt;

&lt;p&gt;Here is a worked example. Say a run takes 10 hours on one machine with 8 H100s. H100s are listed at $2.60/hr on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, so that is 80 GPU-hours, or $208.00.&lt;/p&gt;

&lt;p&gt;Now run it on two machines. The cost depends on scaling efficiency, the share of perfect speed-up you actually get, which you have to measure for your own model and network.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Setup&lt;/th&gt;
&lt;th&gt;Wall-clock&lt;/th&gt;
&lt;th&gt;GPU-hours&lt;/th&gt;
&lt;th&gt;Cost at $2.60/GPU-hour&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;1 machine, 8 GPUs&lt;/td&gt;
&lt;td&gt;10.0 h&lt;/td&gt;
&lt;td&gt;80.0&lt;/td&gt;
&lt;td&gt;$208.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;2 machines, 16 GPUs, 90% efficiency&lt;/td&gt;
&lt;td&gt;5.6 h&lt;/td&gt;
&lt;td&gt;88.9&lt;/td&gt;
&lt;td&gt;$231.11&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;2 machines, 16 GPUs, 75% efficiency&lt;/td&gt;
&lt;td&gt;6.7 h&lt;/td&gt;
&lt;td&gt;106.7&lt;/td&gt;
&lt;td&gt;$277.33&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Wall-clock is 10 hours divided by (2 x efficiency); GPU-hours is 16 times that. Prices checked October 27, 2026. The efficiencies are assumptions for the example, not measurements.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Faqoeg1lh242i8yuod5iv.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Faqoeg1lh242i8yuod5iv.png" alt="Cost of a 10-hour, 8 x H100 job at $2.60 per GPU-hour: $208.00 on one machine, $231.11 on two machines at 90% scaling efficiency, and $277.33 at 75%." width="800" height="304"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Two machines finish sooner but cost 11% to 33% more in this example.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;So the second machine is a time purchase. At 90% efficiency you pay $23.11 more to get the result about 4.4 hours sooner. If nobody is waiting on it, one machine is the cheaper answer.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you run one job across several machines on Nodus?
&lt;/h2&gt;

&lt;p&gt;Add &lt;code&gt;--nodes&lt;/code&gt; and &lt;code&gt;--launcher torchrun&lt;/code&gt; to the same command. The &lt;a href="https://www.nodus-compute.ai/docs/guides/multi-node/" rel="noopener noreferrer"&gt;Nodus multi-node guide&lt;/a&gt; uses this as its two-node smoke test:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;nodus run &lt;span class="nt"&gt;--name&lt;/span&gt; torchrun-2-node &lt;span class="nt"&gt;--gpu&lt;/span&gt; H100 &lt;span class="nt"&gt;--nodes&lt;/span&gt; 2 &lt;span class="nt"&gt;--launcher&lt;/span&gt; torchrun &lt;span class="nt"&gt;--max-cost&lt;/span&gt; 2.00 &lt;span class="nt"&gt;--&lt;/span&gt; torchrun train.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Nodus acquires every machine, checks that they can reach each other, and only then starts your command on all of them together. It sets &lt;code&gt;MASTER_ADDR&lt;/code&gt;, &lt;code&gt;NODE_RANK&lt;/code&gt; and the &lt;code&gt;PET_*&lt;/code&gt; variables that &lt;code&gt;torchrun&lt;/code&gt; reads, so the script itself does not change. &lt;code&gt;--gpus-per-node 8&lt;/code&gt; gives each machine eight GPUs, and &lt;code&gt;--total-gpus&lt;/code&gt; lets Nodus pick the machine shape for you.&lt;/p&gt;

&lt;p&gt;Multi-node training is in Beta, and the docs are specific about its limits. Gangs top out at 8 machines.&lt;/p&gt;

&lt;p&gt;By default all machines are placed on one private network in one region. If you allow wider placement, traffic between machines on public addresses is not encrypted in the Beta. The guide also says a two-machine DDP result does not yet qualify cross-machine FSDP or several GPUs per machine across machines, so check the exercised combinations before a large FSDP run.&lt;/p&gt;

&lt;h2&gt;
  
  
  What happens when one GPU in a multi-GPU run fails?
&lt;/h2&gt;

&lt;p&gt;The whole run stops, because every process waits on the others in each all-reduce. That makes checkpoints more important as you add GPUs: one lost machine out of two throws away everything since the last save.&lt;/p&gt;

&lt;p&gt;On Nodus, the multi-node guide describes the recovery. If a machine is lost or reclaimed, Nodus stops every rank, keeps the surviving machines, replaces only the lost one, and restarts all ranks with the latest checkpoint restored into the state directory. Your script has to save there and load from it on start; the checkpoint guide in the Nodus docs shows how, and our post on &lt;a href="https://www.nodus-compute.ai/blog/automatic-checkpointing-and-resume-for-training/" rel="noopener noreferrer"&gt;automatic checkpointing and resume&lt;/a&gt; compares how other platforms handle it.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  How many GPUs can torchrun use on one machine?
&lt;/h3&gt;

&lt;p&gt;As many as the machine has, one process per GPU. On Nodus, the GPU count you ask for is 1, 2, 4 or 8 per machine, and anything larger needs a multi-node job.&lt;/p&gt;

&lt;h3&gt;
  
  
  Do I need NVLink for multi-GPU training?
&lt;/h3&gt;

&lt;p&gt;DDP and FSDP run over NCCL on whatever links the GPUs share, so NVLink is not required. It does speed up the gradient and all-gather traffic, which matters most for FSDP because it moves weights as well as gradients.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can I use Hugging Face Accelerate or DeepSpeed instead of torchrun on Nodus?
&lt;/h3&gt;

&lt;p&gt;Nodus accepts &lt;code&gt;Accelerate&lt;/code&gt; and &lt;code&gt;Deepspeed&lt;/code&gt; as launchers for multi-node jobs, setting their variables or a hostfile, but the multi-node guide marks them accepted in the Beta and qualified later. &lt;code&gt;torchrun&lt;/code&gt;, Ray and verl are documented without that caveat.&lt;/p&gt;

&lt;h3&gt;
  
  
  Should I use LoRA instead of FSDP for a large model?
&lt;/h3&gt;

&lt;p&gt;Often, yes. LoRA freezes the base weights and trains small adapters, so gradients and optimizer state shrink to a fraction of a percent of the model. If LoRA quality is good enough for your task, it usually fits a model on one GPU that full training would need a cluster for.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/multi-gpu-training-pytorch/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>pytorch</category>
      <category>machinelearning</category>
      <category>deeplearning</category>
      <category>gpu</category>
    </item>
    <item>
      <title>What are the best Hugging Face AutoTrain alternatives?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Tue, 27 Oct 2026 23:11:38 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/what-are-the-best-hugging-face-autotrain-alternatives-1caj</link>
      <guid>https://dev.to/viswaretas_kotra/what-are-the-best-hugging-face-autotrain-alternatives-1caj</guid>
      <description>&lt;p&gt;Hugging Face now marks AutoTrain as no longer maintained, so the best alternative depends on whether you want a managed recipe, a fine-tuning API or your own training script. Nodus is the closest managed replacement for LLM fine-tuning: its recipes take a Hugging Face model and a dataset, run on the GPU you choose and resume from the latest checkpoint if a machine is lost. Pick Together AI if you want to pay per token without choosing hardware, and Axolotl or Unsloth if you want to run open-source trainers on hardware you already have.&lt;/p&gt;

&lt;p&gt;We build Nodus, so read this with that in mind. Every fact about another product links to its own pricing page or docs, and the arithmetic is written out so you can redo it with today's prices.&lt;/p&gt;

&lt;h2&gt;
  
  
  What happened to Hugging Face AutoTrain?
&lt;/h2&gt;

&lt;p&gt;AutoTrain still works, but it is frozen. The &lt;a href="https://huggingface.co/docs/autotrain/index" rel="noopener noreferrer"&gt;AutoTrain docs&lt;/a&gt; and the &lt;a href="https://github.com/huggingface/autotrain-advanced" rel="noopener noreferrer"&gt;GitHub README&lt;/a&gt; both open with the same notice: no new features will be added and bugs will not be fixed. Hugging Face recommends Axolotl, TRL or &lt;code&gt;transformers.Trainer&lt;/code&gt; instead.&lt;/p&gt;

&lt;p&gt;The tool itself is free. You pay only for compute, per the &lt;a href="https://huggingface.co/docs/autotrain/cost" rel="noopener noreferrer"&gt;AutoTrain cost page&lt;/a&gt;. Locally that is your own hardware; as a Space it is billed per minute for the Hugging Face Spaces hardware you attach. The &lt;a href="https://huggingface.co/docs/autotrain/quickstart_spaces" rel="noopener noreferrer"&gt;Spaces quickstart&lt;/a&gt; has you duplicate the AutoTrain Space, pick hardware, and train from the web UI, with logs in TensorBoard and the model pushed to a Hub repository.&lt;/p&gt;

&lt;p&gt;That setup is pleasant for a first fine-tune. The trouble starts when a new model architecture or library version needs a fix that will not come, or when you want a GPU that the Spaces hardware list does not offer.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do the AutoTrain alternatives compare?
&lt;/h2&gt;

&lt;p&gt;The short version: Nodus and Together AI replace the managed part, Modal, RunPod and Vertex AI replace the compute part, and Axolotl or Unsloth replace the trainer.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Option&lt;/th&gt;
&lt;th&gt;What you get&lt;/th&gt;
&lt;th&gt;How you pay&lt;/th&gt;
&lt;th&gt;GPU choice&lt;/th&gt;
&lt;th&gt;If a machine is lost&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;AutoTrain on Spaces&lt;/td&gt;
&lt;td&gt;No-code UI, frozen codebase&lt;/td&gt;
&lt;td&gt;Per minute of Spaces hardware&lt;/td&gt;
&lt;td&gt;Spaces list (T4 up to A100 and RTX PRO 6000)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;PAUSE_ON_FAILURE&lt;/code&gt; pauses the Space on a failed run&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Nodus&lt;/td&gt;
&lt;td&gt;Managed recipes: SFT, LoRA, QLoRA, DPO, ORPO, KTO, distillation, GRPO&lt;/td&gt;
&lt;td&gt;Prepaid credits, listed hourly price per GPU&lt;/td&gt;
&lt;td&gt;You allow GPU types, or take the recipe's preset&lt;/td&gt;
&lt;td&gt;Resumes from the latest full checkpoint&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Together AI&lt;/td&gt;
&lt;td&gt;Fine-tuning API&lt;/td&gt;
&lt;td&gt;Per 1M training tokens, minimum charge per job&lt;/td&gt;
&lt;td&gt;None, managed&lt;/td&gt;
&lt;td&gt;Not stated on the pricing page&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal&lt;/td&gt;
&lt;td&gt;Run your own trainer as Python functions&lt;/td&gt;
&lt;td&gt;Per second&lt;/td&gt;
&lt;td&gt;You pick per function&lt;/td&gt;
&lt;td&gt;Restarts the function on the same input; you write checkpoints&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod&lt;/td&gt;
&lt;td&gt;GPU pods for your own trainer&lt;/td&gt;
&lt;td&gt;Per second&lt;/td&gt;
&lt;td&gt;You pick the pod&lt;/td&gt;
&lt;td&gt;You handle restarts; data without a network volume is lost if the balance hits $0&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Google Vertex AI&lt;/td&gt;
&lt;td&gt;Custom training jobs&lt;/td&gt;
&lt;td&gt;Machine type plus attached accelerator&lt;/td&gt;
&lt;td&gt;You pick machine and accelerator&lt;/td&gt;
&lt;td&gt;Not stated on the pricing page&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Axolotl or Unsloth&lt;/td&gt;
&lt;td&gt;Open-source trainers (Apache-2.0)&lt;/td&gt;
&lt;td&gt;Free; you supply hardware&lt;/td&gt;
&lt;td&gt;Whatever you run them on&lt;/td&gt;
&lt;td&gt;Your own checkpoint and restart logic&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Checked October 27, 2026: &lt;a href="https://huggingface.co/docs/autotrain/cost" rel="noopener noreferrer"&gt;AutoTrain cost&lt;/a&gt;, &lt;a href="https://huggingface.co/docs/autotrain/quickstart_spaces" rel="noopener noreferrer"&gt;Spaces quickstart&lt;/a&gt;, &lt;a href="https://huggingface.co/pricing#spaces" rel="noopener noreferrer"&gt;Hugging Face pricing&lt;/a&gt;, &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;Nodus training guide&lt;/a&gt;, &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;Together AI pricing&lt;/a&gt;, &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt; and &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemption docs&lt;/a&gt;, &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;RunPod pricing&lt;/a&gt; and &lt;a href="https://docs.runpod.io/pods/pricing" rel="noopener noreferrer"&gt;Pods pricing docs&lt;/a&gt;, &lt;a href="https://cloud.google.com/vertex-ai/pricing" rel="noopener noreferrer"&gt;Vertex AI pricing&lt;/a&gt;, &lt;a href="https://github.com/axolotl-ai-cloud/axolotl" rel="noopener noreferrer"&gt;Axolotl&lt;/a&gt; and &lt;a href="https://github.com/unslothai/unsloth" rel="noopener noreferrer"&gt;Unsloth&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Which is cheapest for a 10-hour fine-tune on one A100?
&lt;/h2&gt;

&lt;p&gt;At listed prices, Nodus is the cheapest of the hourly options we priced for the same GPU, and AutoTrain on Spaces sits near the top. We priced one NVIDIA A100 80GB for 10 hours, GPU compute only, from each company's own page.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Where it runs&lt;/th&gt;
&lt;th&gt;Listed price for one A100 80GB&lt;/th&gt;
&lt;th&gt;10 hours&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Hugging Face Spaces (AutoTrain), A100 large&lt;/td&gt;
&lt;td&gt;$2.50/hr&lt;/td&gt;
&lt;td&gt;$25.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modal&lt;/td&gt;
&lt;td&gt;$0.000694/s, or $2.4984/hr&lt;/td&gt;
&lt;td&gt;$24.98&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Secure Cloud, A100 SXM&lt;/td&gt;
&lt;td&gt;$1.79/hr&lt;/td&gt;
&lt;td&gt;$17.90&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RunPod Community Cloud, A100 SXM&lt;/td&gt;
&lt;td&gt;$1.39/hr&lt;/td&gt;
&lt;td&gt;$13.90&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Nodus&lt;/td&gt;
&lt;td&gt;$1.09/hr&lt;/td&gt;
&lt;td&gt;$10.90&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 27, 2026 on the &lt;a href="https://huggingface.co/pricing#spaces" rel="noopener noreferrer"&gt;Hugging Face pricing page&lt;/a&gt;, &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;Modal pricing&lt;/a&gt;, &lt;a href="https://www.runpod.io/pricing" rel="noopener noreferrer"&gt;RunPod pricing&lt;/a&gt; and the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;, where the A100 80GB is listed at $1.09/hr. Modal's per-second rate is multiplied by 36,000 seconds.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffasz01jed7wgc7rx9jji.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffasz01jed7wgc7rx9jji.png" alt="Listed cost of 10 hours on one NVIDIA A100 80GB, checked October 27, 2026: Hugging Face Spaces for AutoTrain $25.00, Modal $24.98, RunPod Secure Cloud $17.90, RunPod Community Cloud $13.90 and Nodus $10.90." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The same 10 A100-hours cost $14.10 less on Nodus than on an AutoTrain Space.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Google Vertex AI is harder to put in one line because it adds charges together. Its &lt;a href="https://cloud.google.com/vertex-ai/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt; lists the A100 80GB accelerator for custom training at $3.92808/hr in Iowa (us-central1), so $39.28 for 10 hours before the cost of the machine type is added.&lt;/p&gt;

&lt;p&gt;Together AI does not bill by the hour at all. Its &lt;a href="https://www.together.ai/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt; charges for tokens processed: training set size times epochs, plus any evaluation tokens. A LoRA fine-tune of Llama 3.1 8B is $0.34 per 1M tokens with a $4.00 minimum.&lt;/p&gt;

&lt;p&gt;A 20M-token dataset trained for 3 epochs is 60M tokens, so 60 x $0.34 = $20.40. That is predictable, and you never size a GPU, but you also cannot make it cheaper by picking a smaller one.&lt;/p&gt;
&lt;h2&gt;
  
  
  Does your GPU choice matter for a LoRA run?
&lt;/h2&gt;

&lt;p&gt;Yes, and often more than the platform. A recipe that lets you pick the GPU lets you skip paying H100 prices for a job that a 24 GB card finishes for less.&lt;/p&gt;

&lt;p&gt;Here is how we checked it. The &lt;a href="https://www.nodus-compute.ai/docs/reference/runtimes/sft/" rel="noopener noreferrer"&gt;&lt;code&gt;nodus/sft&lt;/code&gt; runtime page&lt;/a&gt; publishes the measured seconds per step that its dry-run estimate uses: 0.45 on H100, 0.7 on A100 80GB, 1 on L40S, 1.2 on RTX 4090 and 1.3 on RTX A6000. Multiply by 2,000 steps, the step count in the docs' own LoRA example, then by the listed price on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;GPU&lt;/th&gt;
&lt;th&gt;Time for 2,000 steps&lt;/th&gt;
&lt;th&gt;Listed price&lt;/th&gt;
&lt;th&gt;Estimated GPU cost&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;RTX 4090&lt;/td&gt;
&lt;td&gt;40 min&lt;/td&gt;
&lt;td&gt;$0.290/hr&lt;/td&gt;
&lt;td&gt;$0.19&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;RTX A6000&lt;/td&gt;
&lt;td&gt;43.3 min&lt;/td&gt;
&lt;td&gt;$0.333/hr&lt;/td&gt;
&lt;td&gt;$0.24&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;A100 80GB&lt;/td&gt;
&lt;td&gt;23.3 min&lt;/td&gt;
&lt;td&gt;$1.090/hr&lt;/td&gt;
&lt;td&gt;$0.42&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;L40S&lt;/td&gt;
&lt;td&gt;33.3 min&lt;/td&gt;
&lt;td&gt;$0.793/hr&lt;/td&gt;
&lt;td&gt;$0.44&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;H100 SXM&lt;/td&gt;
&lt;td&gt;15 min&lt;/td&gt;
&lt;td&gt;$2.600/hr&lt;/td&gt;
&lt;td&gt;$0.65&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fmum5sqppnw69w5fymiiy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fmum5sqppnw69w5fymiiy.png" alt="Estimated GPU cost of 2,000 nodus/sft steps from the runtime's published step times and Nodus listed prices: RTX 4090 $0.19, RTX A6000 $0.24, A100 80GB $0.42, L40S $0.44 and H100 SXM $0.65." width="800" height="372"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;The H100 finishes first, but the RTX 4090 does the same 2,000 steps for less than a third of the cost.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;This is arithmetic from published numbers, not a bill from a run. Real step time moves with model size, sequence length and batch size, which is why the dry run prices your actual configuration. The rule still holds: if the job fits in 24 GB and nobody is waiting on it, take the cheaper card. If someone is waiting, the H100 buys back 25 minutes for 46 cents.&lt;/p&gt;

&lt;p&gt;The runtime's presets already make that call for small models. Qwen3-1.7B with LoRA defaults to one RTX 4090, L40S or RTX A6000, while full fine-tuning of Qwen3-8B defaults to 8 x H100.&lt;/p&gt;
&lt;h2&gt;
  
  
  What happens when a fine-tuning run fails halfway?
&lt;/h2&gt;

&lt;p&gt;On Nodus the run resumes from its last checkpoint. On a GPU you rent directly, the restart is your job.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;training guide&lt;/a&gt; says recovery uses full checkpoints with optimizer, scheduler and RNG state, and the &lt;code&gt;sft&lt;/code&gt; runtime saves one every 200 steps by default (&lt;code&gt;saveSteps&lt;/code&gt;). If a node in a multi-node run is lost, the whole group restarts from the latest checkpoint every rank committed, up to 3 times. The spending cap behaves the same way: when &lt;code&gt;maxCostUSD&lt;/code&gt; is reached the run is suspended, not failed, and raising the cap resumes it from the checkpoint. Our post on &lt;a href="https://www.nodus-compute.ai/blog/automatic-checkpointing-and-resume-for-training/" rel="noopener noreferrer"&gt;automatic checkpointing and resume&lt;/a&gt; compares how other platforms handle this.&lt;/p&gt;

&lt;p&gt;Modal's &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;preemption docs&lt;/a&gt; say a preempted function restarts on the same input and recommend checkpointing long training runs yourself. RunPod's &lt;a href="https://docs.runpod.io/pods/pricing" rel="noopener noreferrer"&gt;Pods pricing docs&lt;/a&gt; say pods stop when your balance reaches $0, and pods without a network volume lose their data. With Axolotl or Unsloth, noticing the failure and restarting from a saved checkpoint is up to you.&lt;/p&gt;
&lt;h2&gt;
  
  
  Where is AutoTrain still the better choice?
&lt;/h2&gt;

&lt;p&gt;AutoTrain is still a reasonable pick in a few specific cases.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;You want a point-and-click UI. Nodus starts runs from the CLI or Python SDK; its console shows runs, curves and costs but does not launch them.&lt;/li&gt;
&lt;li&gt;Your task is not an LLM. AutoTrain covers image classification, tabular data, token classification, extractive question answering and more, per its docs and README. The Nodus training catalog is built around language models.&lt;/li&gt;
&lt;li&gt;You run it locally on your own GPU, where the AutoTrain cost page says it costs nothing.&lt;/li&gt;
&lt;li&gt;You have a working AutoTrain config for a model it already supports, and you need one more run of it.&lt;/li&gt;
&lt;li&gt;Your whole workflow lives on the Hugging Face Hub, and a Space that pushes the model and TensorBoard logs straight to a repository is the point.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If none of those apply, the maintenance notice is the deciding fact. A trainer that will not get fixes is a risk for anything you plan to repeat.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you fine-tune a Hugging Face model on Nodus instead?
&lt;/h2&gt;

&lt;p&gt;Upload your data to a Volume, write a TrainingJob that names the Hugging Face model, dry-run it, then apply it. These commands and the manifest are copied from the &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;Nodus training guide&lt;/a&gt; and the &lt;a href="https://www.nodus-compute.ai/docs/guides/volumes/" rel="noopener noreferrer"&gt;Volumes guide&lt;/a&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus create volume support-chats &lt;span class="nt"&gt;--size&lt;/span&gt; 100Gi
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus volume put support-chats ./chats.jsonl /
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1beta1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TrainingJob&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-sft&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;runtime&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/sft&lt;/span&gt;
  &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf://Qwen/Qwen3-0.6B@c1899de289a04d12100db370d81485cdf75e47ca&lt;/span&gt;
    &lt;span class="na"&gt;secret&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf-token&lt;/span&gt;            &lt;span class="c1"&gt;# only for gated repositories&lt;/span&gt;
  &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;volume&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-chats&lt;/span&gt;       &lt;span class="c1"&gt;# a Volume holding chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;format&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;JSONL&lt;/span&gt;
    &lt;span class="na"&gt;columns&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;question&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;completion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;answer&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;parameters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2000&lt;/span&gt;
    &lt;span class="na"&gt;lora&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;16&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;alpha&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;32&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;20.00"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml &lt;span class="nt"&gt;--dry-run&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; yaml     &lt;span class="c"&gt;# status.estimate: cost to completion, first hold, start time&lt;/span&gt;
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; sft.yaml
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus get tj &lt;span class="nt"&gt;-w&lt;/span&gt;
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus &lt;span class="nb"&gt;cp &lt;/span&gt;tj/support-sft:outputs/adapter/adapter_model.safetensors ./adapter_model.safetensors
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;columns&lt;/code&gt; map plays the same role as AutoTrain's column mapping, so an AutoTrain dataset usually moves over without edits. Pin the model to a 40-character commit. Nodus imports that revision once into a read-only Volume and runs the trainer offline, so billed GPU time is never spent downloading weights. To pin a GPU type, add &lt;code&gt;resources: {gpu: {type: [h100-sxm-80g], count: 1}}&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;From Python, the same run is one line from the &lt;a href="https://www.nodus-compute.ai/docs/reference/python/nodus-recipes-finetune/" rel="noopener noreferrer"&gt;finetune recipe reference&lt;/a&gt;, after &lt;code&gt;import nodus&lt;/code&gt; and &lt;code&gt;from nodus.recipes import finetune&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="n"&gt;sft&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;finetune&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sft&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Qwen/Qwen3-1.7B&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;nodus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Volume&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;from_name&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;support-chats&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
                   &lt;span class="n"&gt;lora&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;finetune&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nc"&gt;LoRA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;16&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;max_steps&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;2000&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;run&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;gpu&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;H100&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;max_cost&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;TrainingJobs are in Beta, so fields can still change before v1. In our &lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-modal-fine-tuning-benchmark/" rel="noopener noreferrer"&gt;fine-tuning benchmark against Modal&lt;/a&gt;, a pilot with one small model on one NVIDIA L4, Nodus produced byte-identical weights at 67% lower charges for the successful run. If you already have cloud credits, the &lt;a href="https://www.nodus-compute.ai/docs/guides/pools/cloud-accounts/" rel="noopener noreferrer"&gt;cloud accounts docs&lt;/a&gt; show how Nodus can run work in your own AWS, GCP or Azure account, or in a RunPod or Lambda account you connect with its API key.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Is AutoTrain shutting down?
&lt;/h3&gt;

&lt;p&gt;Hugging Face has not said it is shutting down; its docs say it is no longer maintained. The Space and the &lt;code&gt;autotrain-advanced&lt;/code&gt; package still work, but bugs will not be fixed and new model architectures will not be added.&lt;/p&gt;

&lt;h3&gt;
  
  
  What does Hugging Face recommend instead of AutoTrain?
&lt;/h3&gt;

&lt;p&gt;Its notice names Axolotl, TRL and &lt;code&gt;transformers.Trainer&lt;/code&gt;. Those are trainers, not compute, so you still need a GPU to run them on. The Nodus &lt;code&gt;sft&lt;/code&gt; runtime page lists its checkpoint format as HFTrainer, so the concepts carry over.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can I run Axolotl or Unsloth on Nodus?
&lt;/h3&gt;

&lt;p&gt;Yes, as your own code. A custom TrainingRuntime can run any image, and Nodus decides when to checkpoint the state directory your trainer writes to. See &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;Bring your own runtime&lt;/a&gt; in the training guide, or our &lt;a href="https://www.nodus-compute.ai/blog/modal-alternatives-for-training-2026/" rel="noopener noreferrer"&gt;Modal alternatives for training&lt;/a&gt; post for running scripts as plain Jobs.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can a coding agent start the fine-tune for me?
&lt;/h3&gt;

&lt;p&gt;Yes. &lt;code&gt;nodus mcp install claude&lt;/code&gt; adds the Nodus MCP server to Claude Code, and the agent must accept a dry-run estimate before it creates anything. Runs stay inside your account's budgets and the job's &lt;code&gt;maxCostUSD&lt;/code&gt; cap.&lt;/p&gt;

&lt;h3&gt;
  
  
  Is there a free tier like AutoTrain's local mode?
&lt;/h3&gt;

&lt;p&gt;Running Axolotl, Unsloth or AutoTrain on your own GPU costs nothing beyond the hardware. Modal's $0 plan includes $30 of free credits a month, per its &lt;a href="https://modal.com/pricing" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;. Nodus uses prepaid credits; current GPU rates are on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;, and our &lt;a href="https://www.nodus-compute.ai/blog/runpod-alternatives-2026/" rel="noopener noreferrer"&gt;RunPod alternatives&lt;/a&gt; post compares hourly rates more widely.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/hugging-face-autotrain-alternatives/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>llm</category>
      <category>finetuning</category>
      <category>huggingface</category>
    </item>
    <item>
      <title>Continued pretraining vs fine-tuning: which do you need?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Tue, 27 Oct 2026 20:45:42 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/continued-pretraining-vs-fine-tuning-which-do-you-need-51l5</link>
      <guid>https://dev.to/viswaretas_kotra/continued-pretraining-vs-fine-tuning-which-do-you-need-51l5</guid>
      <description>&lt;p&gt;Use continued pretraining when the model lacks knowledge or vocabulary from your domain, and use fine-tuning when it knows enough but behaves wrong for your task. Nodus runs both from one managed runtime, &lt;code&gt;nodus/sft&lt;/code&gt;, and in our October 2026 pilots it produced byte-identical weights to Modal at 42.5% lower charges for continued pretraining and 67% lower for fine-tuning. Most teams need fine-tuning only; continued pretraining pays off when you hold a large body of domain text the base model has rarely seen.&lt;/p&gt;

&lt;h2&gt;
  
  
  What is the difference between continued pretraining and fine-tuning?
&lt;/h2&gt;

&lt;p&gt;The difference is the data and what the model learns from it. Continued pretraining keeps the original next-token objective and feeds the model raw, unlabeled text: contracts, papers, internal docs, a codebase. The model absorbs vocabulary, style and facts from that corpus.&lt;/p&gt;

&lt;p&gt;Fine-tuning trains on labeled examples: prompt and completion pairs, chat transcripts, or chosen and rejected answers for preference methods. It teaches the model how to respond, in what format, and when to refuse.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;What you want&lt;/th&gt;
&lt;th&gt;Method&lt;/th&gt;
&lt;th&gt;Data you need&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Domain vocabulary and facts&lt;/td&gt;
&lt;td&gt;Continued pretraining&lt;/td&gt;
&lt;td&gt;Raw text&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;A fixed output format or tone&lt;/td&gt;
&lt;td&gt;Supervised fine-tuning (SFT)&lt;/td&gt;
&lt;td&gt;Prompt/completion pairs&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Better instruction following on your task&lt;/td&gt;
&lt;td&gt;SFT&lt;/td&gt;
&lt;td&gt;Chat examples&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Answers people prefer&lt;/td&gt;
&lt;td&gt;DPO, ORPO or KTO&lt;/td&gt;
&lt;td&gt;Chosen/rejected pairs or labels&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fvxo12e4hncaq2e06qtd6.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fvxo12e4hncaq2e06qtd6.png" alt="Continued pretraining fits new domain vocabulary and raw unlabeled text; fine-tuning fits behavior, format and instruction changes with prompt/completion data." width="800" height="332"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Start from the data you actually have: raw text points to pretraining, examples point to fine-tuning.&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  When does continued pretraining pay off?
&lt;/h2&gt;

&lt;p&gt;It pays off when the base model keeps misreading your domain, not when it merely answers in the wrong shape. The strongest evidence is Gururangan et al., &lt;a href="https://arxiv.org/abs/2004.10964" rel="noopener noreferrer"&gt;"Don't Stop Pretraining" (ACL 2020)&lt;/a&gt;. Across four domains (biomedical papers, computer science papers, news and reviews) and eight classification tasks, a second pretraining phase on in-domain text improved results in both high- and low-resource settings.&lt;/p&gt;

&lt;p&gt;Our decision rule has three checks:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The base model mangles your terms, abbreviations or code conventions even with good prompts.&lt;/li&gt;
&lt;li&gt;You have far more raw domain text than labeled examples, typically hundreds of millions of tokens or more.&lt;/li&gt;
&lt;li&gt;The knowledge is stable. Facts that change weekly belong in retrieval, not in weights.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;If all three hold, continued pretraining is worth the compute. If only the first holds, try fine-tuning on a few thousand examples first and measure. Continued pretraining can also erode general skills, so keep a held-out general benchmark next to your domain test. Our post on &lt;a href="https://www.nodus-compute.ai/blog/catastrophic-forgetting-after-fine-tuning/" rel="noopener noreferrer"&gt;catastrophic forgetting after fine-tuning&lt;/a&gt; shows how to measure that.&lt;/p&gt;
&lt;h2&gt;
  
  
  When is fine-tuning enough?
&lt;/h2&gt;

&lt;p&gt;Fine-tuning is enough when the model already understands the material and you need consistent behavior. Typical cases are a JSON schema it must always follow, a support tone, a classification label set, or tool calls in your format.&lt;/p&gt;

&lt;p&gt;It needs much less data than people expect. Zhou et al. fine-tuned a 65B model on 1,000 curated examples in &lt;a href="https://arxiv.org/abs/2305.11206" rel="noopener noreferrer"&gt;"LIMA: Less Is More for Alignment"&lt;/a&gt; and reported strong instruction following.&lt;/p&gt;

&lt;p&gt;Quality and coverage of the examples matter more than raw count. LoRA and QLoRA train a small adapter instead of every weight, which cuts memory enough to fit larger models on one GPU (see &lt;a href="https://www.nodus-compute.ai/blog/vram-needed-for-70b-model/" rel="noopener noreferrer"&gt;how much VRAM a 70B model needs&lt;/a&gt;).&lt;/p&gt;
&lt;h2&gt;
  
  
  How much more does continued pretraining cost?
&lt;/h2&gt;

&lt;p&gt;Cost grows with the tokens you train on, so continued pretraining usually costs tens of times more than fine-tuning. Here is the math for a 7B model, full-weight training on one NVIDIA H100, listed at $2.60/hr on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt; (price checked October 27, 2026).&lt;/p&gt;

&lt;p&gt;Training compute is roughly 6 x parameters x tokens floating-point operations, the standard estimate from &lt;a href="https://arxiv.org/abs/2001.08361" rel="noopener noreferrer"&gt;Kaplan et al. (2020)&lt;/a&gt;. NVIDIA lists the H100 SXM at &lt;a href="https://www.nvidia.com/en-us/data-center/h100/" rel="noopener noreferrer"&gt;1,979 BF16 teraFLOPS with sparsity&lt;/a&gt;, about 990 without it.&lt;/p&gt;

&lt;p&gt;We assume 40% utilization, so about 396 teraFLOPS of useful work. That utilization is an assumption, not a measurement; your real number depends on sequence length, kernels and batch size.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Continued pretraining on 1 billion tokens: 6 x 7B x 1B = 4.2 x 10^19 FLOPs. At 396 teraFLOPS that is 106,000 seconds, about 29.5 hours, or about $77.&lt;/li&gt;
&lt;li&gt;Fine-tuning on 50,000 examples of about 500 tokens (25 million tokens): 1.05 x 10^18 FLOPs, about 0.74 hours, or about $1.92.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The ratio is 40 to 1 because the token count is 40 to 1. Change the assumed utilization and both numbers move together, so the ratio holds. LoRA lowers the fine-tuning side further because frozen weights need no weight gradients or optimizer state.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fcl4j2dtodxi4109l50gd.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fcl4j2dtodxi4109l50gd.png" alt="At an assumed 40% utilization on one H100 at $2.60/hr, continued pretraining on 1 billion tokens costs about $77 and full fine-tuning on 25 million tokens about $1.92." width="800" height="304"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Same model, same GPU, same rate: the 40x gap comes entirely from tokens trained.&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  How did Nodus compare with Modal on both jobs?
&lt;/h2&gt;

&lt;p&gt;We ran the same continued-pretraining and fine-tuning recipes on Nodus and on Modal with Qwen2.5-0.5B on one NVIDIA L4. In both pilots the exported weights matched byte for byte, so the only difference was the bill.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Pilot&lt;/th&gt;
&lt;th&gt;Nodus charge&lt;/th&gt;
&lt;th&gt;Modal charge&lt;/th&gt;
&lt;th&gt;Nodus share of Modal&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-modal-fine-tuning-benchmark/" rel="noopener noreferrer"&gt;Supervised fine-tuning&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;$0.048696&lt;/td&gt;
&lt;td&gt;$0.14746756&lt;/td&gt;
&lt;td&gt;33.0%&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-modal-continued-pretraining-benchmark/" rel="noopener noreferrer"&gt;Continued pretraining&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;$0.121164&lt;/td&gt;
&lt;td&gt;$0.21090282&lt;/td&gt;
&lt;td&gt;57.5%&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Recorded charges for successful attempts before credits, October 2026 pilots, one seed and one accepted run per platform. The pilots used standalone Nodus Jobs, not TrainingJobs. In the chart, Modal's charge is the 100.0% baseline.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhx7j5sa8d9jqmsqnj343.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhx7j5sa8d9jqmsqnj343.png" alt="Nodus recorded 33.0% of Modal's charge for supervised fine-tuning and 57.5% for continued pretraining, with identical weights in both pilots." width="800" height="328"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Identical weights in both pilots, so the lower charge bought the same model.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Two caveats from those posts. The fine-tuning pilot also had one failed Nodus attempt; counting it, Nodus cost 24.7% less than Modal instead of 67%. And a 0.5B model on one L4 says nothing certain about a 70B run, so treat the ratio as evidence for this job size only.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you run continued pretraining on Nodus?
&lt;/h2&gt;

&lt;p&gt;Use the &lt;code&gt;nodus/sft&lt;/code&gt; runtime with &lt;code&gt;task: Pretrain&lt;/code&gt; on the spec, and point it at a Volume of text rows. The default &lt;code&gt;initialization: Continued&lt;/code&gt; starts from the model's existing weights, and &lt;code&gt;method: Full&lt;/code&gt; trains every weight rather than an adapter.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1beta1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TrainingJob&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;domain-pretrain&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;runtime&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/sft&lt;/span&gt;
  &lt;span class="na"&gt;task&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Pretrain&lt;/span&gt;
  &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf://Qwen/Qwen3-0.6B@c1899de289a04d12100db370d81485cdf75e47ca&lt;/span&gt;
  &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;volume&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;domain-corpus&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;corpus.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;format&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;JSONL&lt;/span&gt;
  &lt;span class="na"&gt;parameters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;5000&lt;/span&gt;
    &lt;span class="na"&gt;initialization&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Continued&lt;/span&gt;
    &lt;span class="na"&gt;method&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Full&lt;/span&gt;
    &lt;span class="na"&gt;packing&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
    &lt;span class="na"&gt;appendEOS&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;50.00"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Set &lt;code&gt;appendEOS: false&lt;/code&gt; when your rows are chunks or paragraphs rather than whole documents, so the trainer does not insert an end-of-sequence token after every row. Packing fills each training block with text instead of padding. Price it before it runs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight console"&gt;&lt;code&gt;&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus login
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; pretrain.yaml &lt;span class="nt"&gt;--dry-run&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; yaml
&lt;span class="gp"&gt;$&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;nodus apply &lt;span class="nt"&gt;-f&lt;/span&gt; pretrain.yaml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The dry run returns a cost estimate, and &lt;code&gt;maxCostUSD&lt;/code&gt; stops the run at the cap. Long pretraining runs checkpoint with optimizer state, so a lost GPU resumes the run instead of restarting it.&lt;/p&gt;

&lt;h2&gt;
  
  
  How do you run fine-tuning on Nodus?
&lt;/h2&gt;

&lt;p&gt;Same runtime, no &lt;code&gt;task&lt;/code&gt; field, and a &lt;code&gt;columns&lt;/code&gt; map onto your prompt and completion fields. The &lt;code&gt;lora&lt;/code&gt; block makes it an adapter run; leave it out for full fine-tuning.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;apiVersion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus.dev/v1beta1&lt;/span&gt;
&lt;span class="na"&gt;kind&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TrainingJob&lt;/span&gt;
&lt;span class="na"&gt;metadata&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-sft&lt;/span&gt;
&lt;span class="na"&gt;spec&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;runtime&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;nodus/sft&lt;/span&gt;
  &lt;span class="na"&gt;model&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;hf://Qwen/Qwen3-0.6B@c1899de289a04d12100db370d81485cdf75e47ca&lt;/span&gt;
  &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;volume&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;support-chats&lt;/span&gt;
    &lt;span class="na"&gt;path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;chats.jsonl&lt;/span&gt;
    &lt;span class="na"&gt;format&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;JSONL&lt;/span&gt;
    &lt;span class="na"&gt;columns&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;prompt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;question&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;completion&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;answer&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;parameters&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2000&lt;/span&gt;
    &lt;span class="na"&gt;lora&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;{&lt;/span&gt;&lt;span class="nv"&gt;r&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;16&lt;/span&gt;&lt;span class="pi"&gt;,&lt;/span&gt; &lt;span class="nv"&gt;alpha&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;32&lt;/span&gt;&lt;span class="pi"&gt;}&lt;/span&gt;
  &lt;span class="na"&gt;maxCostUSD&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;20.00"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;a href="https://www.nodus-compute.ai/docs/guides/training/" rel="noopener noreferrer"&gt;Training (Beta) guide&lt;/a&gt; covers validation-based checkpoint selection and preference tuning. A model you trained earlier can be the input of the next TrainingJob, which is how you chain the two methods.&lt;/p&gt;

&lt;h2&gt;
  
  
  Should you do both, and in what order?
&lt;/h2&gt;

&lt;p&gt;Do both only when you have both kinds of data, and always pretrain first. Gururangan et al. found that adapting to the task's own unlabeled text helped even after domain-adaptive pretraining, so the stages stack.&lt;/p&gt;

&lt;p&gt;A sequence that works: continued pretraining on the domain corpus, then SFT on labeled examples, then preference tuning if you have chosen and rejected answers. Each stage starts from the previous stage's exported model. Evaluate after every stage on the same held-out set, plus a general benchmark, so you can see which stage helped and which one cost you general skill.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  What is the difference between pretraining and fine-tuning?
&lt;/h3&gt;

&lt;p&gt;Pretraining teaches a model language and facts from huge amounts of raw text with a next-token objective. Fine-tuning adjusts an already pretrained model with labeled examples so it behaves a certain way. Continued pretraining sits between them: more raw-text pretraining, but on your domain.&lt;/p&gt;

&lt;h3&gt;
  
  
  Can continued pretraining replace retrieval (RAG)?
&lt;/h3&gt;

&lt;p&gt;Not for facts that change. Weights are a snapshot, and retraining every time a document changes is slow and expensive. Teams often pretrain for vocabulary and reasoning style, then use retrieval for current facts.&lt;/p&gt;

&lt;h3&gt;
  
  
  What learning rate should continued pretraining use?
&lt;/h3&gt;

&lt;p&gt;Lower than the original pretraining peak, with a warmup, because a high rate on a narrow corpus speeds up forgetting. Run a short sweep on a small slice and keep the setting whose held-out general score drops least.&lt;/p&gt;

&lt;h3&gt;
  
  
  How do you know continued pretraining worked?
&lt;/h3&gt;

&lt;p&gt;Measure perplexity on held-out domain text before and after, then check a general benchmark for forgetting. In our continued-pretraining pilot, held-out perplexity fell 21.8%, from 21.0 to 16.4, on both Nodus and Modal.&lt;/p&gt;

&lt;h3&gt;
  
  
  Which is cheaper on Nodus?
&lt;/h3&gt;

&lt;p&gt;Fine-tuning, by roughly the ratio of tokens trained. Both run at the same listed GPU rates on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;pricing page&lt;/a&gt;, and the dry run shows the estimate before anything is charged.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/continued-pretraining-vs-fine-tuning/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>llm</category>
      <category>ai</category>
      <category>finetuning</category>
    </item>
    <item>
      <title>Which GPU platforms checkpoint and resume training for you?</title>
      <dc:creator>Viswaretas Kotra</dc:creator>
      <pubDate>Tue, 27 Oct 2026 18:12:40 +0000</pubDate>
      <link>https://dev.to/viswaretas_kotra/which-gpu-platforms-checkpoint-and-resume-training-for-you-nm9</link>
      <guid>https://dev.to/viswaretas_kotra/which-gpu-platforms-checkpoint-and-resume-training-for-you-nm9</guid>
      <description>&lt;p&gt;We checked five platforms against their own docs. Nodus, AWS SageMaker managed spot training and Modal all restart a preempted training run and hand it back the files it saved, but only Nodus also tells your program when to save, including an urgent request when capacity is about to be reclaimed. RunPod Pods and Vast.ai interruptible instances keep your disk and leave the restart to you.&lt;/p&gt;

&lt;p&gt;One thing is true everywhere: no platform resumes your training loop for you. Your script still has to look for its last checkpoint when it starts and load it.&lt;/p&gt;

&lt;p&gt;What differs is everything around that load, and that is the part that decides whether a run finishes unattended. This post compares the platforms. For the code itself, see &lt;a href="https://www.nodus-compute.ai/blog/resume-training-after-spot-preemption/" rel="noopener noreferrer"&gt;how to make spot GPU training survive preemption&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Who saves, who restarts and who resumes?
&lt;/h2&gt;

&lt;p&gt;Recovery after a lost GPU has five steps. Something has to trigger a save, copy it off the machine, start a new machine, put the files back and continue the loop. Here is who does each one, according to each platform's own documentation.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Step&lt;/th&gt;
&lt;th&gt;Nodus&lt;/th&gt;
&lt;th&gt;Modal&lt;/th&gt;
&lt;th&gt;AWS SageMaker managed spot&lt;/th&gt;
&lt;th&gt;RunPod Pods&lt;/th&gt;
&lt;th&gt;Vast.ai interruptible&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Trigger a save before a reclaim&lt;/td&gt;
&lt;td&gt;Platform sends an urgent checkpoint request&lt;/td&gt;
&lt;td&gt;Your exit handler, 30 s grace&lt;/td&gt;
&lt;td&gt;Your code or framework callback&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Scheduled saves&lt;/td&gt;
&lt;td&gt;Platform-timed (&lt;code&gt;interval: auto&lt;/code&gt;) or fixed, from 1 min to 6 h&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;td&gt;Your code or framework callback&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Copy the checkpoint off the machine&lt;/td&gt;
&lt;td&gt;Platform, from &lt;code&gt;/nodus/state&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;Platform, once you write to a Volume&lt;/td&gt;
&lt;td&gt;Platform, syncs &lt;code&gt;/opt/ml/checkpoints&lt;/code&gt; to S3&lt;/td&gt;
&lt;td&gt;You, onto a network volume&lt;/td&gt;
&lt;td&gt;You, to your own storage&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Start a replacement&lt;/td&gt;
&lt;td&gt;Platform, on another machine&lt;/td&gt;
&lt;td&gt;Platform, on the same input&lt;/td&gt;
&lt;td&gt;Platform, on the next Spot instance&lt;/td&gt;
&lt;td&gt;You, or a beta migration you trigger&lt;/td&gt;
&lt;td&gt;Same instance resumes when it regains priority&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Put the files back&lt;/td&gt;
&lt;td&gt;Platform restores the state directory&lt;/td&gt;
&lt;td&gt;Volume mounted again&lt;/td&gt;
&lt;td&gt;Platform copies S3 back to the local path&lt;/td&gt;
&lt;td&gt;Attach the network volume&lt;/td&gt;
&lt;td&gt;Disk stays on that machine&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Continue the training loop&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;td&gt;Your code (some built-in algorithms do it)&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;td&gt;Your code&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Sources: &lt;a href="https://www.nodus-compute.ai/docs/guides/checkpoints/" rel="noopener noreferrer"&gt;Nodus checkpoints&lt;/a&gt;, &lt;a href="https://www.nodus-compute.ai/docs/concepts/attempts-and-recovery/" rel="noopener noreferrer"&gt;Nodus attempts and recovery&lt;/a&gt;, &lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;Modal preemption&lt;/a&gt;, &lt;a href="https://modal.com/docs/guide/lifecycle-functions" rel="noopener noreferrer"&gt;Modal exit handlers&lt;/a&gt;, &lt;a href="https://modal.com/docs/guide/volumes" rel="noopener noreferrer"&gt;Modal Volumes&lt;/a&gt;, &lt;a href="https://docs.aws.amazon.com/sagemaker/latest/dg/model-checkpoints.html" rel="noopener noreferrer"&gt;SageMaker checkpoints&lt;/a&gt;, &lt;a href="https://docs.aws.amazon.com/sagemaker/latest/dg/model-managed-spot-training.html" rel="noopener noreferrer"&gt;SageMaker managed spot training&lt;/a&gt;, &lt;a href="https://docs.runpod.io/pods/maintenance-and-outages" rel="noopener noreferrer"&gt;RunPod maintenance and data safety&lt;/a&gt;, &lt;a href="https://docs.runpod.io/pods/troubleshooting/pod-migration" rel="noopener noreferrer"&gt;RunPod Pod migration&lt;/a&gt;, &lt;a href="https://docs.vast.ai/guides/instances/choosing/instance-types" rel="noopener noreferrer"&gt;Vast.ai instance types&lt;/a&gt;, &lt;a href="https://docs.vast.ai/guides/reference/faq/rental-types" rel="noopener noreferrer"&gt;Vast.ai rental types FAQ&lt;/a&gt;. Checked October 27, 2026.&lt;/p&gt;

&lt;p&gt;Read across the rows and three groups appear. Nodus, SageMaker and Modal own the restart and the file handling once your code writes to the right place. Only Nodus also owns the save trigger and the interval. On RunPod and Vast.ai the platform keeps your disk, and the rest of recovery is yours to build.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does Nodus do automatically?
&lt;/h2&gt;

&lt;p&gt;Nodus treats every run as a series of attempts. When a provider reclaims interruptible capacity, Nodus sends your program an urgent checkpoint request and starts preparing a replacement machine at the same time. The replacement only starts once the old machine is provably gone, so two machines never write the same checkpoint. A checkpoint committed during the notice still counts.&lt;/p&gt;

&lt;p&gt;Between notices, &lt;code&gt;interval: auto&lt;/code&gt; sets the cadence from how often the capacity is interrupted and how long your saves take. A run gets at least four checkpoints, and checkpointing takes no more than about a tenth of the run time. A machine that stops sending heartbeats gets a replacement prepared after 20 seconds. On shared capacity it is replaced after 60 seconds of silence.&lt;/p&gt;

&lt;p&gt;Recovery is bounded. A run fails with &lt;code&gt;NoProgress&lt;/code&gt; after two attempts in a row make no progress, and it gets 8 recoveries by default, or 3 for distributed Jobs. Your code's share is to write its state to &lt;code&gt;/nodus/state&lt;/code&gt; and read it back on start. Hugging Face Trainer users can set &lt;code&gt;integration: HFTrainer&lt;/code&gt; and Nodus answers the checkpoint requests from inside Trainer.&lt;/p&gt;

&lt;h2&gt;
  
  
  Does AWS SageMaker managed spot training do the same?
&lt;/h2&gt;

&lt;p&gt;Mostly. With managed spot training and a checkpoint S3 URI, SageMaker syncs your local checkpoint directory to Amazon S3 during training. After a Spot interruption it resumes the job on the next Spot instance and copies the checkpoints back before your script starts (&lt;a href="https://docs.aws.amazon.com/sagemaker/latest/dg/model-checkpoints.html" rel="noopener noreferrer"&gt;SageMaker checkpoints&lt;/a&gt;). AWS Deep Learning Containers and some built-in algorithms checkpoint without script changes.&lt;/p&gt;

&lt;p&gt;Plan around two limits. First, managed spot training never falls back to on-demand instances. If Spot capacity is unavailable, the job waits until &lt;code&gt;MaxWaitTimeInSeconds&lt;/code&gt; and then stops (&lt;a href="https://docs.aws.amazon.com/sagemaker/latest/dg/model-managed-spot-training.html" rel="noopener noreferrer"&gt;managed spot training&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;Second, the save itself is still triggered by your code or framework, since SageMaker copies what is in the directory rather than asking your program for a consistent state. Our &lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-aws-sagemaker/" rel="noopener noreferrer"&gt;Nodus vs AWS SageMaker&lt;/a&gt; post compares the two on price and setup.&lt;/p&gt;

&lt;h2&gt;
  
  
  What does Modal handle, and what is left to you?
&lt;/h2&gt;

&lt;p&gt;Modal restarts. Every Modal Function is preemptible by default, &lt;code&gt;nonpreemptible&lt;/code&gt; is not supported for GPU Functions, and after a preemption Modal restarts the Function on the same input (&lt;a href="https://modal.com/docs/guide/preemption" rel="noopener noreferrer"&gt;Modal preemption&lt;/a&gt;). On a preemption your exit handler runs with a 30 second grace period (&lt;a href="https://modal.com/docs/guide/lifecycle-functions" rel="noopener noreferrer"&gt;lifecycle functions&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;The saving is yours. Modal's &lt;a href="https://modal.com/docs/examples/long-training" rel="noopener noreferrer"&gt;long-training example&lt;/a&gt; has your code write checkpoints to a Volume, look for the latest one on start, and use &lt;code&gt;modal.Retries&lt;/code&gt; to restart.&lt;/p&gt;

&lt;p&gt;Volumes commit in the background every few seconds, so once a file is written it leaves the machine without extra work (&lt;a href="https://modal.com/docs/guide/volumes" rel="noopener noreferrer"&gt;Modal Volumes&lt;/a&gt;). A single call can run for at most 24 hours (&lt;a href="https://modal.com/docs/guide/timeouts" rel="noopener noreferrer"&gt;timeouts&lt;/a&gt;), which is another reason long runs need checkpoints there. The full comparison is in &lt;a href="https://www.nodus-compute.ai/blog/nodus-vs-modal/" rel="noopener noreferrer"&gt;Nodus vs Modal&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  What about RunPod and Vast.ai?
&lt;/h2&gt;

&lt;p&gt;Both keep your data and leave recovery to you. RunPod's docs say hardware failures can happen without warning, that container storage is lost when a Pod is interrupted, restarted, stopped or terminated, and that long jobs should checkpoint every hour to every few hours onto a network volume (&lt;a href="https://docs.runpod.io/pods/maintenance-and-outages" rel="noopener noreferrer"&gt;RunPod data safety&lt;/a&gt;). If your Pod's GPU is taken while it is stopped, a beta migration you trigger copies &lt;code&gt;/workspace&lt;/code&gt; to a new Pod with a new ID (&lt;a href="https://docs.runpod.io/pods/troubleshooting/pod-migration" rel="noopener noreferrer"&gt;Pod migration&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;Vast.ai interruptible instances are stopped when a higher bid wins, which kills running processes. A paused instance resumes when it regains priority, possibly after a long wait, and the docs tell you to save to disk often and checkpoint long jobs (&lt;a href="https://docs.vast.ai/guides/reference/faq/rental-types" rel="noopener noreferrer"&gt;rental types FAQ&lt;/a&gt;).&lt;/p&gt;

&lt;h2&gt;
  
  
  What does a lost checkpoint interval cost?
&lt;/h2&gt;

&lt;p&gt;On every platform, an interruption without a save on the notice costs the work since the last scheduled checkpoint. That is half an interval on average and a full interval at worst. We priced it on two common training shapes using rates listed on the &lt;a href="https://www.nodus-compute.ai/pricing/" rel="noopener noreferrer"&gt;Nodus pricing page&lt;/a&gt;: 8 x NVIDIA H100 SXM at $2.60/hr each, or $20.80/hr, and 8 x NVIDIA B200 at $5.50/hr each, or $44.00/hr.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Checkpoint every&lt;/th&gt;
&lt;th&gt;Average redone work&lt;/th&gt;
&lt;th&gt;8 x H100 ($20.80/hr)&lt;/th&gt;
&lt;th&gt;8 x B200 ($44.00/hr)&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;15 min&lt;/td&gt;
&lt;td&gt;7.5 min&lt;/td&gt;
&lt;td&gt;$2.60&lt;/td&gt;
&lt;td&gt;$5.50&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;30 min&lt;/td&gt;
&lt;td&gt;15 min&lt;/td&gt;
&lt;td&gt;$5.20&lt;/td&gt;
&lt;td&gt;$11.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;60 min&lt;/td&gt;
&lt;td&gt;30 min&lt;/td&gt;
&lt;td&gt;$10.40&lt;/td&gt;
&lt;td&gt;$22.00&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;120 min&lt;/td&gt;
&lt;td&gt;60 min&lt;/td&gt;
&lt;td&gt;$20.80&lt;/td&gt;
&lt;td&gt;$44.00&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Prices checked October 27, 2026. Our calculation: half the interval times the hourly rate of the run. Save time and restart time are not included.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F1t0uf9bzgq905pindtfy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F1t0uf9bzgq905pindtfy.png" alt="Average redone work per interruption: on 8 x H100 it is $2.60 at a 15-minute interval, $5.20 at 30, $10.40 at 60 and $20.80 at 120; on 8 x B200 it is $5.50, $11.00, $22.00 and $44.00." width="800" height="416"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;Each extra hour between checkpoints adds about half an hour of redone work to every interruption.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Now take one run: 24 hours on 8 x H100, which is 192 GPU-hours or $499.20 at $2.60/hr, interrupted three times. Saving every 2 hours redoes $62.40 of work on average (3 x 1 h x $20.80), or $124.80 at worst (3 x 2 h x $20.80). That is 12.5% to 25% on top of the run. Saving every 30 minutes cuts that to $15.60 on average (3 x 0.25 h x $20.80) and $31.20 at worst, before counting the extra save time.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhi8hz68jnr1cnd202w0u.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhi8hz68jnr1cnd202w0u.png" alt="Redone work from three interruptions on a 24-hour, 8 x H100 run costing $499.20: $62.40 on average and $124.80 at worst when saving every 2 hours, $15.60 and $31.20 when saving every 30 minutes." width="800" height="328"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;A save that commits during the reclaim notice takes the redone work close to zero, which is why who triggers it matters.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;A save on the reclaim notice changes the picture, but only if the save fits the warning. On Nodus the platform sends the request as soon as the notice arrives. On Modal you write that save in an exit handler with 30 seconds. On the others you watch for the notice yourself.&lt;/p&gt;

&lt;p&gt;When the save does not fit, the scheduled interval is what you pay, and &lt;a href="https://www.nodus-compute.ai/blog/resume-training-after-spot-preemption/" rel="noopener noreferrer"&gt;our interval model&lt;/a&gt; shows how to pick it.&lt;/p&gt;
&lt;h2&gt;
  
  
  Which one should you pick?
&lt;/h2&gt;

&lt;p&gt;Our decision rule, from the table above:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Your runs are short, or a lost hour is cheap, and you are happy to restart by hand: any platform works. RunPod on-demand Pods are dedicated to you and cannot be displaced by other users (&lt;a href="https://docs.runpod.io/pods/pricing" rel="noopener noreferrer"&gt;Pod pricing&lt;/a&gt;).&lt;/li&gt;
&lt;li&gt;You want Spot prices and live in AWS, with data in S3: SageMaker managed spot training, accepting that it waits for Spot capacity rather than falling back.&lt;/li&gt;
&lt;li&gt;Your training is a Python function that fits Modal's model and its 24 hour call limit with retries: Modal, with your own save and resume code on a Volume.&lt;/li&gt;
&lt;li&gt;You want runs to finish unattended on the cheapest capacity, with the platform asking for saves and choosing the interval: Nodus.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Whether interruptible capacity pays off at all for your run is a separate question, covered in &lt;a href="https://www.nodus-compute.ai/blog/spot-vs-on-demand-gpus/" rel="noopener noreferrer"&gt;spot vs on-demand GPUs&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;
  
  
  Where are the other platforms the better choice?
&lt;/h2&gt;

&lt;p&gt;SageMaker is the better fit when your training already runs on AWS Deep Learning Containers. Some frameworks there checkpoint without script changes, and your data in S3 and your AWS commitments stay where they are. Modal is the better fit for teams that already write Modal Functions, since background Volume commits make the copy step disappear.&lt;/p&gt;

&lt;p&gt;RunPod suits interactive work on a dedicated Pod, with a network volume that moves between Pods. Vast.ai's bidding lets you set your own price, and a paused instance keeps its disk on the same machine. If your job cannot checkpoint at all, an on-demand machine anywhere beats any recovery feature.&lt;/p&gt;
&lt;h2&gt;
  
  
  How do you turn it on with Nodus?
&lt;/h2&gt;

&lt;p&gt;Write your state to &lt;code&gt;/nodus/state&lt;/code&gt;, load it on start, and run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;nodus-compute
nodus login
nodus run &lt;span class="nt"&gt;--gpu&lt;/span&gt; H100:8 &lt;span class="nt"&gt;--interruptible&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;allow &lt;span class="nt"&gt;--checkpoint&lt;/span&gt; /nodus/state &lt;span class="nt"&gt;--max-cost&lt;/span&gt; 550 &lt;span class="nt"&gt;-d&lt;/span&gt; &lt;span class="nt"&gt;--&lt;/span&gt; torchrun &lt;span class="nt"&gt;--nproc_per_node&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;8 train.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;--interruptible&lt;/code&gt; accepts &lt;code&gt;allow&lt;/code&gt;, &lt;code&gt;prefer&lt;/code&gt; or &lt;code&gt;never&lt;/code&gt;. The &lt;code&gt;--max-cost&lt;/code&gt; cap stops the run at $550, a little above the $499.20 the 24-hour example costs at list price. &lt;code&gt;nodus describe job/&amp;lt;name&amp;gt;&lt;/code&gt; shows each attempt, why it ended and the latest checkpoint.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Does Nodus edit my command to add a resume flag?
&lt;/h3&gt;

&lt;p&gt;No. Nodus restores files, never process memory, and never adds resume flags. A restored attempt sets &lt;code&gt;NODUS_RESTORED=1&lt;/code&gt;, which your script can check before loading.&lt;/p&gt;

&lt;h3&gt;
  
  
  What happens when the run hits its &lt;code&gt;--max-cost&lt;/code&gt; cap?
&lt;/h3&gt;

&lt;p&gt;A checkpointed Nodus Job checkpoints and then suspends with reason &lt;code&gt;MaxCostReached&lt;/code&gt;. It continues from that checkpoint when you raise the cap, and a Job stopped by an empty balance resumes on its own once it is funded again.&lt;/p&gt;

&lt;h3&gt;
  
  
  Does SageMaker copy checkpoints I upload to S3 mid-job?
&lt;/h3&gt;

&lt;p&gt;No. Checkpoints already in S3 are copied into the container when the job starts, and files added to the S3 folder later are not. Deleting a checkpoint in the container also deletes it in S3.&lt;/p&gt;

&lt;h3&gt;
  
  
  How large can a Nodus checkpoint be?
&lt;/h3&gt;

&lt;p&gt;Up to 1 TiB by default (&lt;code&gt;maxSize: 1Ti&lt;/code&gt;), across up to 64 paths. After a Job finishes, Nodus keeps only its final checkpoint once seven days have passed.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://www.nodus-compute.ai/blog/automatic-checkpointing-and-resume-for-training/" rel="noopener noreferrer"&gt;Nodus blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>machinelearning</category>
      <category>devops</category>
      <category>cloud</category>
      <category>tutorial</category>
    </item>
  </channel>
</rss>
