GitHub Archive Events Scraper — Historical GH Events by Date
Pricing
from $1.50 / 1,000 results
GitHub Archive Events Scraper — Historical GH Events by Date
Download the full historical firehose of public GitHub events from GH Archive by date and hour. Extract pushes, stars, forks, pull requests, issues, releases and comments since 2011. Filter by repo, actor, org and event type. No API key, no login.
Pricing
from $1.50 / 1,000 results
Rating
0.0
(0)
Developer
Logiover
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
6 days ago
Last modified
Categories
Share
GitHub Archive Events Scraper — Historical Public GitHub Events by Date & Hour
Download the complete historical firehose of every public GitHub event — pushes, stars, forks, pull requests, issues, releases and comments — straight from the GH Archive (data.gharchive.org) bulk record, queryable by date and hour with rich filters. Unlike the GitHub REST Events API (which only returns the last ~90 recent events for a repo or user), this Actor reads the full public event history since February 2011, one hour at a time, and gives you clean flat rows ready for analysis. No API key, no login, no token, no GitHub account.
🏆 What this Actor does
The GitHub Archive Events Scraper streams gzip-compressed hourly archive files from GH Archive (URL pattern https://data.gharchive.org/YYYY-MM-DD-H.json.gz). Each file is newline-delimited JSON holding hundreds of thousands of public GitHub events for that single UTC hour. The Actor pipes each file through gunzip and a line reader, parses every event, applies your filters (event type, repository, actor login, organization), and writes matching events as flat dataset rows — without ever loading a whole 70 MB file into memory.
This is the same public firehose that powers star-history charts, the GitHub Innovation Graph, OSS trend dashboards and developer-ecosystem research. Because the events follow the standard GitHub Events API v3 schema, you get PushEvent, WatchEvent (a star), ForkEvent, PullRequestEvent, IssuesEvent, ReleaseEvent and more, with their full payloads flattened into tidy columns. Point it at any date range since 2011 and pull the exact slice of GitHub history you need.
👥 Who is it for?
- Developer-ecosystem & OSS researchers studying how projects, languages and communities grow over time.
- Data scientists & ML teams building datasets of commits, stars, PRs and issues for trend models or LLM training corpora.
- Recruiters & dev-lead sourcers finding active contributors to specific repos, orgs or technologies by their public activity.
- Security & supply-chain analysts tracking new repo creations, releases and package-adjacent activity for threat intelligence.
- Founders, VCs & market analysts measuring project momentum (star velocity, fork growth, contributor counts) for due diligence.
🎯 Use cases
- Star-history & trend analysis — pull every
WatchEventfor a repo or org across a date window to reconstruct exact star-growth curves GitHub no longer exposes. - Contributor sourcing — extract all actors who opened PRs or pushed commits to a target repository in a given month, for recruiting or community outreach.
- Release & changelog tracking — collect every
ReleaseEventacross an ecosystem to build a historical release timeline. - Supply-chain & security research — monitor
CreateEventrepo creations andReleaseEventpublishes for suspicious or newly-appearing projects. - OSS health metrics — quantify issue open/close rates, PR merge rates and push frequency for a portfolio of repositories over time.
✨ Why use the GitHub Archive Events Scraper?
- 🔓 Fully keyless — GH Archive is a public static file host. No GitHub token, no OAuth, no login, no rate-limited REST API.
- 🗄️ True historical depth — every public event since 2011-02-12, not just the ~90 recent events the GitHub REST Events API caps you at.
- 🌊 Firehose volume — a single hour holds hundreds of thousands of events; one run can yield thousands to millions of filtered rows.
- 🎛️ Precise filters — narrow by event type, repository (substring or owner/ prefix), actor login and organization so you only pay for the rows you want.
- 🧠 Memory-safe streaming — files are gunzipped and parsed line by line, never buffered whole, so huge windows run in 1 GB of memory.
- 📤 Clean flat export — every event becomes one row with a typed set of columns, ready for CSV, JSON, Excel, HTML, XML or JSONL and pay-per-result pricing.
📊 What data can you extract?
Every matching public event is saved as a single flat row. Fields are populated based on the event type — a PushEvent fills commitCount and commitMessages, a PullRequestEvent fills the pr* fields, an IssuesEvent fills the issue* fields, and so on. Unused fields for a given event type are simply omitted.
| Field | Type | Description |
|---|---|---|
eventId | string | Unique GitHub event ID. |
eventType | string | Event type: PushEvent, WatchEvent, ForkEvent, PullRequestEvent, IssuesEvent, ReleaseEvent, CreateEvent, etc. |
action | string | Payload action where applicable (opened, closed, started, created, published). |
createdAt | string | UTC timestamp of the event (ISO 8601). |
actorLogin | string | GitHub username that performed the event. |
actorId | string | Numeric GitHub user ID of the actor. |
actorUrl | string | GitHub profile URL of the actor. |
repoName | string | Repository full name (owner/name). |
repoUrl | string | https://github.com/<owner/name> link. |
orgLogin | string | Organization login, if the event belongs to one. |
refType | string | For Create/Delete events: repository, branch or tag. |
ref | string | Git ref (branch or tag name) for push/create/delete events. |
commitCount | string | Number of commits in a push event. |
commitMessages | string | Joined commit messages for a push event. |
prNumber | string | Pull request number. |
prTitle | string | Pull request title. |
prState | string | Pull request state (open/closed). |
prMerged | string | Whether the PR was merged (true/false). |
issueNumber | string | Issue number. |
issueTitle | string | Issue title. |
issueState | string | Issue state (open/closed). |
forkedTo | string | Full name of the new fork for a ForkEvent. |
releaseTag | string | Tag name of a published release. |
releaseName | string | Human-readable release name. |
commentBody | string | Body text of an issue, commit or PR review comment. |
hourFile | string | Source GH Archive hourly file (e.g. 2024-06-15-15). |
Example output row (a star / WatchEvent)
{"eventId": "39326469018","eventType": "WatchEvent","action": "started","createdAt": "2024-06-15T15:00:00Z","actorLogin": "TLReber","actorId": "3442398","actorUrl": "https://github.com/TLReber","repoName": "TLReber/LSPT-TextTransformation","repoUrl": "https://github.com/TLReber/LSPT-TextTransformation","hourFile": "2024-06-15-15"}
🚀 How to use
You can drive the Actor two ways, and they combine freely.
Option A — Grab a whole date window (bulk firehose)
Set startDate and endDate and (optionally) restrict eventTypes. The Actor downloads every hour file in the range and saves matching events until maxItems is reached. Great for "all stars across June 2024" or "every release in Q1".
{"startDate": "2024-06-15","endDate": "2024-06-15","eventTypes": ["WatchEvent"],"maxItems": 5000}
Option B — Focus on specific repos, orgs or developers
Add repoFilter, orgFilter or actorFilter to keep only the events you care about. Filters are case-insensitive; repoFilter matches on a substring (so facebook/ catches every Facebook repo, and react catches any repo with "react" in its name).
{"startDate": "2024-06-15","endDate": "2024-06-15","hours": [9, 12, 15, 18],"eventTypes": ["PullRequestEvent", "IssuesEvent", "PushEvent"],"repoFilter": ["facebook/react", "vuejs/"],"orgFilter": ["microsoft"],"maxItems": 20000}
Steps
- Open the Actor, set your
startDate/endDate(keep the window small at first — one day is 24 files of ~70 MB each). - Optionally set an
hourswhitelist andeventTypesto keep the run cheap while you experiment. - Add any
repoFilter/actorFilter/orgFilteryou need, and a sensiblemaxItemscap. - Click Start. Watch the log — each hour reports how many matching events it added.
- Open the Output tab and export to JSON, CSV, Excel, HTML, XML or JSONL, or pull it via the Apify API.
⚙️ Input parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
startDate | string | 2024-06-15 | Inclusive UTC start date (YYYY-MM-DD). |
endDate | string | 2024-06-15 | Inclusive UTC end date (YYYY-MM-DD). Every hour from startDate 00:00 to endDate 23:00 is fetched. |
hours | array | [] | Optional whitelist of UTC hours 0–23. Empty = all 24 hours per day. |
eventTypes | array | ["WatchEvent","PullRequestEvent"] | Event types to keep. Empty = all types. |
repoFilter | array | [] | Keep events whose owner/name contains any entry (case-insensitive substring). Empty = all repos. |
actorFilter | array | [] | Keep events by these actor logins (case-insensitive exact). Empty = all users. |
orgFilter | array | [] | Keep events under these organizations (case-insensitive exact). Empty = all orgs. |
maxItems | integer | 5000 | Global hard cap on saved events. Raise for bulk exports. |
proxyConfiguration | object | { "useApifyProxy": true } | Apify Proxy. Datacenter is sufficient (public static host). |
Full input example
{"startDate": "2024-06-01","endDate": "2024-06-02","hours": [],"eventTypes": ["ReleaseEvent", "PushEvent", "PullRequestEvent"],"repoFilter": ["kubernetes/"],"actorFilter": [],"orgFilter": ["kubernetes"],"maxItems": 50000,"proxyConfiguration": { "useApifyProxy": true }}
📤 Output example
A fully-populated PullRequestEvent row:
{"eventId": "39326470112","eventType": "PullRequestEvent","action": "opened","createdAt": "2024-06-15T15:00:02Z","actorLogin": "octocat","actorId": "583231","actorUrl": "https://github.com/octocat","repoName": "facebook/react","repoUrl": "https://github.com/facebook/react","orgLogin": "facebook","prNumber": "28911","prTitle": "Fix hydration warning in Suspense boundary","prState": "open","prMerged": "false","hourFile": "2024-06-15-15"}
💡 Tips for best results
- Start with a single hour — set
startDate=endDateandhours: [15]with a tighteventTypeslist to preview the data cheaply before scaling up. - Always keep a
maxItemscap. One hour is hundreds of thousands of events; without a cap a multi-day run can pull millions. - Filter early with
eventTypes. Stars (WatchEvent) and PRs are a small fraction of the firehose (most events arePushEvent), so filtering slashes cost. repoFilteris a substring match — useowner/namefor an exact repo,owner/for a whole account, or a bare word to catch a family of repos.actorFilterandorgFilterare exact matches on the login, not substrings — pass the precise username or org slug.- Hours have no zero-padding in GH Archive (
...-9.json.gz, not...-09), but you can enter9or"9"in thehourslist — both work. - Very recent hours may 404 for a short window until GH Archive publishes them; the Actor logs a warning and skips them gracefully.
- Time zone is UTC. A "day" is 24 UTC hours, so
createdAtis in UTC and your date bounds are UTC too. - For star history, combine
eventTypes: ["WatchEvent"]+repoFilter: ["owner/repo"]across the months you care about, then group by day in your spreadsheet. - Widen the window, not the memory — streaming keeps memory flat, so covering more days just takes more time, not more RAM.
🔌 Integrations
Send your extracted events anywhere Apify connects:
- Google Sheets — push rows straight into a spreadsheet for star-history charts or contributor lists.
- Slack — get notified when a run finishes or when a target repo crosses a threshold.
- Zapier & Make — trigger downstream automations (CRM enrichment, alerting) from new dataset items.
- Webhooks — POST finished datasets to your own API or data warehouse.
- Schedule — run daily/weekly to keep a rolling archive of a repo, org or ecosystem's activity.
🧑💻 API usage
Run the Actor programmatically with the Apify API or clients.
cURL
curl -X POST "https://api.apify.com/v2/acts/logiover~github-archive-events-scraper/runs?token=YOUR_APIFY_TOKEN" \-H "Content-Type: application/json" \-d '{"startDate": "2024-06-15","endDate": "2024-06-15","hours": [15],"eventTypes": ["WatchEvent"],"maxItems": 2000}'
Node.js (apify-client)
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: 'YOUR_APIFY_TOKEN' });const run = await client.actor('logiover/github-archive-events-scraper').call({startDate: '2024-06-15',endDate: '2024-06-15',eventTypes: ['PullRequestEvent', 'IssuesEvent'],repoFilter: ['facebook/react'],maxItems: 10000,});const { items } = await client.dataset(run.defaultDatasetId).listItems();console.log(items);
Python (apify-client)
from apify_client import ApifyClientclient = ApifyClient("YOUR_APIFY_TOKEN")run = client.actor("logiover/github-archive-events-scraper").call(run_input={"startDate": "2024-06-15","endDate": "2024-06-15","eventTypes": ["WatchEvent"],"orgFilter": ["microsoft"],"maxItems": 10000,})for item in client.dataset(run["defaultDatasetId"]).iterate_items():print(item["repoName"], item["actorLogin"], item["createdAt"])
🤖 Use with AI agents (MCP)
This Actor works as a tool for AI agents through the Apify MCP server, so an LLM assistant can pull GitHub history on demand. Point your MCP-compatible client (Claude, Cursor, or the Apify Tester MCP client) at the Apify MCP server and the agent can call this Actor directly.
Example prompt: "Use the GitHub Archive Events Scraper to get every star (WatchEvent) for the repo
vercel/next.json 2024-06-15, then tell me how many there were and list the top 10 users who starred it."
❓ FAQ
Is the GitHub Archive Events Scraper keyless — do I need a GitHub token or login?
No. GH Archive is a public static file host, so the Actor needs no GitHub token, OAuth, API key or account. Just set a date range and run.
How is this different from the GitHub REST Events API?
The GitHub REST Events API only returns the ~90 most recent events for a repo or user and is heavily rate-limited. GH Archive is the full historical bulk record of every public event since 2011, so you can query any date in the past and pull unlimited history.
How far back does the data go?
GH Archive publishes hourly files from 2011-02-12 to roughly the current hour. You can request any date in that range. Dates before 2011-02-12 have no files and are skipped.
How much data can one run return?
A single UTC hour contains hundreds of thousands of events. With filters you typically pull thousands to tens of thousands of rows per day; without filters a run can reach millions. Use maxItems and eventTypes to control volume and cost.
Why did my run return zero results?
Usually one of three reasons: (1) the date/hour isn't published yet (very recent hours 404 briefly), (2) your eventTypes / repoFilter / actorFilter / orgFilter matched nothing in that window, or (3) the range was empty. Widen the window, clear filters, or pick a fully-published past date.
Why are some fields empty on a row?
Fields are event-type specific. A WatchEvent (star) has no PR or issue data, so those columns are omitted; a PushEvent fills commitCount/commitMessages but not prTitle. Each row only carries the fields relevant to its eventType.
What is a WatchEvent — is it a star?
Yes. In the GitHub Events schema a star is recorded as a WatchEvent with action: "started". To reconstruct star history, filter eventTypes: ["WatchEvent"] for your target repo across a date range.
Can I export to CSV, JSON or Excel?
Yes. After a run, download the dataset from the Apify Console as CSV, JSON, Excel, HTML, XML or JSONL, or pull it through the Apify API. Every event is a flat row, so it imports cleanly into spreadsheets and databases.
How fast is it, and how much does it cost?
Speed is bound by download size — each hour file is ~70 MB gzipped. Restricting hours and eventTypes makes runs faster and cheaper. Pricing is pay-per-result, so tight filters keep cost low.
Is scraping GitHub Archive data legal?
GH Archive is a public, openly published dataset of already-public GitHub events. This Actor only reads that public data. You are responsible for using it in line with GitHub's terms, GH Archive's terms and applicable laws such as GDPR.
How often is the data updated?
GH Archive adds a new file roughly every hour, so recent activity becomes available within a short delay. Schedule this Actor to keep a rolling, up-to-date archive of any repo, org or ecosystem.
Which other GitHub scrapers pair well with this one?
Combine it with the GitHub Repository Scraper (repo metadata, stars, topics, languages) and GitHub Activity Stream (a specific user's or repo's recent activity) for a complete GitHub dataset. See the related scrapers below.
⚖️ Is it legal?
This Actor extracts only publicly available, openly published data from GH Archive — a public dataset of GitHub's own public event stream. It is intended for legitimate research, analytics, recruiting and monitoring use. You are responsible for complying with GitHub's Terms of Service, GH Archive's terms, GDPR and any applicable local laws and privacy regulations when you store or process the results, particularly any personal data such as usernames.
🔗 Related scrapers by logiover
Building a wider developer-data pipeline? Pair this with the rest of the logiover developer-tools suite:
- GitHub Repository Scraper — repo metadata, stars, forks, topics, languages and more by name or search.
- GitHub Activity Stream — a specific user's or repo's recent public activity feed.
- npm Package Intelligence Scraper — npm registry metadata, versions, dependencies and download stats.
- PyPI Package Scraper — Python package metadata, releases and maintainer data.
- Docker Hub Scraper · crates.io Scraper · CVE Security Advisory Monitor
👉 Browse all logiover scrapers on Apify Store — 230+ actors across developer tools, real estate, jobs, crypto, social media and B2B data.
📝 Changelog
2026-07-22
- 🎉 Initial release. Streams GH Archive hourly files (
data.gharchive.org), gunzips and parses newline-delimited JSON line by line, and saves flat event rows. - Filters by event type, repository (substring), actor login and organization, with a global
maxItemscap and per-file dedupe by event ID. - Memory-safe streaming (no whole-file buffering), graceful 404 skips for unpublished hours, and fresh-IP retries with exponential backoff on transient errors.