Managing multiple MTurk accounts can be tedious. What if you could paste multiple HIT set IDs once and let a userscript automatically accept HITs for all connected accounts?
Here’s how I built a centralized MTurk HIT catcher using PHP, a JSON endpoint, and a userscript.
Features
Central PHP page to save and manage HIT set IDs.
Toggle catching HITs on/off.
JSON endpoint for userscripts to fetch IDs.
Userscript auto-accepts HITs for multiple accounts.
Server rendering using Ngrok for remote access.
PHP Controller (hitaccept.php)
This page allows you to save HIT set IDs, see the current status, and serve IDs as JSON.
<?php
$file = __DIR__ . "/hit_ids.json";
$statusFile = __DIR__ . "/status.txt";
if (isset($_GET["toggle"])) {
$status = ($_GET["toggle"] === "off") ? "off" : "on";
file_put_contents($statusFile, $status);
echo "Status set to $status. <a href='hitaccept.php'>Back</a>";
exit;
}
if ($_SERVER["REQUEST_METHOD"] === "POST") {
$data = $_POST["hit_ids"] ?? "";
$ids = array_filter(array_map("trim", explode("\n", $data)));
file_put_contents($file, json_encode($ids));
echo "Saved! <a href='hitaccept.php'>Back</a>";
exit;
}
if (isset($_GET["json"])) {
header("Content-Type: application/json");
$status = file_exists($statusFile) ? trim(file_get_contents($statusFile)) : "on";
$ids = file_exists($file) ? file_get_contents($file) : "[]";
echo json_encode([
"status" => $status,
"ids" => json_decode($ids, true)
]);
exit;
}
$current = file_exists($file) ? file_get_contents($file) : "[]";
$status = file_exists($statusFile) ? trim(file_get_contents($statusFile)) : "on";
?>
<!DOCTYPE html>
<html>
<head>
<title>MTurk HIT Controller</title>
</head>
<body>
<h2>📋 Paste HIT Set IDs (one per line)</h2>
<form method="POST">
<textarea name="hit_ids" rows="6" cols="60"></textarea><br><br>
<button type="submit">💾 Save IDs</button>
</form>
<h3>Current HIT IDs</h3>
<pre><?php echo htmlspecialchars($current); ?></pre>
<h3>Status: <?php echo strtoupper($status); ?></h3>
<p>
<a href="?toggle=on">▶️ Start Catching</a> |
<a href="?toggle=off">⏹ Stop Catching</a>
</p>
<p>JSON endpoint: <a href="hitaccept.php?json">hitaccept.php?json</a></p>
</body>
</html>
What it does:
Save multiple HIT set IDs.
Toggle catching on/off.
Serve a JSON endpoint for your userscript.
Userscript for Auto-Accepting HITs
Install in Tampermonkey or Greasemonkey:
// ==UserScript==
// @name MTurk Central HIT Catcher
// @namespace yourdomain.com
// @version 1.0
// @description Accept HITs automatically from set_ids provided by central server
// @match https://worker.mturk.com/*
// @grant GM_xmlhttpRequest
// ==/UserScript==
(function() {
'use strict';
const SERVER_URL = "https://your-ngrok-url.ngrok-free.app/hitaccept.php?json";
const FETCH_INTERVAL = 10000; // 10s
function fetchSetIdsAndCatch() {
GM_xmlhttpRequest({
method: "GET",
url: SERVER_URL,
onload: function(response) {
try {
let data = JSON.parse(response.responseText);
if (data.status === "off") {
console.log("⏹ Catcher stopped by server.");
return;
}
let ids = data.ids || [];
ids.forEach(id => {
let acceptUrl = `https://worker.mturk.com/projects/${id}/tasks/accept_random?format=json`;
GM_xmlhttpRequest({
method: "GET",
url: acceptUrl,
onload: function(res) {
if (res.status === 200 && res.responseText.includes("task_id")) {
console.log("✅ Accepted HIT:", id);
} else {
console.log("❌ No HITs available for:", id);
}
}
});
});
} catch (e) {
console.error("Error parsing JSON:", e);
}
}
});
}
setInterval(fetchSetIdsAndCatch, FETCH_INTERVAL);
console.log("🚀 MTurk Central HIT Catcher started, polling every", FETCH_INTERVAL/1000, "seconds");
})();
Running the Project
- Start your PHP server locally:
php -S localhost:8000
- Expose it to the internet via Ngrok:
ngrok http 8000
- Replace SERVER_URL in your userscript with your Ngrok URL:
https://your-ngrok-url.ngrok-free.app/hitaccept.php?json
Open the Tampermonkey dashboard and activate the script.
Go to hitaccept.php, paste your HIT set IDs, and click Start Catching.
Check your browser console for logs:
HIT accepted
No HITs available
Summary
With this setup, you can:
Centralize multiple HIT IDs.
Control the catching process via a web interface.
Automatically accept HITs across multiple accounts.
It’s perfect for heavy MTurk users or small teams who need automation without manual repetition.
Top comments (1)
To tweak your PHP-based HIT catcher for extra MTurk features, like filtering HITs by reward or qualifications, you’ll want to play around with MTurk’s API filtering options. If you’re dealing with a lot of HIT IDs, things might slow down a bit, especially with all those API calls or database queries. To keep things running smooth, consider caching results, fine-tuning your database with some indexing, and controlling the number of requests to avoid hitting those rate limits. Also, using batch processing or pagination can help you handle big datasets without breaking a sweat. If you want to level up your HIT catcher, think about integrating it with third-party MTurk tools like TurkerView or MTurk Suite. They’ve got cool extras like performance analytics and HIT tracking that can be super useful through their APIs or custom plugins.