# OpenAlex Scholarly Works - Papers, Citations and Open Access (`alaudinburki/openalex-works`) Actor

Search 250 million scholarly works and get flat rows - title, DOI, year, journal, citation count and whether it is open access. Free public API, no key.

- **URL**: https://apify.com/alaudinburki/openalex-works.md
- **Developed by:** [alaudin burki](https://apify.com/alaudinburki) (community)
- **Categories:** Developer tools
- **Stats:** 2 total users, 1 monthly users, 90.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.00 / 1,000 results

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## OpenAlex Scholarly Works — Papers, Citations and Open Access

Search the OpenAlex catalogue of scholarly works and get one flat row per paper: title, DOI, year,
venue, citation count and open-access status. The API is public and key-less, so a search runs without
an account. Rows are metadata only — no abstracts and no full text.

### How to use

1. Put a search phrase in **Search text** (OpenAlex matches it against titles, abstracts and full
   text), or leave it empty and use **Filter** alone to select a slice of the catalogue.
2. Optionally add an OpenAlex filter expression, e.g. `from_publication_date:2024-01-01,is_oa:true`.
   The two fields combine: the search and the filter are applied together.
3. Run the Actor and open the dataset. The `SUMMARY` key-value record reports the row count, the
   requests made and the reason the run stopped.

### Inputs

| Input | What it does | Default |
|---|---|---|
| `query` | Full-text search phrase, matched by OpenAlex against work titles, abstracts and full text. | none — no search term |
| `filter` | OpenAlex filter expression, comma-separated, e.g. `publication_year:2023,is_oa:true`. | none — no filter |
| `maxItems` | Stop after this many rows. Capped at 20,000. | `500` |
| `maxPages` | Stop after this many requests. Each request returns up to 200 works. Capped at 200. | `5` |

Example input:

```json
{ "query": "climate adaptation", "filter": "from_publication_date:2024-01-01,is_oa:true", "maxItems": 200, "maxPages": 1 }
```

### Output dataset

| Field | Meaning |
|---|---|
| `title` | Work title as OpenAlex holds it. |
| `doi` | The DOI as a full URL, e.g. `https://doi.org/10.1234/example`. Null when the work has no DOI. |
| `year` | Publication year as a number. |
| `date` | Publication date, `YYYY-MM-DD`. |
| `language` | Language code of the work, e.g. `en`. Null where OpenAlex has none. |
| `citedBy` | Citation count recorded by OpenAlex at the time of the run. A count, not a quality measure. |
| `journal` | Host venue's display name, e.g. the journal or repository. Null for works with no known venue. |
| `isOpenAccess` | Whether OpenAlex classes the work as open access. Its definition is its own. |
| `oaStatus` | Open-access route in OpenAlex's vocabulary: `gold`, `green`, `hybrid`, `bronze`, `diamond` or `closed`. |
| `url` | Publisher landing page for the work, when OpenAlex records one. Null otherwise. |

Each row also carries `id` (`openalex:` followed by the OpenAlex work URL), `source`, `firstSeenAt` and
`scrapedAt`, plus the work `type` (`article`, `preprint`, `book-chapter` and so on). Rows are
de-duplicated by OpenAlex id.

### Why this is different

- One dataset row per work, with the citation count and the open-access route already resolved — the
  API nests the venue and the access details inside `primary_location` and `open_access` objects.
- The DOI arrives as a resolvable URL, not a bare string, so it can be followed without rebuilding it.
- It separates the boolean from the route: `isOpenAccess` answers yes or no, `oaStatus` tells you
  whether that means gold, green, hybrid, bronze or diamond.
- Two inputs cover the common jobs: a text search for a topic, and a filter expression for a date
  range, an access type or a field.
- The run names its own end state: `SUMMARY` records `truncated` and `stopReason`, so a dataset cut off
  at a cap does not look like the end of the catalogue.

### Limitations

- **Metadata only.** No abstracts, no full text, no references list and no author affiliations.
- Citation counts are OpenAlex's own and are a snapshot; they move between runs.
- Open-access classification is OpenAlex's judgement, and `oaStatus` categories do not correspond to
  the terms other indexes use.
- `doi`, `journal`, `url` and `language` are frequently null, especially for preprints, older works and
  grey literature.
- The search is relevance ranked by OpenAlex. It is not a systematic review protocol and will not
  enumerate every work on a topic.
- A run stops at `maxItems` or `maxPages` — 500 rows over 5 requests by default, so a broad topic is
  truncated unless you raise the caps.

### FAQ

**Do I need an API key?**
No. The API is queried without credentials, and the Actor sends none.

**How do I restrict results to one year or one access type?**
Use the filter field, e.g. `publication_year:2023` or `is_oa:true`. Several filters can be joined with
commas in the same expression.

**Why is `doi` null for some rows?**
Not every work has a registered DOI. The row is still valid — use `id` or `url` to identify it.

**Is `citedBy` comparable across runs?**
Only loosely. It is a live count from OpenAlex, so a later run can show a higher number for the same
paper.

**Can I get the abstract or the PDF?**
No. The Actor returns the metadata fields listed above; the full text is not fetched.

### Pricing and limits

Pricing is per event: one charge per run, with the current price on this Actor's Apify pricing panel.
Each request returns up to 200 works; a run defaults to 500 rows over 5 requests and can be raised to
20,000 rows and 200 requests. Requests are paced 250 ms apart, retried up to three times on rate-limit
and server errors, and time out after 30 seconds. The source itself is free to query.

# Actor input Schema

## `query` (type: `string`):

Full-text search across titles and abstracts, e.g. climate adaptation.

## `filter` (type: `string`):

OpenAlex filter syntax, e.g. from_publication_date:2024-01-01,is_oa:true.

## `maxItems` (type: `integer`):

Stop after this many rows.

## `maxPages` (type: `integer`):

Stop after this many pages.

## Actor input object example

```json
{
  "maxItems": 500,
  "maxPages": 5
}
```

# Actor output Schema

## `results` (type: `string`):

One row per item, with the 10 fields listed under Views.

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "maxItems": 500,
    "maxPages": 5
};

// Run the Actor and wait for it to finish
const run = await client.actor("alaudinburki/openalex-works").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "maxItems": 500,
    "maxPages": 5,
}

# Run the Actor and wait for it to finish
run = client.actor("alaudinburki/openalex-works").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "maxItems": 500,
  "maxPages": 5
}' |
apify call alaudinburki/openalex-works --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,alaudinburki/openalex-works"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/E5U7aVHoW1bm1RyTI/builds/gzaiAdprfl1R2eN3k/openapi.json
