LinkedIn Jobs Scraper & Search API: Apply Links, No Reposts avatar

LinkedIn Jobs Scraper & Search API: Apply Links, No Reposts

Pricing

Pay per event

Go to Apify Store
LinkedIn Jobs Scraper & Search API: Apply Links, No Reposts

LinkedIn Jobs Scraper & Search API: Apply Links, No Reposts

Search an hourly index of public LinkedIn jobs. Drop reposts and agencies, or find hard-to-fill roles as hiring leads for staffing agencies. Filter by remote/hybrid, experience, salary, visa, industry and company size. Every job has an apply link, the employer's own where we find it. No login.

Pricing

Pay per event

Rating

5.0

(3)

Developer

SharpLine Labs

SharpLine Labs

Maintained by Community

Actor stats

3

Bookmarked

4

Total users

3

Monthly active users

9 hours ago

Last modified

Share

What is LinkedIn Jobs Search Pro?

LinkedIn Jobs Search Pro searches an hourly index of public LinkedIn jobs and adds the employer's own apply link (Workday, Greenhouse, iCIMS and other careers sites) wherever we can find it. Write your search the way you think about it (python AND (django OR flask) NOT php, ^Senior, =Data Engineer), choose countries and a time range, and get clean JSON, CSV or Excel. There are also token-lean YAML, Markdown and TOON exports for AI agents.

No LinkedIn account, no cookies, no login. Pay only for the jobs you get: $1.25 per 1,000 jobs, no start fee.

Try it: keep the prefilled input (US, past 24 hours, data engineer jobs, 20 results) and press Start.

Why use this LinkedIn jobs scraper?

  • Every job has an apply link, labelled. For jobs that send you off LinkedIn, we look the job up on the employer's own careers board (found for ~27% of off-site jobs overall and ~36% in the US as of 2026-10-26). By default a partner lookup fills the rest, and anything still missing links to the LinkedIn job page. Every link says where it came from: easy_apply, board_verified, board_title (probable), partner or linkedin.
  • Title search that does what you mean. Type data engineer and you get Data Engineers, not "Data Center Engineer". Need more? Every text field also takes prefix*, ^starts-with, =exact, AND/OR/NOT with parentheses and /regex/. C++, C# and .NET work as written.
  • Fresh index. Refreshed every hour since 2026-10-24, and the busiest areas every 30 minutes: the large US states (California, Texas, New York, Florida, Illinois, Pennsylvania, Ohio, North Carolina, Virginia, Washington), Canada, the United Kingdom, Germany, France, India, Brazil, China and Japan.
  • Coverage notes, published. LinkedIn shows at most about 1,000 results per search. When an area hits that cap, our crawler splits it into regions and searches each one. At peak hours some loss can remain; we estimate and track it on every run, and flag areas where it can't be measured.
  • Remote / hybrid / on-site from the job's own text. We read the location, LinkedIn's tag and the description. When there's no signal the job says unknown rather than guessing. Accuracy numbers will be published once our 300-job labelled set is done.
  • No reposts, no agencies (if you want). LinkedIn shows a re-listed job as "just posted"; we spot these by the job ID and drop them by default (they are often half of the "new" jobs). One switch drops staffing firms, recruiters and job boards. The same job posted in several cities comes back once, with all its locations.
  • Hiring leads for agencies. Every job carries its real age (job_age_days, from the job ID) and hard_to_fill: re-listed and open 30+ days. hardToFill: "only" returns just those roles, and the HIRING_LEADS record groups each run by employer (open roles, hard-to-fill roles, company size, industry, website). About 1 in 7 of the US jobs LinkedIn shows as new are hard-to-fill roles.
  • Built for schedules. onlyNewSinceLastRun returns only jobs this exact search hasn't delivered before, and never charges twice for a job it already checked.
  • Built for AI agents. A compact ai view and YAML/Markdown/TOON exports keep the full description while dropping HTML and noise. Callable from Claude, ChatGPT, Cursor and other agents through Apify's MCP server.
  • Honest failure modes. A filter rule that can't be parsed, or a time range our history doesn't cover yet, stops the run with a clear message and costs nothing.

How to search LinkedIn jobs: step by step

  1. Pick a time range (past hour or past 24 hours today; longer ranges open as our history grows, see below).
  2. Pick one or more countries. The default is the United States; clear the list (an empty countries: []) to search all indexed countries.
  3. Type the job titles you want, one per line, and any titles to exclude. Optionally add locations.
  4. Narrow with workplace, experience level and employment type; tick Exclude recruitment agencies if you only want direct employers. Hard-to-fill roles (for agencies), company, description, salary, years of experience, visa sponsorship, industry, applicants, Easy Apply and ATS filters are under More filters.
  5. Set Max results and press Start. Download the results as JSON, CSV, Excel, XML, HTML, JSONL or RSS, or call the API.
  6. For alerts, save the input as a task, turn on Only new since last run, and add a schedule.

Use cases

Job seekers and job-alert bots

Get the new remote data-engineering jobs in the US each hour, without the ones that are really on-site, and with the employer link so you can apply on the company's own site.

{
"timeRange": "1h",
"countries": ["US"],
"titleSearch": ["\"data engineer\"", "\"analytics engineer\""],
"titleExclusionSearch": ["intern*", "^Lead", "director"],
"workplace": ["remote"],
"excludeReposts": true,
"onlyNewSinceLastRun": true,
"limit": 100
}

Staffing and recruitment agencies: hiring leads

Your best prospects are direct employers who have been trying to fill a role for weeks. LinkedIn hides that: a role re-listed for the third time shows as "posted 2 hours ago". This search finds those roles by job-ID age, drops other agencies, and hands you one row per company.

{
"timeRange": "24h",
"countries": ["US"],
"titleSearch": ["\"registered nurse\"", "\"data engineer\"", "\"electrician\""],
"locationSearch": ["Texas"],
"hardToFill": "only",
"hardToFillDays": 30,
"excludeAgencies": true,
"onlyNewSinceLastRun": true,
"limit": 300
}

What you get:

  • Jobs (dataset, hard_to_fill view): title, location, job_age_days (how long the opening has really existed), company size, industry, website, LinkedIn link and the employer's own apply link.
  • HIRING_LEADS (key-value record): one row per employer, sorted by hard-to-fill roles, then open roles: open_roles, hard_to_fill_roles, oldest_role_age_days, titles, locations, company_size, company_industry, company_website, company_headquarters and up to 10 example jobs. Agencies are left out.

Schedule it daily with onlyNewSinceLastRun for a fresh lead list every morning. Notes: a re-listed role is usually still open and often hard to fill, but some employers refresh many postings at once (one employer re-listed 25 roles in a single day, all 77 days old), so check open_roles against hard_to_fill_roles. Ages come from the job ID: exact to the day for IDs since Oct 2026, within a few weeks before that. For a broad search (no titles), raise maxJobsToCheck: candidates are capped at the newest 5 × maxJobsToCheck jobs before the hard-to-fill filter.

Recruiters and sourcers

Find fresh, low-competition roles at the companies you recruit for, or find which companies are struggling to fill a role (many applicants, reposted).

{
"timeRange": "24h",
"countries": ["GB", "IE"],
"titleSearch": ["^Senior AND (\"site reliability\" OR devops OR platform)"],
"excludeAgencies": true,
"seniority": ["mid-senior level"],
"maxApplicants": 25,
"limit": 200
}

Sales and lead generation: hiring signals

A company hiring a "Salesforce administrator" or a "head of RevOps" is a warm lead for CRM consultancies. Index-only mode returns title, company, location and the job link at the cheaper rate.

{
"timeRange": "24h",
"countries": ["US", "CA"],
"titleSearch": ["\"salesforce admin*\"", "\"revenue operations\"", "=RevOps Manager"],
"includeDetails": false,
"excludeReposts": true,
"onlyNewSinceLastRun": true,
"limit": 1000
}

HR-tech, ATS vendors and job-board aggregation

Feed a job board only with jobs whose employer link is confirmed, on the ATS platforms you support.

{
"timeRange": "24h",
"countries": ["US"],
"titleSearch": ["engineer*", "developer*"],
"applyLinks": "verified",
"ats": ["greenhouse", "lever", "ashby", "workday"],
"easyApply": "exclude",
"limit": 500
}

Labour-market research

Count today's postings for a role family across countries. Index-only keeps it cheap; first_seen_at gives you a clean timeline.

{
"timeRange": "24h",
"countries": ["DE", "FR", "NL", "ES", "IT"],
"titleSearch": ["/data\\s?(engineer|scientist|analyst)/"],
"includeDetails": false,
"limit": 5000
}

AI agents and LLM pipelines

Ask an agent to "find 50 remote Python jobs posted in the last hour and summarise them". The TOON export keeps the context small while every job keeps its full description.

{
"timeRange": "1h",
"countries": ["US", "GB", "CA"],
"titleSearch": ["python"],
"workplace": ["remote"],
"aiFormat": "toon",
"limit": 50
}

Career coaches and university careers services

Build a weekly digest of graduate and entry-level roles for your students, with salary shown.

{
"timeRange": "24h",
"countries": ["GB"],
"titleSearch": ["graduate", "\"entry level\"", "junior", "trainee"],
"seniority": ["internship", "entry level"],
"hasSalary": true,
"aiFormat": "markdown",
"onlyNewSinceLastRun": true,
"limit": 300
}

Find jobs that say they sponsor visas ("visaSponsorship": "not_no" instead keeps every job except the ones that say they don't). Each job carries visa_sponsorship: yes, no or unknown.

{
"timeRange": "24h",
"countries": ["NL", "DE", "IE", "AE", "SG"],
"titleSearch": ["\"software engineer\"", "\"backend developer\""],
"visaSponsorship": "yes",
"limit": 200
}

LinkedIn jobs boolean search: filter cheat-sheet

Every rule is case- and accent-insensitive. AND, OR, NOT must be UPPERCASE. One rule per line.

You writeIt matchesExample match
javathe whole word"Senior Java Developer" (not "JavaScript")
data engineerthe exact phrase (plain words)"Senior Data Engineer" (not "Data Center Engineer")
"machine learning"the exact phrase (quotes optional)"Machine Learning Engineer"
python AND djangoboth words, anywhere"Django + Python dev"
dev*words starting with"DevOps", "Developer"
*scriptwords ending with"JavaScript", "TypeScript"
^Seniorthe field starts with"Senior Data Analyst"
=Data Engineerthe whole field equals"Data Engineer" only
python AND (django OR flask) NOT phpboolean logicPython + Django, no PHP
"C++", C#, .NETkept as written"C++ Engineer", ".NET Developer"
/data\s?eng/a regular expression (see below)"Data Eng…", "DataEng…"

Regular expressions go between slashes. Alternatives with | work too; written outside the table:

/data\s?(eng|sci)/

matches "Data Engineer", "DataScience" and "Data Scientist". Accents are ignored here as well: /résumé/ matches "Résumé" and "resume".

  • Include rules (titleSearch, companySearch, locationSearch, descriptionSearch): a job is kept when any line matches. To require several things, put them on one line with AND.
  • Exclusion rules (…ExclusionSearch): a job is dropped if any rule matches.
  • Bad rule = free stop. A rule that can't be parsed stops the run before anything is charged, naming the field and line (e.g. titleSearch[0]: unbalanced '(' …).
  • Cheap filters first. Countries, time range, title, company, location, Easy Apply, reposts and the agency list run on the index and are free. Workplace, seniority, employment type, description, salary, years of experience, visa sponsorship, industry, applicants, ATS and the agency wording check need the job page and may add a job-checked charge for jobs they drop.

Other filters: workplace (remote / hybrid / on-site / unknown), seniority, employmentType, excludeAgencies, excludeReposts (on by default), applyLinks (complete / basic / verified), hasSalary, maxApplicants, easyApply (any / only / exclude), ats, and:

  • minSalary + salaryCurrency (default USD): keeps jobs whose pay, converted to a year (hour × 2080, day × 260, week × 52, month × 12), reaches minSalary at the top of the range. Pay comes from LinkedIn's salary box, or else a pay range in the description ("$120k–$150k", "€55.000 – €65.000 brutto pro Jahr", "£40,000 per annum"); bonuses, sign-on amounts, 401(k) and funding figures are ignored. When minSalary is set, jobs with no stated pay, or pay in another currency, are dropped (no currency conversion).
  • experienceYears: 0-2, 3-5, 6-10, 10+ (inclusive, so 10 is in both of the last two) and unknown for jobs that don't state a number. Read from phrases like "3+ years", "minimum of 5 years", "5–7 years of experience", "mindestens 3 Jahre Berufserfahrung"; when a post lists several, the first required one counts.
  • visaSponsorship: any (default), yes (the post says it sponsors) or not_no (drops only posts that say they don't sponsor, e.g. "unable to sponsor", "must be authorized to work in the US without sponsorship", "U.S. citizenship is required"). Most posts say neither and come out unknown.
  • industries / industryExclusion: rules (same syntax as titles) against LinkedIn's industry for the job, e.g. "staffing and recruiting". A job without an industry fails industries and passes industryExclusion. Older inputs (titleMatchMode and the other match modes, applyLinkRequired, partnerApplyLinks, partnerIncludeProbable) still work.

Reposts and recruitment agencies

Reposts. LinkedIn job IDs grow over time, and a re-listed or refreshed job keeps its old ID while LinkedIn shows it as "posted 10 minutes ago". We record the newest job ID every hour, so we know how old an ID is. A job whose ID already existed 2 or more days before it appeared is a repost (is_repost: true). In late October 2026 that was about half of the US jobs LinkedIn listed as new. excludeReposts (on by default) drops them; turn it off to see them too.

Real age and hard-to-fill roles. Every job also carries id_created_estimate (when its job ID was created) and job_age_days. A repost whose ID is at least hardToFillDays old (default 30) has hard_to_fill: true: the same opening re-listed for a month or more. hardToFill: "only" keeps just those (and keeps reposts whatever excludeReposts says). Of the US reposts on 2026-10-27, 30% were more than a month old and 14% more than three months.

Agencies. excludeAgencies (off by default) drops jobs from staffing firms, recruiters, job boards and gig platforms. Each job carries is_agency and agency_reason:

agency_reasonSignal
knownon our list of large agencies, job boards and gig platforms (Robert Half, Insight Global, CyberCoders, Jobot, AMN, SonicJobs...)
namethe company name says so (Staffing, Recruiting, Personnel, Talent Partners...)
titlecontract-staffing markers in the title (W2, C2C, ::, "Local to")
industryLinkedIn industry Staffing and Recruiting or Executive Search
descriptionthird-party wording: "our client", "direct client", C2C, W2, "Visa:"
contract_shopa contract job in IT consulting whose post opens with a staffing header ("Duration:", "long term contract")

Employer notes such as "we don't accept resumes from agencies" don't count. Without job details (includeDetails: false) only the first three signals are used.

Enriched fields (pattern-based, no AI guesswork)

Every job with details also carries fields we extract with code from the job page, the location and the company's public LinkedIn page. No language model: the same text always gives the same answer, and a field stays empty when the post doesn't say.

FieldWhat it holds
salary_min / salary_max / salary_currency / salary_period, salary_annual_min / _maxpay from LinkedIn's salary block, else a pay range in the description
experience_years_min, experience_levelminimum years asked ("3+ years"), and the bucket 0-2 / 2-5 / 5-10 / 10+
visa_sponsorshipyes / no / unknown
work_arrangement, office_days, remote_scopeon_site / hybrid / remote_ok / remote_only, office days per week, where a remote worker may live
employment_type_normalized, contract_monthsFULL_TIME, PART_TIME, CONTRACTOR, TEMPORARY, INTERN, VOLUNTEER, PER_DIEM, OTHER
categoriesup to 3 of 33 job categories (Technology, Healthcare, Finance & Accounting, ...)
skillstools, languages, licenses and methods named in the post (from a 1,800-entry dictionary)
education_min, education_preferred, degree_or_equivalent, certificationsthe lowest degree required, and named certifications (CPA, PMP, RN, ...)
benefitshealth, dental, 401k/pension, PTO, parental leave, equity, bonus, ...
hours_per_week, schedulestated hours, day/night/weekend/on-call shifts
language, languagesthe description's language(s)
summary, responsibilities, requirementssentences and bullets copied from the post's own sections (extractive, never rewritten)
contact_emailsemail addresses in the post
location_city / _region / _region_code / _country / _timezone, location_derivedthe location string, parsed
company_size, company_employees_min / _max, company_employees_on_linkedin, company_industry, company_website, company_headquarters, company_type, company_founded, company_followers, company_specialties, company_logofrom the company's public LinkedIn page (includeCompanyDetails, on by default)

Filters on them (under More filters): minSalary, experienceYears, visaSponsorship, workArrangement, categories / categoryExclusion, languages, companySize, industries / industryExclusion. The Enriched dataset view shows the main ones as a table.

Moving from Fantastic.jobs? Set compatibility: "fantastic" and every job also gets the same data under their column names (ai_salary_min_value, ai_experience_level, ai_work_arrangement, ai_taxonomies_a, ai_key_skills, org_linkedin_size, locations_derived, ...), so existing scripts keep working. One difference: ai_core_responsibilities and ai_requirements_summary hold sentences copied from the post, not written summaries.

LinkedIn shows "Apply" either as Easy Apply (you apply inside LinkedIn, ~20% of jobs) or as an off-site link to the employer. For off-site jobs we look the job up on the employer's own careers board (Workday, SuccessFactors, iCIMS, Greenhouse, Lever, Ashby, Oracle and more) and label the result:

apply_sourceMeaningapply_confidence
easy_applyLinkedIn Easy Apply; apply_url is the LinkedIn job pagen/a
board_verifiedFound on the employer's board with a matching requisition ID, or an identical title in the same city with a single candidatehigh
board_titleProbable: a very close title, no location conflict, not confirmed. Check before you apply.medium / low
partnerFilled by the partner lookup (Complete mode, the default; see below)high
linkedinNo employer link found: apply_url is the LinkedIn job page (apply from there); apply_reason says why (no_board_known, not_on_board)n/a

ats names the platform of the link (e.g. workday, greenhouse). Apply links (applyLinks) has three modes: complete (default: our links, the partner fills the rest), basic (our links only, no partner cost) and verified (keep only Easy Apply and board_verified jobs).

Coverage today (employer off-site jobs, 2026-10-26)

CountryFoundCountryFoundCountryFound
United States36%Germany8%Singapore24%
Canada25%Spain12%Japan19%
United Kingdom17%Netherlands8%Australia12%
Ireland30%Italy12%United Arab Emirates26%
France9%India21%China / Hong Kong18%

Overall: ~27%. Coverage grows as we map more employers' boards. The LinkedIn url is always included.

In Complete mode (the default), off-site jobs we couldn't match, plus probable board_title ones, are sent (up to partnerMaxJobs, default 100) to bebity/linkedin-jobs-scraper, a separate third-party actor. Choose Basic to skip it.

  • It runs as a separate run on YOUR Apify account and appears in your Console as its own run.
  • That actor bills you at its own price, $1 to $1.50 per 1,000 jobs it looks up, depending on your Apify plan. We cap its run at a matching maximum cost and keep its paid company add-ons off.
  • On top of that we charge apply-link-partner, $0.20 per 1,000 links it actually fills. Easy Apply answers are free.
  • It may not work on Apify's Creator plan, which can't run other developers' actors. If the partner run fails, isn't allowed on your plan or there isn't enough run time left, your run still succeeds; OUTPUT.partner explains what happened, and there's no partner fee.

Exports and AI-friendly output

Dataset formats (built in): JSON, CSV, Excel, XML, HTML, JSONL and RSS. Use the Export button or the API (?format=csv).

Dataset views: overview (the main table), apply (apply-link audit) and ai (compact fields for LLMs: title, company, location, posted date, workplace, seniority, employment type, salary, apply link, LinkedIn URL, full description).

Token-lean exports for LLMs: set aiFormat to yaml, markdown or toon. After the run, one record JOBS_AI in the run's key-value store holds all delivered jobs in that format. Empty fields and the HTML are dropped; the description stays whole unless you set descriptionMaxChars. OUTPUT.ai_export_url links to it. Like any record in a run's default key-value store, that link can be read by anyone who has it, without a token, so share it only where that's fine.

Keep the full description. It is what an AI needs most to judge a job (requirements, location rules, visa, pay), so every export keeps it whole unless you set descriptionMaxChars. The format is where the savings are. Measured on 100 real jobs with the o200k_base tokenizer (GPT-4o family; Claude's is similar), same fields, full description:

FormatTokens per jobvs JSON
JSON (minified, AI fields)879100%
CSV85397%
TOON85497%
Markdown882100%
YAML888101%
Full dataset item (all fields, text + HTML)2,155245%

The biggest saving is dropping description_html and the other non-AI fields (the ai view and JOBS_AI do this): about 60% fewer tokens with no loss of meaning. Between formats the difference is small; TOON and CSV are about 3-15% smaller than JSON depending on how much of the job is description.

Which to use: for an agent or tool call, the ai dataset view as JSON. To paste many jobs into one prompt, aiFormat: "toon". For a human-readable digest or chat answer, aiFormat: "markdown". TOON values that contain commas or quotes are double-quoted CSV-style (inner quotes doubled). Set descriptionMaxChars only when a hard token budget forces it.

How much does it cost to scrape LinkedIn jobs?

Pay per event. Platform usage is included, there's no start fee, and each job is charged at most once per run.

EventWhenPrice per 1,000
job-resultA job delivered with details (includeDetails on, default)$1.25
job-index-onlyA job delivered with index fields only (includeDetails off)$0.40
job-checkedA job page we opened for a detail filter, which the filter then dropped$0.20
apply-link-partnerComplete mode only: a link the partner actually filled$0.20 (+ the partner actor's own price on your account)
Bad filter rule / time range not available yetn/a$0

Worked examples

ScenarioCalculationCost
Try it: 20 jobs with details, Basic links20 × $0.00125$0.025
Try it: 20 jobs, Complete links (default), ~10 looked up by the partner$0.025 + up to 10 × $0.0002 to us, plus ~$0.015 billed by the partner actor≈ $0.04
100 US jobs with details100 × $0.00125$0.125
100 remote jobs, where 300 more jobs were opened and dropped by the workplace filter100 × $0.00125 + 300 × $0.0002$0.185
1,000 jobs, index fields only (lead lists)1,000 × $0.0004$0.40
Hourly alert, ~20 new jobs per hour for 30 days14,400 × $0.00125$18.00
100 jobs + partner lookup for 40 jobs without a link, 30 filled$0.125 + 30 × $0.0002 to us, plus ~$0.04–0.06 billed by the partner actor≈ $0.17–0.19

Set Maximum cost per run in the run options; the run stops cleanly when it's reached. A 100-job US search took about 3 to 4 minutes in our tests (200 s in the latest one).

Is there a free LinkedIn jobs scraper?

Apify's free plan includes monthly platform credit you can spend on this actor. At $1.25 per 1,000 jobs, the try-it run above costs about $0.03.

Time ranges

Our index history starts on 2026-10-24. Longer ranges open as the history grows:

Time rangeAvailable from
Past hournow
Past 24 hoursnow
Past 7 days2026-10-31
Past 30 days2026-11-23
Past 3 months2027-01-24

Choosing a range early ends the run successfully with no charge, and the status message suggests what to use instead.

Output example

{
"job_id": 4391715720,
"url": "https://www.linkedin.com/jobs/view/4391715720",
"title": "Lead Mechanical Engineer (Mission Critical/Data Centers)",
"company": "WSP in the U.S.",
"location": "Austin, TX",
"locations": ["Austin, TX"],
"country": "US",
"posted_date": "2026-10-27",
"first_seen_at": "2026-10-27T13:38:20+00:00",
"is_repost": false,
"id_created_estimate": "2026-10-27",
"job_age_days": 0.6,
"hard_to_fill": false,
"is_agency": false,
"agency_reason": null,
"apply_type": "external",
"apply_url": "https://emit.fa.ca3.oraclecloud.com/hcmUI/CandidateExperience/en/sites/CX_2001/job/83796",
"apply_source": "board_verified",
"apply_confidence": "high",
"ats": "oracle_orc",
"workplace": "unknown",
"seniority": "Not Applicable",
"employment_type": "Full-time",
"applicants": 25,
"salary": null,
"salary_min": null,
"salary_max": null,
"salary_currency": null,
"salary_period": null,
"salary_annual_min": null,
"salary_annual_max": null,
"salary_source": null,
"experience_years_min": 7,
"visa_sponsorship": "unknown",
"description_text": "Great people. Great places. Great projects. …",
"recruiter": null
}

The run's OUTPUT record shows the funnel (how many jobs each filter step kept or dropped), the charged events, why the run stopped, and the available time ranges. The HIRING_LEADS record groups the delivered jobs by employer (see the agencies use case).

Schedules and integrations

  • Schedules: save your input as a task, enable onlyNewSinceLastRun, and schedule it hourly or daily for a job-alert feed with no repeats.
  • API: POST https://api.apify.com/v2/acts/sharplinelabs~linkedin-jobs-search/run-sync-get-dataset-items returns the jobs in one call (for small runs); for bigger ones start a run and read the dataset. Clients: apify-client for Python and JavaScript.
  • Make, n8n, Zapier: use the Apify app/node: Run Actor → Get dataset items → Google Sheets, Airtable, Slack, email.
  • Webhooks: fire on ACTOR.RUN.SUCCEEDED to push new jobs to your app.
  • RSS: the dataset's ?format=rss export works in any feed reader.
  • AI agents (MCP): connect https://mcp.apify.com?tools=sharplinelabs/linkedin-jobs-search in Claude Desktop, Claude Code, Cursor, VS Code or ChatGPT. Runs take a few minutes, so agents should start the run, poll it, then read the dataset (or the JOBS_AI record).

FAQ

Do I need a LinkedIn account or cookies?

No. Everything comes from LinkedIn's public, logged-out job pages. We never log in and you never share credentials.

How fresh are the jobs?

The index is refreshed every hour, and the busiest areas every 30 minutes. first_seen_at tells you when we first saw each job.

Every job gets an apply_url. Easy Apply jobs (~20%) link to LinkedIn. For off-site jobs we find the employer's own page for about 27% overall (36% in the US) as of 2026-10-26; in Complete mode the partner lookup fills most of the rest, and anything left points to the LinkedIn job page (apply_source: "linkedin").

board_verified matched on a requisition ID, or an identical title in the same city with a single candidate. board_title is a close title match we couldn't confirm, so check it before applying. applyLinks: "verified" keeps only verified links (and Easy Apply).

Why use experienceYears instead of LinkedIn's seniority?

LinkedIn's own seniority label is often missing or vague: in our October 2026 sample, 55% of jobs were labelled "Not Applicable", yet 73% of those state the years required in the description, and "Mid-Senior level" covered anything from 2 to 8 years. experienceYears reads the requirement from the description itself ("3+ years", "minimum of 5 years", "mindestens 3 Jahre").

Can I get only remote jobs?

Yes: workplace: ["remote"]. The label comes from the job's own text. Jobs with no signal are unknown; add "unknown" to the list if you'd rather not miss them.

Can I get only jobs on Workday, Greenhouse or Lever?

Yes: ats: ["workday", "greenhouse", "lever"]. This keeps jobs whose employer link we found on those systems.

Why did my search return fewer jobs than expected?

Your rules matched fewer jobs in that time range, or the run hit maxJobsToCheck or your maximum cost. The OUTPUT funnel shows exactly which step dropped them. Try fewer exclusions, turn off excludeReposts, or use a longer time range.

Will I pay twice on a schedule?

No. With onlyNewSinceLastRun, jobs this search already delivered, or already checked and dropped, are skipped and not charged again.

Is there a LinkedIn jobs API?

LinkedIn's official job APIs are for partners only. This actor gives you an API over public job postings: one HTTP call returns JSON.

Can I use it from Python?

Yes: pip install apify-client, then client.actor("sharplinelabs/linkedin-jobs-search").call(run_input={...}) and iterate client.dataset(run["defaultDatasetId"]).iterate_items().

Can I export LinkedIn jobs to Excel or Google Sheets?

Yes. Export the dataset as Excel or CSV, or use the Make / n8n / Zapier integrations to append rows to Google Sheets.

I'm switching from another LinkedIn jobs actor. Do the inputs carry over?

Mostly. We use the common timeRange, titleSearch, titleExclusionSearch, locationSearch and descriptionSearch field names. Check the cheat-sheet for rule syntax.

What does Complete mode do with my account?

It starts one run of bebity/linkedin-jobs-scraper with your own Apify token, only for jobs still missing a confirmed link, up to partnerMaxJobs. You see it in your Console and pay that actor's price ($1 to $1.50 per 1,000 jobs, depending on your plan), plus our $0.20 per 1,000 filled links. It may not work on Apify's Creator plan, which can't run other developers' actors; then the run still finishes with our own links. Pick Basic to never start it.

What counts as a repost?

A job whose LinkedIn job ID already existed 2 or more days before it showed up as new. See "Reposts and recruitment agencies" above.

How do I find companies that can't fill a role?

Set hardToFill: "only" and excludeAgencies: true. You get roles LinkedIn shows as new but that were first created 30+ days ago (hardToFillDays changes the threshold), and the HIRING_LEADS record lists the employers behind them with company size and website.

Something's wrong. Where do I get help?

Open an issue on the Issues tab with your run ID. We read every one.

Changelog

  • 2026-10-28: hard-to-fill roles for agencies: job_age_days, id_created_estimate and hard_to_fill on every job, hardToFill / hardToFillDays filters, the HIRING_LEADS per-employer record and a hard_to_fill dataset view. Job pages are now always read in English, so the experience-level, employment-type and industry filters no longer drop jobs whose LinkedIn page came back in another language. More employer apply links (new careers-site readers: Taleo, SuccessFactors fixes, Radancy, Avature, PeopleSoft, softgarden, gupy and more).

  • 2026-10-27: enriched fields (work arrangement with remote-only vs remote-OK, office days, remote scope, employment type, 33 job categories, skills, education, certifications, benefits, hours, language, extractive summary/responsibilities/requirements, parsed location, company size/industry/website/HQ from the company page) with workArrangement, categories, languages and companySize filters; compatibility: "fantastic" field names; phrases with * keep word order; AI exports keep the full description.

  • 2026-10-27: parsed salary (salary_min / salary_max / salary_currency / salary_period, yearly figures, salary_source) with a minSalary filter; experience_years_min with an experienceYears filter; visa_sponsorship (yes / no / unknown) with a visaSponsorship filter; industries / industryExclusion filters.

  • 2026-10-27: simpler input (core search on top, the rest under More filters); plain words now match the exact phrase (data engineer no longer matches "Data Center Engineer"); repost detection by job ID age (the old posted-date rule missed nearly all reposts); excludeAgencies with is_agency / agency_reason; applyLinks modes with the partner lookup on by default; apply_url is never empty (LinkedIn page fallback, apply_source: "linkedin").

  • 2026-10-27: AI-friendly exports (aiFormat: YAML / Markdown / TOON, descriptionMaxChars, ai dataset view); optional partner apply-link lookup (partnerApplyLinks, beta); stricter regex guard; default limit is now 20 and countries defaults to the US ([] = all countries).

  • 2026-10-27: the built-in employer-board registry is used in every run (more apply links); maxJobsToCheck holds across a platform migration; accent-insensitive regex; C++, C# and .NET kept in quoted phrases.

  • 2026-10-27: first release: hourly index since 2026-10-24, boolean text filters, workplace classifier, employer apply links, onlyNewSinceLastRun, pay-per-event pricing.