Bonfirehub APImississauga.bonfirehub.ca ↗
Fetch all open RFPs, RFTs, and ACANs from the City of Mississauga's Bonfire procurement portal, including titles, dates, documents, and contact details.
What is the Bonfirehub API?
The Mississauga Bonfire Hub API exposes a single endpoint, list_open_opportunities, that returns every currently open public procurement opportunity published on the City of Mississauga's Bonfire portal. Each record includes the opportunity title, reference number, solicitation type, department, open/close dates, questions-due deadline, supporting documents, and a variable set of detail-page fields such as bonding requirements, insurance, and site visit information.
curl -X GET 'https://api.parse.bot/scraper/7c96adf8-8770-4187-a103-50add01906ff/list_open_opportunities?project_type=RFP' \ -H 'X-API-Key: $PARSE_API_KEY'
Typed, relational, agent-ready
A generated client with real types, enums, and the links between objects — the structure a flat JSON response can't carry. Autocompletes in your editor and reads cleanly to coding agents.
- Fully typed · autocompletes
- Objects link to objects
- Typed errors & pagination
Typed Python client. Set up the SDK in your uv project, then pull this API’s typed client:
uv add parse-sdk uv run parse init uv run parse add --marketplace mississauga-bonfirehub-ca-api
uv run parse add --marketplace pulls a pinned snapshot of this canonical API — it won’t change underneath you. To customize it, subscribe and swap to your own copy.
"""Walkthrough: Mississauga Procurement Portal — list open opportunities."""
from parse_apis.mississauga_bonfirehub_ca_api import MississaugaProcurement, ParseError
client = MississaugaProcurement()
# Browse all open opportunities, capped to 5 total items.
try:
for opp in client.opportunities.list(limit=5):
print(opp.reference_number, opp.title)
print(f" Type: {opp.project_type} Dept: {opp.department}")
print(f" Closes: {opp.date_close} Documents: {opp.document_count}")
except ParseError as e:
print(f"Portal scrape failed ({e.code}): {e}")
# Drill into the first RFP to inspect its detail rows and documents.
rfp = client.opportunities.list(project_type="RFP", limit=1).first()
if rfp is not None:
print(f"\n--- {rfp.reference_number}: {rfp.title} ---")
for detail in rfp.details:
print(f" {detail.label}: {detail.value}")
for doc in rfp.documents[:3]:
print(f" Doc: {doc.name} ({doc.type}) created {doc.date_created}")
for cc in rfp.commodity_codes:
print(f" Commodity: [{cc.scheme}] {cc.code} — {cc.name}")
if rfp.contact_name is not None:
print(f" Contact: {rfp.contact_name} <{rfp.contact_email}>")
print("\nexercised: opportunities.list / opportunities.list(project_type=)")
Returns every opportunity currently shown on the portal's 'Open Public Opportunities' tab, enriched with its public detail page: title, reference number, solicitation type, department, description, open/questions-due/close dates, contact (when the City chooses to publish it), the solicitation-specific detail rows (bonding, insurance, site visit, addenda deadline, anticipated award, etc.), commodity codes, and the supporting document list (names, types, dates; file contents require a supplier login and are not returned). Closed, awarded and past opportunities are never included. One call costs one list request plus one detail-page request per open opportunity (hard-capped at 60; total_open reports the full count and detail_errors lists any opportunity whose detail page could not be read). All timestamps are UTC in YYYY-MM-DD HH:MM:SS form as published by the portal. An empty opportunities array means the City currently has nothing open (not observed during this build; the portal always had at least one open opportunity).
| Param | Type | Description |
|---|---|---|
| project_type | string | Optional case-insensitive solicitation type filter matched against each opportunity's project_type (the prefix of its reference number). Values seen this run: RFP, RFT, ACAN. Omitted = all open opportunities; an unrecognized value yields an empty list. |
{
"type": "object",
"fields": {
"count": "integer number of records returned (after project_type filter)",
"total_open": "integer number of open opportunities on the portal before filtering",
"detail_errors": "array of {project_id, reason} for detail pages that could not be read",
"opportunities": "array of open opportunity records (see sample for per-record keys)",
"timezone_note": "string describing the timestamp convention",
"details_fetched": "integer number of detail pages read successfully",
"opportunities[].url": "public detail page URL",
"opportunities[].status": "always 'Open' (only open opportunities are returned)",
"opportunities[].details": "array of {label, value} rows from the detail page (bonding, insurance, site visit, addenda deadline, etc.); label set varies by opportunity",
"opportunities[].documents": "array of {name, type, description, date_created} supporting documents listed on the detail page",
"opportunities[].project_id": "string portal project identifier",
"opportunities[].description": "project description text from the detail page, or null",
"opportunities[].project_type": "solicitation type code (RFP, RFT, ACAN, ...)",
"opportunities[].document_count": "integer number of documents listed",
"opportunities[].commodity_codes": "array of {scheme, code, name} commodity classifications",
"opportunities[].reference_number": "City solicitation reference, e.g. RFP-2026-0019",
"opportunities[].accepts_submissions": "boolean, whether the portal accepts online submissions",
"opportunities[].contact_name / contact_email": "buyer contact, null when the City hides contact info for that opportunity",
"opportunities[].date_open / date_questions_due / date_close / date_intent_to_bid_due / date_anticipated_evaluation / date_modified": "UTC timestamps 'YYYY-MM-DD HH:MM:SS' or null when the portal has no value"
},
"sample": {
"data": {
"count": 1,
"total_open": 4,
"detail_errors": [],
"opportunities": [
{
"url": "https://mississauga.bonfirehub.ca/opportunities/110173",
"tags": null,
"title": "Event Security Services for Mississauga Sports and Entertainment Centre",
"status": "Open",
"details": [
{
"label": "Deadline for Issuing Addenda",
"value": "2026-10-01"
},
{
"label": "Anticipated Award or Execution of Agreement",
"value": "November 1, 2026"
},
{
"label": "Is a Performance Bond required?",
"value": "No"
},
{
"label": "Additional Insurance Requirements",
"value": "Errors and Omissions Insurance $2,000,000.00 per claims made."
}
],
"date_open": "2026-09-11 20:30:00",
"documents": [
{
"name": "03 StandardTCs NonConstruction.pdf",
"type": "Documentation",
"description": null,
"date_created": "2026-03-16 13:19:41"
},
{
"name": "Solicitation Document",
"type": "Form",
"description": "Solicitation Builder",
"date_created": "2026-09-11 20:30:00"
}
],
"date_close": "2026-10-06 18:00:00",
"department": "Community Services - Recreation and Culture",
"project_id": "110173",
"description": "Refer to RFP Particulars",
"contact_name": null,
"project_type": "RFP",
"contact_email": null,
"date_modified": "2026-09-11 20:55:11",
"document_count": 8,
"commodity_codes": [
{
"code": "561612",
"name": "Security Guards and Patrol Services",
"scheme": "US_NAICS_2022"
}
],
"reference_number": "RFP-2026-0025",
"date_questions_due": "2026-09-25 20:00:00",
"accepts_submissions": true,
"date_intent_to_bid_due": null,
"date_anticipated_evaluation": "2026-10-23 20:00:00"
}
],
"timezone_note": "All dates are UTC as published by the portal (YYYY-MM-DD HH:MM:SS).",
"details_fetched": 4
},
"status": "success"
}
}About the Bonfirehub API
What the API Returns
The list_open_opportunities endpoint returns a snapshot of all opportunities on the portal's Open Public Opportunities tab. The top-level response includes total_open (how many opportunities exist before any filter), count (records returned after filtering), details_fetched (how many detail pages were successfully read), and detail_errors (an array of {project_id, reason} entries for any detail pages that could not be retrieved). A timezone_note string describes the timestamp convention used throughout.
Per-Opportunity Fields
Each entry in the opportunities array carries url (the public detail page), status (always 'Open'), and enriched fields drawn from the detail page. The details array contains {label, value} rows whose label set varies by opportunity — common labels include bonding, insurance, site visit schedule, and addenda deadline. The documents array lists {name, type, description, date_created} for every supporting file attached to the opportunity. Contact information (name, email, phone) appears when the City chooses to publish it.
Filtering
The optional project_type input parameter performs a case-insensitive substring match against each opportunity's solicitation type prefix (for example, RFP, RFT, or ACAN). Passing no value returns all open solicitation types. Filtered and unfiltered response shapes are identical; only count changes relative to total_open.
Coverage Scope
The API covers only opportunities currently in the Open state on the portal. Closed, awarded, and cancelled opportunities are not included. Document file contents are not returned — only the document metadata (name, type, description, date_created) listed on the detail page.
The Bonfirehub API is a managed, monitored endpoint for mississauga.bonfirehub.ca — not a raw scraper you maintain. Every endpoint is automatically health-checked on a schedule, and when mississauga.bonfirehub.ca changes and a check fails, the API is automatically queued for repair and re-verified. It is built to keep working as the site underneath it changes.
This isn't an official mississauga.bonfirehub.ca API — it's an independent, maintained REST wrapper over public data. Where the source has no official API (or only a limited one), Parse gives you a stable contract over a source that never promised one, and keeps it current. Need a new endpoint or field? You can revise it yourself in plain English and the agent rebuilds it against the live site in minutes — contributing the change back to the shared API is free.
Will this API break when the source site changes?+
Is this an official API from the source site?+
Can I fix or extend this API myself if I need a new endpoint or field?+
What happens if I call an endpoint that has an issue?+
- Monitor new RFPs and RFTs from the City of Mississauga to identify bidding opportunities in real time
- Filter open solicitations by type (e.g.,
ACAN) to focus procurement alerts on specific categories - Extract questions-due and close dates from
opportunitiesrecords to populate a procurement calendar - Pull the
documentsarray to track when new addenda or supporting files are attached to an opportunity - Aggregate
departmentfields across open opportunities to analyze which City departments are actively procuring - Use
detail_errorsmonitoring to detect when specific opportunity detail pages become unavailable - Build a supplier-facing dashboard that surfaces opportunity descriptions and contact details from the portal
| Tier | Price | Credits/month | Rate limit |
|---|---|---|---|
| Free | $0/mo | 200 | 5 req/min |
| Hobby | $30/mo | 1,000 | 20 req/min |
| Developer | $100/mo | 5,000 | 100 req/min |
| Team | $300/mo | 20,000 | 300 req/min |
| Company | $1,000/mo | 100,000 | 500 req/min |
Each endpoint has a fixed posted price per successful call — most fall between 1 and 10 credits — shown on this API's page before you run it. Exceeding the rate limit returns a 429 response. Authenticate with the X-API-Key header.
Does the City of Mississauga's Bonfire portal have an official developer API?+
What does the `details` array contain, and does its structure vary?+
details array is a list of {label, value} rows pulled from each opportunity's detail page, and the label set is not fixed. Common labels include bonding requirements, insurance requirements, site visit schedule, and addenda deadline, but not every opportunity carries all labels. Your code should treat this array as variable-length and match labels by string.Does the API return document file contents, or only metadata?+
documents array includes name, type, description, and date_created for each attached file, but not the file bytes or download URLs for gated documents. You can fork this API on Parse and revise it to add a document-download endpoint if your use case requires file contents.Are closed, awarded, or cancelled opportunities accessible through this API?+
How fresh is the opportunity data, and does the API paginate results?+
total_open confirms the full count before any project_type filter is applied.