OceanirDocs

Dashboard
OverviewAPI ReferenceGuidesEnterpriseChangelog
← Back to Docs
Step-by-Step Guides
Overview
Getting Started
Auth Integration
Orca Geolocation
MCP Workflows
GuideMCPAgent workflows

Oceanir MCP workflows

Oceanir MCP is not just developer API access. It lets teams plug visual verification into AI workflows: analyze image and video evidence, generate reviewable reports, and route uncertain cases to humans.

1. Pull image from case folder
2. Send image to Oceanir
3. Get ranked location candidates
4. Generate evidence summary
5. Export PDF
6. Save report to case folder
7. Notify analyst

Where MCP fits

MCP turns Oceanir into a step inside an existing analyst, claims, newsroom, legal, or security workflow. The agent can fetch the media, call Oceanir, assemble the evidence, export the report, and leave the final decision with a human reviewer.

Insurance claims

New claim photo -> Oceanir verifies likely location/property -> creates report -> flags mismatch -> sends to adjuster

Journalism

Breaking image or video frame -> Oceanir checks claimed location -> returns evidence -> journalist confirms -> exports verification note

Corporate site review

Contractor submits site images -> Oceanir compares imagery against expected site -> saves report to project folder

Legal evidence documentation

Image evidence uploaded -> Oceanir analyzes visual context -> generates audit trail -> exports PDF for review

Enterprise security

Incident image -> Oceanir estimates location context -> compares against known facilities -> routes to security team

The strongest public framing: Oceanir MCP lets teams plug visual verification into AI workflows: analyze image/video evidence, generate reviewable reports, and route uncertain cases to humans.

Design tools around cases

A single analyze_imagetool is useful for demos, but operational teams need case-shaped tools that preserve context and create auditable outputs. The working MCP server below uses Oceanir's v1 API-key endpoints.

create_verification_case
analyze_case_image
list_verification_cases
generate_case_summary
export_case_report
flag_location_mismatch
get_oceanir_usage

Recommended lifecycle

create_verification_case
  -> analyze_case_image
  -> generate_case_summary
  -> export_case_report
  -> flag_location_mismatch

The workflow tools below are backed by API-key endpoints: cases are created through /api/v1/cases, images are analyzed through /api/v1/cases/:caseId/images/analyze, summaries come from /api/v1/cases/:caseId/summary, and reports export through /api/v1/cases/:caseId/report.

Add Oceanir to your agent

Use the same Oceanir MCP server across coding agents, desktop assistants, and custom GPT workflows. Pick the client your team already uses, add the server, then ask the agent to run the case lifecycle instead of calling a single raw endpoint.

Before you connect a client

Create an Oceanir API key from Workspace -> API Keys, install Node.js 20 or newer, and save the MCP server file from the next section at ~/oceanir-mcp/index.js. The same server powers Codex, Claude Code, Claude Desktop, Cursor, Windsurf, and other local MCP clients.

mkdir -p ~/oceanir-mcp
cd ~/oceanir-mcp
npm init -y
npm install @modelcontextprotocol/sdk node-fetch
export OCEANIR_API_KEY="your-api-key-here"

Codex

Engineering teams adding Oceanir to repo workflows, scripts, and internal tools.

Add the local MCP server once. Codex CLI and the IDE extension share the same MCP config, so the tool is available in both places.

export OCEANIR_API_KEY="your-api-key-here"
codex mcp add oceanir -- node ~/oceanir-mcp/index.js
codex mcp list

Claude Code

Case automation inside a codebase, project folder, or analyst operations repo.

Use a user-scoped server for personal access or project scope when the team should share the MCP entry.

claude mcp add oceanir --scope user --env OCEANIR_API_KEY=your-api-key-here -- node ~/oceanir-mcp/index.js
claude mcp list

Claude Desktop

Analysts who want Oceanir available in regular Claude conversations.

Add the server to Claude Desktop's MCP config, then restart Claude Desktop.

{
  "mcpServers": {
    "oceanir": {
      "command": "node",
      "args": ["/absolute/path/to/oceanir-mcp/index.js"],
      "env": {
        "OCEANIR_API_KEY": "your-api-key-here"
      }
    }
  }
}

ChatGPT

Custom GPTs that need workflow-shaped Actions for case creation, analysis, summaries, and exports.

Use GPT Actions for HTTP endpoints today. Use a hosted remote MCP connector when you want ChatGPT Connectors / Deep Research style access.

operationId: create_verification_case
operationId: analyze_case_image
operationId: list_verification_cases
operationId: generate_case_summary
operationId: export_case_report
operationId: get_oceanir_usage

Generic MCP clients

Cursor, Windsurf, VS Code agent mode, or any client that reads MCP JSON.

Point the client at the same local server command and keep the API key in the environment.

{
  "mcpServers": {
    "oceanir": {
      "command": "node",
      "args": ["/absolute/path/to/oceanir-mcp/index.js"],
      "env": {
        "OCEANIR_API_KEY": "your-api-key-here"
      }
    }
  }
}

For shared operations, put the MCP setup in your internal onboarding docs and keep each analyst's Oceanir API key in their local environment or approved secret manager.

Prompt to test the workflow

Analyze this claim photo with Oceanir.
Return ranked location candidates, the strongest visual evidence, and any uncertainty.
If the claimed property address conflicts with the image evidence, flag it for human review.
Generate a concise review summary that an adjuster can read.

Local MCP server file

The server below exposes workflow-shaped Oceanir tools over stdio. Local MCP clients start this process when the agent needs Oceanir.

1. Get your Oceanir API key

Go to Workspace -> API Keys and create a new key. Store it as an environment variable before starting the MCP server.

2. Create the MCP server file

Save the following as ~/oceanir-mcp/index.js on your machine:

#!/usr/bin/env node
// Oceanir MCP workflow server
// Requires: npm install @modelcontextprotocol/sdk node-fetch

import { Server } from "@modelcontextprotocol/sdk/server/index.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
import fetch from "node-fetch";

const OCEANIR_API = "https://oceanir.ai/api";
const API_KEY = process.env.OCEANIR_API_KEY;

if (!API_KEY) {
  console.error("OCEANIR_API_KEY is required");
  process.exit(1);
}

async function oceanir(method, path, body) {
  const res = await fetch(`${OCEANIR_API}${path}`, {
    method,
    headers: {
      Authorization: `Bearer ${API_KEY}`,
      "Content-Type": "application/json",
    },
    ...(body ? { body: JSON.stringify(body) } : {}),
  });

  if (!res.ok) {
    throw new Error(`Oceanir request failed: ${res.status} ${await res.text()}`);
  }

  return res.json();
}

const server = new Server(
  { name: "oceanir-workflows", version: "1.0.0" },
  { capabilities: { tools: {} } }
);

server.setRequestHandler("tools/list", async () => ({
  tools: [
    {
      name: "create_verification_case",
      description: "Create a visual verification case for an investigation, claim, project, or incident.",
      inputSchema: {
        type: "object",
        properties: {
          title: { type: "string" },
          description: { type: "string" },
          claimed_location: { type: "string" }
        },
        required: ["title"]
      }
    },
    {
      name: "analyze_case_image",
      description: "Analyze an image URL with Oceanir and return location evidence, coordinates, confidence, and visual clues.",
      inputSchema: {
        type: "object",
        properties: {
          case_id: { type: "string" },
          image_url: { type: "string" },
          depth: { type: "integer", enum: [1, 2, 3], default: 2 }
        },
        required: ["case_id", "image_url"]
      }
    },
    {
      name: "list_verification_cases",
      description: "List existing Oceanir verification cases visible to the API key owner.",
      inputSchema: {
        type: "object",
        properties: {
          limit: { type: "integer", default: 20, minimum: 1, maximum: 200 }
        }
      }
    },
    {
      name: "get_oceanir_usage",
      description: "Fetch current Oceanir API usage and meter status.",
      inputSchema: { type: "object", properties: {} }
    },
    {
      name: "generate_case_summary",
      description: "Generate a concise case summary for human review.",
      inputSchema: {
        type: "object",
        properties: { case_id: { type: "string" } },
        required: ["case_id"]
      }
    },
    {
      name: "export_case_report",
      description: "Export a reviewable case report as PDF base64 or markdown.",
      inputSchema: {
        type: "object",
        properties: {
          case_id: { type: "string" },
          format: { type: "string", enum: ["pdf", "markdown"], default: "pdf" }
        },
        required: ["case_id"]
      }
    },
    {
      name: "flag_location_mismatch",
      description: "Produce a human-review mismatch note from claimed and observed locations.",
      inputSchema: {
        type: "object",
        properties: {
          claimed_location: { type: "string" },
          observed_location: { type: "string" },
          evidence: { type: "string" }
        },
        required: ["claimed_location", "observed_location"]
      }
    }
  ]
}));

server.setRequestHandler("tools/call", async (req) => {
  const args = req.params.arguments ?? {};

  switch (req.params.name) {
    case "create_verification_case": {
      const data = await oceanir("POST", "/v1/cases", {
        name: args.title ?? args.name,
        description: args.description,
        claimed_location: args.claimed_location,
      });
      return { content: [{ type: "text", text: JSON.stringify(data, null, 2) }] };
    }
    case "analyze_case_image": {
      const data = await oceanir("POST", `/v1/cases/${encodeURIComponent(args.case_id)}/images/analyze`, {
        image_url: args.image_url,
        depth: args.depth ?? 2,
      });
      return { content: [{ type: "text", text: JSON.stringify(data, null, 2) }] };
    }
    case "list_verification_cases": {
      const limit = Number(args.limit ?? 20);
      const data = await oceanir("GET", `/v1/cases?limit=${encodeURIComponent(limit)}`);
      return { content: [{ type: "text", text: JSON.stringify(data, null, 2) }] };
    }
    case "get_oceanir_usage": {
      const data = await oceanir("GET", "/v1/usage");
      return { content: [{ type: "text", text: JSON.stringify(data, null, 2) }] };
    }
    case "generate_case_summary": {
      const data = await oceanir("GET", `/v1/cases/${encodeURIComponent(args.case_id)}/summary`);
      return { content: [{ type: "text", text: JSON.stringify(data, null, 2) }] };
    }
    case "export_case_report": {
      const data = await oceanir("POST", `/v1/cases/${encodeURIComponent(args.case_id)}/report`, {
        format: args.format ?? "pdf",
      });
      return { content: [{ type: "text", text: JSON.stringify(data, null, 2) }] };
    }
    case "flag_location_mismatch": {
      const mismatch = [
        "Location mismatch flagged for human review.",
        `Claimed: ${args.claimed_location}`,
        `Observed: ${args.observed_location}`,
        args.evidence ? `Evidence: ${args.evidence}` : "",
      ].filter(Boolean).join("\n");
      return { content: [{ type: "text", text: mismatch }] };
    }
    default:
      throw new Error(`Unknown tool: ${req.params.name}`);
  }
});

const transport = new StdioServerTransport();
await server.connect(transport);

3. Install dependencies

cd ~/oceanir-mcp
npm install @modelcontextprotocol/sdk node-fetch

4. Configure Claude Desktop

Open ~/Library/Application Support/Claude/claude_desktop_config.json and add:

{
  "mcpServers": {
    "oceanir": {
      "command": "node",
      "args": ["/root/oceanir-mcp/index.js"],
      "env": {
        "OCEANIR_API_KEY": "your-api-key-here"
      }
    }
  }
}

5. Restart Claude Desktop

Quit and relaunch Claude Desktop. The assistant can now analyze evidence, list existing cases, summarize results, and check usage during the workflow.

Try it with a workflow prompt: Analyze this claim photo with Oceanir, compare the result to the claimed property address, summarize the visual evidence, and flag any mismatch for an adjuster.

ChatGPT Actions

ChatGPT Custom GPTs can use the same workflow model through HTTP Actions. This is the easiest ChatGPT path when you already have HTTP endpoints and do not want to run a hosted remote MCP server yet.

Action schema starter

openapi: 3.1.0
info:
  title: Oceanir Visual Verification Workflows
  version: 1.0.0
servers:
  - url: https://oceanir.ai
paths:
  /api/v1/cases:
    post:
      operationId: create_verification_case
      summary: Create a visual verification case
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [name]
              properties:
                name: { type: string }
                description: { type: string }
                claimed_location: { type: string }
      responses:
        "201":
          description: Created case
          content:
            application/json:
              schema: { type: object }
    get:
      operationId: list_verification_cases
      summary: List existing verification cases for the authenticated workspace
      responses:
        "200":
          description: Case list
          content:
            application/json:
              schema: { type: object }
  /api/v1/cases/{case_id}/images/analyze:
    post:
      operationId: analyze_case_image
      summary: Analyze an image and attach the result to a case
      parameters:
        - name: case_id
          in: path
          required: true
          schema: { type: string }
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [image_url]
              properties:
                image_url: { type: string }
                depth:
                  type: integer
                  enum: [1, 2, 3]
                  default: 2
      responses:
        "200":
          description: Attached image analysis
          content:
            application/json:
              schema: { type: object }
  /api/v1/cases/{case_id}/summary:
    get:
      operationId: generate_case_summary
      summary: Generate a case summary for human review
      parameters:
        - name: case_id
          in: path
          required: true
          schema: { type: string }
      responses:
        "200":
          description: Case summary
          content:
            application/json:
              schema: { type: object }
  /api/v1/cases/{case_id}/report:
    post:
      operationId: export_case_report
      summary: Export a reviewable case report
      parameters:
        - name: case_id
          in: path
          required: true
          schema: { type: string }
      requestBody:
        content:
          application/json:
            schema:
              type: object
              properties:
                format:
                  type: string
                  enum: [pdf, markdown]
                  default: pdf
      responses:
        "200":
          description: PDF base64 or markdown report
          content:
            application/json:
              schema: { type: object }
  /api/v1/usage:
    get:
      operationId: get_oceanir_usage
      summary: Fetch current API usage and meter status
      responses:
        "200":
          description: API usage summary
          content:
            application/json:
              schema:
                type: object
components:
  securitySchemes:
    OceanirApiKey:
      type: apiKey
      in: header
      name: Authorization
security:
  - OceanirApiKey: []

In the Action settings, use API key authentication with the Authorization header and the value Bearer your-api-key-here.

ChatGPT Actions work best when the image is available by URL. For private case folders, use your agent or internal connector to fetch the file first, then pass it to Oceanir through your controlled integration.

ChatGPT Connector / remote MCP

If your workspace uses ChatGPT developer mode connectors, expose Oceanir through a hosted remote MCP endpoint instead of the local stdio file. Use OAuth or workspace-scoped authorization for production; avoid embedding a shared API key in a public connector.

Remote MCP server URL:
https://your-company.example.com/oceanir/mcp

Recommended tools:
create_verification_case
analyze_case_image
list_verification_cases
generate_case_summary
export_case_report
flag_location_mismatch
get_oceanir_usage

Credit usage

Each Oceanir MCP or Action analysis draws from your Oceanir balance. D1 is for quick surface checks, D2 is standard analysis, and D3 is the deeper forensic workflow for Pro and Unit subscribers. Monitor usage in Workspace -> Usage.