SAM.gov API limits explained: keys, daily quotas and getting throttled
If SAM.gov API calls start failing after about ten requests, nothing is broken. You've hit your key's daily quota. Here's how the limits work, how to raise yours and how to need fewer calls.
The official rate limits
GSA publishes the daily limits for SAM.gov API keys in one table (on the Entity Management, Exclusions and Extracts API pages):
| Account type | Key type | Daily limit |
|---|---|---|
| Non-federal user with no role in SAM.gov | Personal API key | 10 requests/day |
| Non-federal user with a role in SAM.gov | Personal API key | 1,000 requests/day |
| Federal user | Personal API key | 1,000 requests/day |
| Non-federal system account | System account API key | 1,000 requests/day |
| Federal system account | System account API key | 10,000 requests/day |
The Get Opportunities API page only says daily requests are "limited based on the federal or non-federal or general roles". Most people who generate a key straight after signing up are in the first row: 10 requests a day. That's why issue reports to GSA describe being "throttled after 8โ9 calls".
Getting a key, and getting a bigger one
- Personal key: sign in to SAM.gov, open your Account Details page (
sam.gov/workspace/profile/account-details) and use the "Public API Key" field. A one-time password is emailed to you before the key is shown. - From 10 to 1,000 a day: ask your entity's administrator to give you a role in an entity registered in SAM.gov.
- System accounts (1,000 or 10,000 a day) are requested in your SAM.gov workspace and need approval.
- Expiry: SAM.gov's Terms of Use say to update your API key every 90 days, and GSA's docs for some APIs state keys are valid for 90 days. If an old key is suddenly rejected, generate a new one first.
Common errors and traps
- 429 after a handful of calls. Users report HTTP 429 (Too Many Requests) once they're over quota. GSA doesn't document when the daily count resets, so budget per day rather than retrying in a tight loop.
- One result per call.
limitdefaults to 1. Setlimit=1000, the maximum. - Mandatory dates.
postedFromandpostedToare required (MM/dd/yyyy), at most one year apart. - Typos fail silently. The NAICS filter is
ncode, notnaics. A user in GSA's issue tracker reports that unknown parameters are ignored, so a misspelt filter returns everything. - Descriptions cost calls.
descriptionis a URL that needs your key appended, so fetching full text is one more keyed request per notice. Fetch it only for shortlisted notices.
A small client with a budget and backoff
import os, time, random, requests
URL = "https://api.sam.gov/opportunities/v2/search"
KEY = os.environ["SAM_API_KEY"]
DAILY_BUDGET = 10 # set to your tier from GSA's table
used = 0
def search(params, max_retries=4):
global used
for attempt in range(max_retries + 1):
if used >= DAILY_BUDGET:
raise RuntimeError("Daily SAM.gov budget used up; try tomorrow or use the extract")
used += 1
r = requests.get(URL, params={"api_key": KEY, "limit": 1000, **params}, timeout=60)
if r.status_code == 429 or r.status_code >= 500:
if attempt == max_retries:
r.raise_for_status()
wait = float(r.headers.get("Retry-After", 0)) or min(60, 2 ** attempt) + random.random()
time.sleep(wait)
continue
r.raise_for_status()
return r.json()
data = search({"postedFrom": "10/21/2026", "postedTo": "10/21/2026", "ncode": "541511"})
print(data.get("totalRecords"), len(data.get("opportunitiesData") or []))
Retries count against the budget too.
The keyless alternative: the public daily extract
For bulk or daily syncs you may not need the API at all. SAM.gov Data Services publishes the full Contract Opportunities list as a public CSV once a day, with no key and no quota:
https://sam.gov/api/prod/fileextractservices/v1/api/download/Contract%20Opportunities/datagov/ContractOpportunitiesFullCSV.csv?privacy=Public
It redirects to the file (use curl -L), it's large, it's encoded as Windows-1252, and it can be a day behind the website. Filter it locally and save your API quota for the notices you need in full. More detail: SAM.gov API: how it works.
We built this
Disclosure: Your Evenings Ltd built and sells this. It isn't an official government product and isn't affiliated with GSA or SAM.gov. SAM.gov & Grants.gov Scraper on the Apify Store reads the public daily extract for you, so you don't need a SAM.gov API key and don't use up your quota. It filters by keyword, NAICS, agency, set-aside, notice type and dates, can return only new notices on a schedule, and can track solicitations for amendments and deadline changes (SAM.gov amendment alerts).
FAQ
What is the SAM.gov API rate limit? It depends on your account. GSA's table gives 10 requests/day for a non-federal user with no role, 1,000/day for a non-federal user with a role, a federal user or a non-federal system account, and 10,000/day for a federal system account.
Why am I throttled after about 10 SAM.gov API calls? A personal key for a non-federal user with no role in an entity registered in SAM.gov is limited to 10 requests a day. Getting a role from your entity's administrator raises it to 1,000.
Where do I get a SAM.gov API key? On your SAM.gov Account Details page, in the "Public API Key" field. SAM.gov's Terms of Use say to update it every 90 days.
Can I get SAM.gov contract opportunities without an API key? Yes. SAM.gov Data Services publishes a public daily Contract Opportunities CSV extract that needs no key.
Product names and logos belong to their owners. Your Evenings Ltd is not affiliated with or endorsed by them. This product uses the Grants.gov API but is not endorsed or certified by the U.S. Department of Health and Human Services.