Arizona ROC Contractor License Scraper
Pricing
from $2.19 / 1,000 license records
Arizona ROC Contractor License Scraper
Look up Arizona Registrar of Contractors licenses by number, company, qualifying party, or city. Get status, bond, classification, personnel, and complaint history. Export as JSON, CSV, or Excel.
Pricing
from $2.19 / 1,000 license records
Rating
0.0
(0)
Developer
ParseBird
Maintained by CommunityActor stats
1
Bookmarked
2
Total users
1
Monthly active users
3 days ago
Last modified
Categories
Share
Arizona ROC Contractor License Scraper
Look up Arizona Registrar of Contractors (AZ ROC) license records by license number, company name, qualifying party, or city. The Arizona ROC Contractor License Scraper pulls license status, bond details, classification, personnel, and complaint history for any Arizona contractor, with no login and no AZ ROC API key.
| Search by license number, company, qualifying party, or city, filter by classification, status, and type, then get full bond, personnel, and complaint-history data straight from AZ ROC's own records. |
Copy to your AI assistant
Copy this block into ChatGPT, Claude, Cursor, or any LLM to start using this actor.
Actor: parsebird/az-roc-contractor-license-scraper (Apify). Looks up Arizona Registrar of Contractors (AZ ROC) contractor licenses. Call with ApifyClient.Input JSON fields: licenseNumbers: string[] — exact ROC license numbers, e.g. ["333318"] (leading zeros added automatically to 6 digits); companyNames: string[] — partial business name matches; qualifyingPartyNames: string[] — partial name matches for the individual responsible for the license; cities: array<string> — Arizona cities to search by mailing address; licenseClassification: string — optional classification code, e.g. "C-37" (see the Classification Reference in the README); licenseType: "ALL"|"RESIDENTIAL"|"COMMERCIAL"|"DUAL" (default ALL); licenseStatus: "ALL"|"ACTIVE"|"SUSPENDED"|"EXPIRED"|"REVOKED"|"CANCELLED" (default ALL); maxResultsPerSearch: int (default 0 = unlimited); scrapeDetailPage: bool (default true) — full bond/personnel/complaint data; scrapeComplaints: bool (default true); maxConcurrency: int 1-10 (default 3); proxyConfiguration: object (default residential).Output: one dataset item per license — licenseNumber, licenseType, licenseStatus, businessName, dbaName, qualifyingParty, entityType,personnel, primaryClassification, classificationDesc, classifications, city, state, zip, phone, issuedDate, renewedThroughDate,expirationDate, bondType, bondStatus, bondAmount, bondCompany, bondNumber, bondEffectiveDate, openCases, disciplinedCases,resolvedCases, complaintCount, complaints, profileUrl, searchQuery, scrapedAt.Example: { "licenseNumbers": ["333318"], "cities": ["Tucson"], "licenseClassification": "C-37", "licenseStatus": "ACTIVE" }API: https://api.apify.com/v2/acts/parsebird~az-roc-contractor-license-scraper · Token: https://console.apify.com/account/integrations
What does Arizona ROC Contractor License Scraper do?
The Arizona Registrar of Contractors licenses every contractor legally allowed to work in Arizona. There is no public AZ ROC API — this scraper reads the same public search backend the AZ ROC contractor-search website itself uses. For every matching license it extracts:
- 🏷️ License identity — number, type, status, business name, DBA name, entity type, and qualifying party.
- 👥 Personnel — officers, members, partners, and the qualifying party, each with their role.
- 🧾 Classification — the license's classification code and plain-English description (e.g.
C-37→ Plumbing). - 💰 Bond information (optional) — bond type, status, amount, surety company, and bond number.
- ⚠️ Complaint history (optional) — open, disciplined, and resolved case counts for the prior two years, as displayed by AZ ROC.
Common uses: vetting a contractor before hiring, verifying an active license and bond before signing a contract, due-diligence checks for lenders and insurers, and building a local dataset of licensed contractors by city or trade.
Input parameters
| Parameter | Type | Required | Default | Description |
|---|---|---|---|---|
| licenseNumbers | array | No | [] | ROC license numbers to look up directly. Leading zeros added automatically to make 6 digits. Fastest, most precise mode. |
| companyNames | array | No | [] | Business names to search. Partial matches accepted. Each name is its own search. |
| qualifyingPartyNames | array | No | [] | Full name of the qualifying party (format: First Last). Partial names allowed. |
| cities | array | No | [] | Arizona cities to search by mailing address, e.g. Phoenix, Tucson. Must match AZ ROC's exact spelling on file. |
| licenseClassification | string | No | "" | Classification code filter, e.g. B-1, R-11, C-37. See the Classification Reference below. |
| licenseType | enum | No | ALL | One of ALL, RESIDENTIAL, COMMERCIAL, DUAL. |
| licenseStatus | enum | No | ALL | One of ALL, ACTIVE, SUSPENDED, EXPIRED, REVOKED, CANCELLED. |
| maxResultsPerSearch | integer | No | 0 | Cap records per individual search query. 0 = unlimited. |
| resultsPerPage | enum | No | "50" | Kept for input compatibility only — see the FAQ for why it has no effect. |
| scrapeDetailPage | boolean | No | true | Fetch each license's full bond, complaint, classification, and personnel data. |
| scrapeComplaints | boolean | No | true | Capture complaint history (requires scrapeDetailPage). AZ ROC only shows the prior two years. |
| maxConcurrency | integer | No | 3 | Max concurrent requests to AZ ROC's search backend (1-10). |
| proxyConfiguration | object | No | Residential | Apify Proxy settings. |
Example inputs
Direct license lookup:
{"licenseNumbers": ["333318"]}
City + classification, active only:
{"cities": ["Tucson"],"licenseClassification": "C-37","licenseStatus": "ACTIVE"}
Fast list-only crawl by company name:
{"companyNames": ["Acme Plumbing"],"scrapeDetailPage": false}
Full detail with complaint history:
{"qualifyingPartyNames": ["John Smith"],"scrapeDetailPage": true,"scrapeComplaints": true}
What data can you extract from AZ ROC?
Core fields
| Field | Description |
|---|---|
| licenseNumber | ROC license number (e.g. 333318) |
| licenseType | Residential, Commercial, Dual, or General Engineering — derived from the classification's own description |
| licenseStatus | Active, Suspended, Expired, Revoked, Cancelled, Inactive, etc. |
| businessName | Legal business entity name |
| dbaName | "Doing Business As" name where present |
| qualifyingParty | Individual responsible for the license |
| entityType | AZ ROC's own entity-type label (e.g. LLC, Corporation) |
| personnel | Officers, members, partners, qualifying party — each with name and role |
Classification fields
| Field | Description |
|---|---|
| primaryClassification | Classification code (e.g. B-1, R-11, C-37) |
| classificationDesc | Plain-English description of the classification |
| classifications | Array of { code, description } — AZ ROC issues each classification as its own separate license number, so this typically holds one entry matching primaryClassification |
Address, contact & lifecycle
| Field | Description |
|---|---|
| city / state / zip | Business mailing address |
| phone | Formatted as (XXX) XXX-XXXX when the source has 10 digits |
| issuedDate | First-issued date, YYYY-MM-DD |
| renewedThroughDate / expirationDate | AZ ROC exposes a single forward-looking "Renewed Through" date; both fields carry that same value |
Bond information (with scrapeDetailPage)
| Field | Description |
|---|---|
| bondType | Contractor bond type (e.g. Surety) |
| bondStatus | Active, Cancelled, Expired, etc. |
| bondAmount | Bond face amount, formatted as $ {amount} |
| bondCompany | Surety company name |
| bondNumber | Surety bond number |
| bondEffectiveDate | Bond effective date, YYYY-MM-DD |
Complaint history (with scrapeComplaints, last 2 years exposed by AZ ROC)
| Field | Description |
|---|---|
| openCases | Count of open complaints |
| disciplinedCases | Count of complaints resulting in discipline |
| resolvedCases | Count of resolved/settled complaints |
| complaintCount | Total complaint count |
| complaints | Per-complaint detail, when any exist |
Metadata
| Field | Description |
|---|---|
| profileUrl | Direct link to the license's AZ ROC detail page |
| searchQuery | The input value that produced this record |
| scrapedAt | ISO-8601 timestamp of extraction |
Output example
{"licenseNumber": "333318","licenseType": "Dual","licenseStatus": "Active","businessName": "Mike Robbins Plumbing LLC","dbaName": "Phoenix Residential & Commercial Plumbing","qualifyingParty": "Tyler Michael Robbins","entityType": "LLC","personnel": [{ "name": "Tyler Michael Robbins", "role": "Qualifying Party" },{ "name": "Michael A Robbins", "role": "Manager;Member" }],"primaryClassification": "CR-37","classificationDesc": "Plumbing","classifications": [{ "code": "CR-37", "description": "Plumbing" }],"city": "Apache Junction","state": "AZ","zip": "85120","phone": "(480) 529-4852","issuedDate": "2021-05-12","renewedThroughDate": "2027-05-31","expirationDate": "2027-05-31","bondType": "Surety","bondStatus": "Active","bondAmount": "$ 6,750","bondCompany": "RLI Insurance Company","bondNumber": "LSM1483204","bondEffectiveDate": "2021-05-04","openCases": 0,"disciplinedCases": 0,"resolvedCases": 0,"complaintCount": 0,"profileUrl": "https://azroc.my.site.com/AZRoc/s/contractor-search?licenseId=a0o8y0000004CYXAA2","searchQuery": "333318","scrapedAt": "2026-09-05T14:40:46.584Z"}
Download the dataset as JSON, CSV, Excel, HTML, or XML from the Storage tab or the Apify API.
Use cases
- Pre-hire vetting — confirm a contractor's license is Active and bonded before signing a contract.
- Lender / insurer due diligence — check license status, classification, and complaint history in bulk.
- Market research — pull every licensed contractor for a trade classification or city.
- Compliance monitoring — track qualifying parties and personnel across multiple licenses.
How it works
- Search — each
licenseNumbers,companyNames,qualifyingPartyNames, orcitiesentry runs as its own search against AZ ROC's contractor-search backend. - Flatten — each matched business can hold multiple licenses; the scraper emits one row per license.
- Filter —
licenseStatus,licenseType, andlicenseClassificationare applied precisely on the client side (see the FAQ for why). - Enrich (optional) — with
scrapeDetailPageon, each license's own detail record is fetched for bond, personnel, and (withscrapeComplaints) complaint history. - Rows stream to the dataset, deduplicated across all searches by license.
How much does it cost to scrape AZ ROC?
This actor is pay per result — charged once per license record saved to the dataset, regardless of whether scrapeDetailPage is on.
| Plan | Price per 1,000 licenses |
|---|---|
| Free | $2.99 |
| Bronze | $2.79 |
| Silver | $2.49 |
| Gold | $2.19 |
A small platform Actor start fee also applies per run. Turn scrapeDetailPage off for a faster, list-only crawl at the same per-row price. Apify's monthly free platform usage covers small runs.
How to look up AZ ROC contractors
- Click Try for free and sign in to Apify.
- Enter one or more license numbers, company names, qualifying party names, or cities.
- Optionally set a classification code, license type, or license status filter.
- Toggle Scrape detail page and Scrape complaints for full bond and complaint data.
- Click Start, then watch rows appear in the Output tab.
- Export from Storage, or pull results via the API.
Run it via API
Python:
from apify_client import ApifyClientclient = ApifyClient("<YOUR_APIFY_TOKEN>")run = client.actor("parsebird/az-roc-contractor-license-scraper").call(run_input={"cities": ["Tucson"],"licenseClassification": "C-37","licenseStatus": "ACTIVE",})for lic in client.dataset(run["defaultDatasetId"]).iterate_items():print(lic["businessName"], "-", lic["licenseNumber"], "-", lic["licenseStatus"])
JavaScript:
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: '<YOUR_APIFY_TOKEN>' });const run = await client.actor('parsebird/az-roc-contractor-license-scraper').call({licenseNumbers: ['333318'],scrapeDetailPage: true,scrapeComplaints: true,});const { items } = await client.dataset(run.defaultDatasetId).listItems();console.log(items);
Schedule recurring runs, add webhooks, or push results to Google Sheets, Slack, Zapier, and Make with Apify integrations.
Classification Reference
AZ ROC uses a letter-prefix classification system. The actor returns the raw code plus a plain-English description in primaryClassification / classificationDesc. This table is scraped directly from AZ ROC's own classification list.
| Prefix | Scope | Example codes |
|---|---|---|
| A | General Engineering | A, A-4 Drilling, A-9 Swimming Pools, A-14 Asphalt Paving |
| B | General Residential / Commercial | B General Residential, B-1 General Commercial, B-3 General Remodeling |
| C | Commercial Specialty | C-37 Plumbing, C-39 Air Conditioning and Refrigeration, C-11 Electrical, C-16 Fire Protection Systems, C-42 Roofing, C-78 Solar Plumbing |
| CR | Commercial/Residential Specialty (Dual) | CR-37 Plumbing, CR-39 Air Conditioning and Refrigeration, CR-11 Electrical, CR-42 Roofing |
| K | Dual (General) | KA Dual Engineering, KB-1 Dual Building Contractor, KB-2 Dual Residential and Small Commercial |
| R | Residential Specialty | R-11 Electrical, R-37 Plumbing (Including Solar), R-39 Air Conditioning and Refrigeration, R-62 Minor Home Improvements |
Full code list used by licenseClassification:
Pass any of these codes into licenseClassification to filter results to that endorsement.
License Status Reference
Active statuses — contractor may legally work
| Status | Meaning |
|---|---|
| Active | License in good standing, contractor may bid and build |
| Active - Probation | Active but subject to Board-imposed conditions |
| Pending Renewal | Renewal application in process |
Inactive / restricted statuses — contractor may not legally work
| Status | Meaning |
|---|---|
| Suspended | Temporarily barred from contracting |
| Expired | License lapsed; renewal not completed |
| Cancelled | License cancelled (often voluntary) |
| Revoked | Permanently terminated by ROC action |
Use licenseStatus: "ACTIVE" to receive only currently authorized contractors.
FAQ
Do I need an AZ ROC account or API key? No. The scraper reads AZ ROC's own public contractor-search backend. There is no public search API — this actor is the alternative.
Why does resultsPerPage have no effect?
AZ ROC's search returns every matching record in a single response — the site's own "Next" pagination is purely a client-side display convenience over data it already has in full. This actor reads that same complete response directly, so there's nothing to paginate and no page-size setting to apply.
How reliable is licenseClassification filtering?
AZ ROC's own classification search parameter was found (through direct testing) to return additional, unrelated classifications alongside the requested one rather than filtering exactly. To guarantee correct results, this actor always applies an exact match against each license's own parsed classification code after fetching results, rather than trusting AZ ROC's filter alone.
Why is expirationDate the same as renewedThroughDate?
AZ ROC's contractor detail page shows a single forward-looking date, labeled "Renewed Through" — there is no separate expiration date exposed. Both fields carry that value for compatibility with schemas that expect an expirationDate field.
Why are some bond/complaint fields null?
bondExpirationDate is not exposed by AZ ROC's bond data at all (only an effective date). Complaint and bond details require scrapeDetailPage (and scrapeComplaints for complaints); with both off, or when a license genuinely has no bond or complaint record, those fields are null.
What proxy do I need? AZ ROC's search backend has responded to direct and datacenter requests during testing, but residential is recommended for larger production runs to reduce rate-limiting risk.
Something's not working. Open an issue on the Issues tab with your input and the run link — we respond quickly.
Is it legal to scrape AZ ROC contractor licenses?
AZ ROC contractor license records are public information, published by the State of Arizona and viewable by any visitor without logging in. Scraping publicly available government records is legal in most jurisdictions, and this actor does not access private data or bypass any login. You are responsible for how you use the data — follow AZ ROC's Terms of Use and applicable data-protection law, and consult a lawyer if you are unsure. See Apify's guide on the legality of web scraping.
Related actors
- BuildZoom Scraper — contractor profiles and reviews from BuildZoom.
- UK Companies House Scraper — UK company registry records.
- Zefix.ch Scraper — Swiss commercial register lookups.
- Allabolag Scraper — Swedish company and B2B lead data.
Browse all ParseBird actors on Apify Store.