Data Labeling Marketplace

Data Labeling Marketplace

The Data Labeling Marketplace on PandaChain connects data requesters with workers who label data for ML training. Budgets are held in escrow, payments are automatic, and reputation is tracked on-chain.


How It Works

RoleActionOutcome
RequesterPosts labeling request with budgetBudget locked in escrow
WorkerClaims task, submits labelsEarns PANDA per accepted label
RequesterReviews submissions, accepts/rejectsAccepted = payment released
SystemTracks reputation, enforces deadlinesQuality incentives maintained

Posting a Labeling Request

  1. Navigate to /app/labor/post
  2. Fill in the request form:
    • Title: Clear description of the labeling task
    • Category: Image, Text, Audio, Video, RLHF, or Code
    • Description: Detailed guidelines for workers
    • Data Schema: JSON schema for expected label format
    • Price per Label: How much PANDA each accepted label pays
    • Total Labels: Number of labels needed
    • Reputation Required: Minimum worker reputation (0-100)
    • Deadline: When the request expires
  3. Submit -- your budget (price x labels) is locked in the LaborMarketplace escrow
# On-chain: LaborMarketplace contract
@call
def post_request(self, ctx, title, category, description, schema, budget, price_per_label, reputation_required, deadline, total_labels):
    """Post a new labeling request. Budget is locked in escrow."""
    request_id = self.state.next_id
    self.state.requests[str(request_id)] = {
        "title": title,
        "requester": ctx.sender,
        "category": category,
        "budget": budget,
        "price_per_label": price_per_label,
        "status": "open",
        ...
    }
    # Lock funds
    self.state.escrow[str(request_id)] = budget
    self.state.next_id += 1

Submitting Labels (Workers)

  1. Browse the marketplace at /app/labor
  2. Filter by category, pay rate, deadline, or reputation requirement
  3. Click a request to view details and schema
  4. Click Claim Task to reserve a spot
  5. Submit your label data as JSON matching the schema
  6. Wait for the requester to review

Quality Tips

  • Follow the schema exactly -- malformed submissions are auto-rejected
  • Higher quality scores improve your reputation
  • Reputation unlocks higher-paying tasks
  • Consistent accuracy leads to more claims

Earning Reputation

Your on-chain reputation score (0-100) is calculated from:

FactorWeight
Acceptance rate40%
Average quality score30%
Total labels submitted20%
Account age10%

Higher reputation unlocks:

  • Access to premium requests (reputation-gated)
  • Priority in task claiming during high demand
  • Higher visibility to requesters

Earning from Datasets

Beyond individual labels, workers can earn ongoing revenue:

  1. Dataset Royalties: If a requester publishes a dataset using your labels, you earn a percentage of future sales
  2. Quality Bonuses: Some requesters offer bonus payments for top-quality submissions
  3. Referral Rewards: Invite other workers and earn from their first 10 tasks

Dispute Resolution

If a worker disagrees with a rejection:

  1. Worker initiates a dispute within 48 hours
  2. A panel of 3 randomly-selected high-reputation workers reviews the submission
  3. Majority vote decides the outcome
  4. If the dispute is upheld, the label is accepted and the requester's rejection rate increases
  5. Frivolous disputes cost a small stake
@call
def dispute_rejection(self, ctx, submission_id: str):
    """Initiate a dispute for a rejected submission."""
    sub = self.state.submissions[submission_id]
    if sub["worker"] != ctx.sender:
        raise ValueError("Only the worker can dispute")
    if sub["status"] != "rejected":
        raise ValueError("Can only dispute rejected submissions")
    # Lock dispute stake
    self.state.disputes[submission_id] = {
        "worker": ctx.sender,
        "initiated_at": ctx.block_number,
        "votes": {},
        "status": "pending",
    }

Contract Architecture

The LaborMarketplace system consists of:

ContractPurpose
LaborMarketplaceCore marketplace: requests, claims, submissions
ReputationRegistryTracks worker reputation scores
EscrowVaultHolds requester budgets until labels accepted
DisputeResolverHandles disputes with random panel selection

Categories

CategoryExamples
ImageObject detection, segmentation, classification
TextSentiment analysis, NER, summarization quality
AudioTranscription, speaker identification, emotion
VideoAction recognition, temporal annotation
RLHFPreference ranking, helpfulness scoring
CodeCode review, bug classification, complexity

API Reference

Query Methods

  • get_all_requests() -- List all open requests
  • get_request(id) -- Get request details
  • get_submissions(request_id) -- Get submissions for a request
  • get_contributors(request_id) -- Get contributor list with earnings
  • get_worker_profile(address) -- Get worker reputation and stats
  • get_stats() -- Marketplace-wide statistics
  • get_trending_categories() -- Categories sorted by activity

Call Methods

  • post_request(...) -- Post a new labeling request (locks budget)
  • claim_task(request_id) -- Claim a task as a worker
  • submit_label(request_id, data) -- Submit a label
  • accept_label(submission_id, quality_score) -- Accept a submission (requester)
  • reject_label(submission_id, reason) -- Reject a submission (requester)
  • dispute_rejection(submission_id) -- Initiate a dispute (worker)
  • withdraw_remaining(request_id) -- Withdraw unspent escrow after deadline (requester)