FarFISH Logo
FarFISHDocs

Steam Integration API

Track gaming achievements, social tasks, and daily activities through the Steam integration system.

Base URL

text
https://app.farfish.xyz/api/steam

Platform Note: All gaming features (Steam integration, fishing, tasks) are available across all FarFISH apps - Web App, Base App, Farcaster Mini App, and Android App.


GET /api/steam/task-status

Get all Steam-related task completion status for a wallet.

Request

Endpoint: GET /api/steam/task-status?wallet={address}

Query Parameters:

  • wallet (required) - Ethereum wallet address

Example:

text
GET /api/steam/task-status?wallet=0x742d35cc6634c0532925a3b844bc9e7595f0beb9

Response

Success (200):

json
{
  "wallet": "0x742d35cc6634c0532925a3b844bc9e7595f0beb9",
  "tasks": {
    "daily_checkin": false,
    "add_miniapp": true,
    "fc_follow": true,
    "fc_like_recast": false,
    "fc_comment": false,
    "referral": true,
    "referral_milestone_5": true,
    "referral_milestone_10": false,
    "referral_milestone_30": false,
    "referral_milestone_50": false,
    "nft_mint": true
  },
  "fishingCooldown": 43200,
  "timestamp": "2025-01-12T10:30:00.000Z"
}

Response Schema:

typescript
{
  wallet: string;           // Queried wallet address
  tasks: {
    daily_checkin: boolean;         // true = on cooldown, false = available
    add_miniapp: boolean;           // Added mini app to Farcaster
    fc_follow: boolean;             // Followed on Farcaster
    fc_like_recast: boolean;        // Liked/recasted post
    fc_comment: boolean;            // Commented on post
    referral: boolean;              // Made at least 1 referral
    referral_milestone_5: boolean;  // 5+ referrals
    referral_milestone_10: boolean; // 10+ referrals
    referral_milestone_30: boolean; // 30+ referrals
    referral_milestone_50: boolean; // 50+ referrals
    nft_mint: boolean;              // Owns FarFISH NFT
  };
  fishingCooldown: number;  // Seconds until daily checkin available (0 = ready)
  timestamp: string;        // ISO timestamp of response
}

Daily Checkin (Fishing) Cooldown

Cooldown Duration: 24 hours (86,400 seconds)

Availability Logic:

typescript
const lastFishing = user.steam.fishing.last; // Unix timestamp
const now = Date.now() / 1000;
const elapsed = now - lastFishing;

if (elapsed >= 86400) {
  // Available to claim
  tasks.daily_checkin = false;
  fishingCooldown = 0;
} else {
  // On cooldown
  tasks.daily_checkin = true;
  fishingCooldown = 86400 - elapsed; // Seconds remaining
}

Task Completion Rewards

Completing Steam tasks contributes to overall progress and may unlock rewards like FRH bonuses or special NFTs.

cURL Example

bash
curl "https://app.farfish.xyz/api/steam/task-status?wallet=0x742d35cc6634c0532925a3b844bc9e7595f0beb9"

JavaScript Example

typescript
async function getTaskStatus(wallet: string) {
  const response = await fetch(
    `https://app.farfish.xyz/api/steam/task-status?wallet=${wallet}`
  );
  const data = await response.json();
  
  console.log('Fishing cooldown:', data.fishingCooldown, 'seconds');
  console.log('Tasks completed:', 
    Object.entries(data.tasks)
      .filter(([_, completed]) => completed)
      .map(([task]) => task)
  );
  
  return data;
}

POST /api/steam/task/complete

Mark a Steam task as completed.

Request

Endpoint: POST /api/steam/task/complete

Headers:

text
Content-Type: application/json

Body Schema:

typescript
{
  wallet: string;  // Ethereum wallet address
  taskId: string;  // Task identifier
}

Valid Task IDs:

  • daily_checkin - Daily fishing task
  • add_miniapp - Add mini app to Farcaster
  • fc_follow - Follow on Farcaster
  • fc_like_recast - Like/recast post
  • fc_comment - Comment on post

Example Request:

json
{
  "wallet": "0x742d35cc6634c0532925a3b844bc9e7595f0beb9",
  "taskId": "daily_checkin"
}

Response

Success (200):

json
{
  "success": true,
  "taskId": "daily_checkin",
  "timestamp": 1705056000
}

Error (400):

json
{
  "error": "Task on cooldown",
  "cooldownRemaining": 43200
}

Daily Checkin Special Behavior

The daily_checkin task has unique cooldown handling:

Data Updated: Task completion timestamp is recorded in the backend.

Cooldown Enforcement:

  • Cannot complete if less than 24 hours since last completion
  • Cooldown calculated server-side (untrusted client timestamps)

Other Tasks

Data Updated: Task completion is recorded with timestamp in the backend.

Idempotent: Completing already-completed task returns success.

cURL Example

bash
curl -X POST https://app.farfish.xyz/api/steam/task/complete \
  -H "Content-Type: application/json" \
  -d '{
    "wallet": "0x742d35cc6634c0532925a3b844bc9e7595f0beb9",
    "taskId": "daily_checkin"
  }'

JavaScript Example

typescript
async function completeTask(wallet: string, taskId: string) {
  const response = await fetch('https://app.farfish.xyz/api/steam/task/complete', {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({ wallet, taskId })
  });
  
  const data = await response.json();
  
  if (data.success) {
    console.log(`Task ${taskId} completed!`);
  } else {
    console.error('Error:', data.error);
  }
}

POST /api/steam/verify

Verify on-chain task completion (NFT minting, staking).

Request

Endpoint: POST /api/steam/verify

Headers:

text
Content-Type: application/json

Body Schema:

typescript
{
  wallet: string;  // Ethereum wallet address
  taskId: string;  // Task to verify
}

Verifiable Tasks:

  • nft_mint - Verify NFT ownership or active stake

Example Request:

json
{
  "wallet": "0x742d35cc6634c0532925a3b844bc9e7595f0beb9",
  "taskId": "nft_mint"
}

Response

Success (200):

json
{
  "success": true,
  "taskId": "nft_mint",
  "verified": true
}

Failure (200):

json
{
  "success": false,
  "taskId": "nft_mint",
  "verified": false,
  "reason": "No NFTs owned and no active stakes"
}

NFT Mint Verification Logic

Checks on-chain state via Base blockchain RPC:

  1. Check NFT Balance:

    typescript
    const balance = await nftContract.read.balanceOf([wallet]);
    if (balance > 0) return true; // Has NFT
    
  2. Check Active Stakes:

    typescript
    const stakeIds = await stakingContract.read.getUserStakeIds([wallet]);
    if (stakeIds.length > 0) return true; // Has staked NFTs
    
  3. Result:

    • If either check passes, task marked completed
    • Data stored: user:{wallet}.tasks.nft_mint = true

Verification Frequency

Verification can be called multiple times. Useful for:

  • Checking if task auto-completed after minting
  • Re-verifying after staking
  • Updating UI state after on-chain transactions

cURL Example

bash
curl -X POST https://app.farfish.xyz/api/steam/verify \
  -H "Content-Type: application/json" \
  -d '{
    "wallet": "0x742d35cc6634c0532925a3b844bc9e7595f0beb9",
    "taskId": "nft_mint"
  }'

JavaScript Example

typescript
async function verifyTask(wallet: string, taskId: string) {
  const response = await fetch('https://app.farfish.xyz/api/steam/verify', {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({ wallet, taskId })
  });
  
  const data = await response.json();
  
  if (data.verified) {
    console.log(`Task ${taskId} verified!`);
  } else {
    console.log(`Task ${taskId} not yet completed:`, data.reason);
  }
}

GET /api/steam/progress

Get user's overall Steam progress with auto-verification.

Request

Endpoint: GET /api/steam/progress?wallet={address}

Query Parameters:

  • wallet (required) - Ethereum wallet address

Example:

text
GET /api/steam/progress?wallet=0x742d35cc6634c0532925a3b844bc9e7595f0beb9

Response

Success (200):

json
{
  "progress": {
    "nft_mint": true,
    "fc_follow": true,
    "fc_like_recast": false,
    "referral": true,
    "referral_milestone_5": true
  },
  "referralCount": 7
}

Response Schema:

typescript
{
  progress: Record<string, boolean>; // Task completion map
  referralCount: number;             // Total referrals made
}

Auto-Verification Behavior

On every request, this endpoint automatically:

  1. Calls /api/steam/verify for nft_mint task
  2. Updates task completion status if verification passes
  3. Returns current progress including auto-verified tasks

Benefits:

  • UI stays up-to-date with on-chain state
  • No manual verification button needed
  • Seamless task completion after minting/staking

cURL Example

bash
curl "https://app.farfish.xyz/api/steam/progress?wallet=0x742d35cc6634c0532925a3b844bc9e7595f0beb9"

JavaScript Example

typescript
async function getSteamProgress(wallet: string) {
  const response = await fetch(
    `https://app.farfish.xyz/api/steam/progress?wallet=${wallet}`
  );
  const data = await response.json();
  
  const completedTasks = Object.keys(data.progress).filter(
    task => data.progress[task]
  );
  
  console.log('Completed tasks:', completedTasks);
  console.log('Total referrals:', data.referralCount);
  
  return data;
}

Backend Data Model

User Steam Data Structure

typescript
{
  steam: {
    fishing: {
      last: number  // Unix timestamp of last daily checkin
    },
    add_app: {
      completed: boolean,
      ts: number  // Completion timestamp
    },
    follow: {
      completed: boolean,
      ts: number
    },
    like_recast: {
      completed: boolean,
      ts: number
    },
    comment: {
      completed: boolean,
      ts: number
    }
  },
  tasks: {
    nft_mint: boolean,        // On-chain verified
    referral: boolean,
    referral_milestone_5: boolean,
    referral_milestone_10: boolean,
    referral_milestone_30: boolean,
    referral_milestone_50: boolean
  }
}

Referral Milestone Logic

Referral milestones auto-update based on refcount:{wallet}:

typescript
const referralCount = await backend.get(`refcount for wallet`);

tasks.referral = referralCount >= 1;
tasks.referral_milestone_5 = referralCount >= 5;
tasks.referral_milestone_10 = referralCount >= 10;
tasks.referral_milestone_30 = referralCount >= 30;
tasks.referral_milestone_50 = referralCount >= 50;

Integration Example

Complete Steam task tracking UI:

typescript
// Get wallet address from your Web3 connection library
const { address } = useWalletConnection();
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';

function useSteamTasks() {
  const { address } = useAccount();
  const queryClient = useQueryClient();
  
  // Fetch task status
  const { data: status, isLoading } = useQuery({
    queryKey: ['steam', 'status', address],
    queryFn: async () => {
      const res = await fetch(`/api/steam/task-status?wallet=${address}`);
      return res.json();
    },
    enabled: !!address,
    refetchInterval: 10_000, // Poll every 10 seconds
  });
  
  // Complete task mutation
  const completeTask = useMutation({
    mutationFn: async (taskId: string) => {
      const res = await fetch('/api/steam/task/complete', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ wallet: address, taskId })
      });
      return res.json();
    },
    onSuccess: () => {
      // Refetch status after completion
      queryClient.invalidateQueries({ queryKey: ['steam', 'status', address] });
    },
  });
  
  return { status, isLoading, completeTask };
}

// Usage
function SteamDashboard() {
  const { status, isLoading, completeTask } = useSteamTasks();
  
  if (isLoading) return <div>Loading...</div>;
  
  const dailyAvailable = status.fishingCooldown === 0;
  
  return (
    <div>
      <h2>Daily Checkin</h2>
      {dailyAvailable ? (
        <button onClick={() => completeTask.mutate('daily_checkin')}>
          Claim Daily Reward
        </button>
      ) : (
        <p>Next claim in: {Math.floor(status.fishingCooldown / 3600)} hours</p>
      )}
      
      <h2>Social Tasks</h2>
      <ul>
        <li>Follow: {status.tasks.fc_follow ? '✅' : '⬜'}</li>
        <li>Like/Recast: {status.tasks.fc_like_recast ? '✅' : '⬜'}</li>
        <li>Comment: {status.tasks.fc_comment ? '✅' : '⬜'}</li>
      </ul>
      
      <h2>Milestones</h2>
      <ul>
        <li>1 Referral: {status.tasks.referral ? '✅' : '⬜'}</li>
        <li>5 Referrals: {status.tasks.referral_milestone_5 ? '✅' : '⬜'}</li>
        <li>10 Referrals: {status.tasks.referral_milestone_10 ? '✅' : '⬜'}</li>
      </ul>
    </div>
  );
}

Error Handling

ErrorHTTP StatusMeaningAction
Task on cooldown400Cannot complete yetDisplay cooldown timer
Invalid task ID400Unknown taskIdCheck valid task list
Verification failed200On-chain check failedUser hasn't completed requirement
Server error500Backend/RPC issueRetry with exponential backoff

Last updated: October 12, 2026