{"owner":"opengeos","repo":"segment-geospatial","hasSkills":true,"totalSkillsCount":2,"totalTokensCount":4071,"categories":["anthropic-skill","project-spec"],"hasMcp":false,"mcpConfig":null,"found":["agent-harness/cli_anything/samgeo/skills/SKILL.md","docs/api.md"],"skills":{"agent-harness/cli_anything/samgeo/skills/SKILL.md":"---\nname: \"cli-anything-samgeo\"\ndescription: \"CLI harness for segment-geospatial — segment satellite/aerial imagery with SAM models from the command line\"\n---\n\n# cli-anything-samgeo\n\nSegment geospatial imagery (satellite, aerial, drone) using Meta AI's Segment\nAnything Model (SAM) family from the command line. Supports SAM v1, SAM 2,\nSAM 3, FastSAM, HQ-SAM, and LangSAM (text-based).\n\n## Installation\n\nRequires Python >= 3.10.\n\n```bash\npip install segment-geospatial[all]\ncd agent-harness && pip install -e .\n```\n\n## Syntax\n\n```\ncli-anything-samgeo [--json] [--project PATH] COMMAND [ARGS...]\n```\n\nGlobal flags:\n- `--json` — Machine-readable JSON output (use this for agent consumption)\n- `--project PATH` — Path to project JSON file (required for project-scoped commands)\n\n## Command Groups\n\n### project — Project management\n```bash\ncli-anything-samgeo project new -n NAME -o PATH [-s SOURCE] [-t MODEL_TYPE] [-m MODEL_ID]\ncli-anything-samgeo --project PATH project info\ncli-anything-samgeo --project PATH project set-source IMAGE_PATH\ncli-anything-samgeo --project PATH project history [-l LIMIT]\n```\n\n### model — Model management\n```bash\ncli-anything-samgeo model list [-t TYPE]\ncli-anything-samgeo model info MODEL_TYPE [-m MODEL_ID]\ncli-anything-samgeo model check MODEL_TYPE\n```\n\nModel types: `sam`, `sam2`, `sam3`, `fast_sam`, `hq_sam`, `text_sam`\n\n### segment — Segmentation operations\n```bash\ncli-anything-samgeo --project PATH segment automatic -o OUTPUT [--min-size N] [--max-size N]\ncli-anything-samgeo --project PATH segment points -o OUTPUT -c \"x1,y1;x2,y2\" -l \"1,0\"\ncli-anything-samgeo --project PATH segment boxes -o OUTPUT -b \"x1,y1,x2,y2\"\ncli-anything-samgeo --project PATH segment text -o OUTPUT -t \"buildings\"\n```\n\n### data — Data operations\n```bash\ncli-anything-samgeo data info RASTER_PATH\ncli-anything-samgeo data download-tiles -o OUTPUT -b \"west,south,east,north\" [-z ZOOM] [-s SOURCE]\ncli-anything-samgeo data reproject INPUT OUTPUT [--crs EPSG:CODE]\ncli-anything-samgeo data split INPUT OUT_DIR [--tile-size N] [--overlap N]\ncli-anything-samgeo data basemaps [--all]\n```\n\n### vector — Vector operations\n```bash\ncli-anything-samgeo vector convert RASTER_MASK OUTPUT [--simplify TOLERANCE]\ncli-anything-samgeo vector info VECTOR_PATH\ncli-anything-samgeo vector filter INPUT OUTPUT [--min-area N] [--max-area N]\n```\n\n### export — Export operations\n```bash\ncli-anything-samgeo --project PATH export render OUTPUT [-f FORMAT] [--overwrite]\ncli-anything-samgeo export formats\n```\n\nFormats: `geotiff`, `cog`, `gpkg`, `shp`, `geojson`, `png`\n\n### session — Session management\n```bash\ncli-anything-samgeo --project PATH session status\ncli-anything-samgeo --project PATH session history [-l LIMIT]\n```\n\n## Example Workflows\n\n### Satellite image segmentation pipeline\n```bash\n# Download tiles\ncli-anything-samgeo --json data download-tiles -o image.tif -b \"-122.42,37.77,-122.40,37.79\" -z 17\n\n# Create project\ncli-anything-samgeo --json project new -n urban-seg -o project.json -s image.tif -t sam2\n\n# Run automatic segmentation\ncli-anything-samgeo --json --project project.json segment automatic -o masks.tif\n\n# Convert to GeoPackage\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg --simplify 1.0\n\n# Export as GeoJSON\ncli-anything-samgeo --json --project project.json export render output.geojson -f geojson --overwrite\n```\n\n### Text-based segmentation\n```bash\ncli-anything-samgeo --json project new -n text-seg -o proj.json -s image.tif -t text_sam\ncli-anything-samgeo --json --project proj.json segment text -o masks.tif -t \"buildings\"\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg\n```\n\n## Agent Guidance\n\n- Always use `--json` for machine-readable output\n- Create a project first before running segmentation commands\n- The `--project` flag must come before the command group\n- Check model availability with `model check TYPE` before segmenting\n- Use `data info` to inspect rasters before processing\n- Export formats are auto-detected from file extension in `vector convert`\n- For large images, use `--batch` with `segment automatic`\n","docs/api.md":"# REST API\n\nsegment-geospatial includes a built-in REST API powered by [FastAPI](https://fastapi.tiangolo.com/) that allows you to run image segmentation over HTTP. This is useful for integrating segmentation into web applications, pipelines, and non-Python clients.\n\n## Installation\n\nInstall the API dependencies with the `api` extra:\n\n```bash\npip install \"segment-geospatial[api]\"\n```\n\nTo also install a specific SAM model backend, combine extras:\n\n```bash\npip install \"segment-geospatial[api,samgeo3]\"\n```\n\n## Starting the Server\n\nUse the `samgeo-api` command:\n\n```bash\nsamgeo-api\n```\n\nOptions:\n\n```bash\nsamgeo-api --host 0.0.0.0 --port 8000        # Custom host/port\nsamgeo-api --preload sam2:sam2-hiera-large     # Preload a model at startup\nsamgeo-api --reload                            # Auto-reload for development\n```\n\nAlternatively, use `uvicorn` directly:\n\n```bash\nuvicorn samgeo.api:app --host 0.0.0.0 --port 8000\n```\n\nOnce running, interactive API docs (Swagger UI) are available at [http://localhost:8000/docs](http://localhost:8000/docs).\n\n## Endpoints\n\n### Health Check\n\n```\nGET /health\n```\n\nReturns the server status and version.\n\n```bash\ncurl http://localhost:8000/health\n```\n\n```json\n{\"status\": \"ok\", \"version\": \"1.2.3\"}\n```\n\n### List Models\n\n```\nGET /models\n```\n\nReturns available model versions/IDs and which models are currently loaded in memory.\n\n```bash\ncurl http://localhost:8000/models\n```\n\n### Clear Models\n\n```\nDELETE /models\n```\n\nClears the model cache and frees GPU memory.\n\n```bash\ncurl -X DELETE http://localhost:8000/models\n```\n\n### Automatic Segmentation\n\n```\nPOST /segment/automatic\n```\n\nRuns automatic mask generation on an uploaded image. Supports SAM, SAM2, and SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam2` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `sam2-hiera-large`, `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `foreground` | bool | `true` | Extract foreground objects only |\n| `unique` | bool | `true` | Assign unique ID to each object |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n| `points_per_side` | int | `32` | Points sampled per side (SAM/SAM2) |\n| `pred_iou_thresh` | float | `0.8` | IoU threshold for filtering |\n| `stability_score_thresh` | float | `0.95` | Stability score threshold |\n\n**Example:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/automatic \\\n  -F \"file=@image.tif\" \\\n  -F \"model_version=sam2\" \\\n  -F \"output_format=geojson\"\n```\n\n### Prompt-based Segmentation\n\n```\nPOST /segment/predict\n```\n\nRuns segmentation with point or bounding box prompts. Supports SAM, SAM2, and SAM3.\n\nFor SAM3 with bounding box prompts, the model finds **all similar objects** in the image (not just the object inside the box). Point prompts with SAM3 segment the specific object at the point location.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam3` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `point_coords` | string | none | JSON array of `[[x, y], ...]` |\n| `point_labels` | string | none | JSON array of `[1, 0, ...]` (1=foreground, 0=background) |\n| `boxes` | string | none | JSON array of `[[xmin, ymin, xmax, ymax], ...]` |\n| `point_crs` | string | none | CRS string (e.g., `EPSG:4326`) for point/box coordinates |\n| `multimask_output` | bool | `false` | Return multiple masks per prompt |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example with point prompts:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"point_coords=[[100, 200]]\" \\\n  -F \"point_labels=[1]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with box prompts (finds all similar objects):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.jpg\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 12,\n  \"detections\": [\n    {\"id\": 1, \"value\": 1, \"bbox\": [50, 80, 200, 250], \"width\": 150, \"height\": 170},\n    {\"id\": 2, \"value\": 2, \"bbox\": [310, 45, 480, 210], \"width\": 170, \"height\": 165}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 12,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"value\": 1, \"bbox_pixel\": [50.0, 80.0, 200.0, 250.0]}\n    }\n  ]\n}\n```\n\n### Text-prompt Segmentation\n\n```\nPOST /segment/text\n```\n\nRuns text-prompt segmentation using SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `prompt` | string | required | Text description (e.g., `building`, `tree`) |\n| `model_id` | string | auto | SAM3 model identifier (`facebook/sam3` or `facebook/sam3.1`) |\n| `backend` | string | `meta` | One of `meta`, `transformers`; SAM 3.1 uses `meta` |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `confidence_threshold` | float | `0.5` | Detection confidence threshold |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example (GeoJSON mask polygons):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.jpg\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 46,\n  \"detections\": [\n    {\"id\": 1, \"bbox\": [2506, 134, 2653, 324], \"width\": 147, \"height\": 190, \"score\": 0.887},\n    {\"id\": 2, \"bbox\": [1200, 450, 1380, 620], \"width\": 180, \"height\": 170, \"score\": 0.862}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 46,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"score\": 0.887, \"bbox_pixel\": [2506.47, 134.43, 2653.27, 323.52]}\n    }\n  ]\n}\n```\n\n## GeoJSON output\n\nWith `output_format=geojson`, every segmentation endpoint returns one polygon\nfeature per mask. Each feature's `properties` carry the mask's raster `value`\nand, when the model reports one, its confidence `score`, so a single request\nyields both geometry and confidence:\n\n```json\n{\"type\": \"Feature\", \"geometry\": {\"type\": \"Polygon\", \"coordinates\": [...]}, \"properties\": {\"value\": 1, \"score\": 0.887}}\n```\n\n## Caching\n\nThe API automatically caches models and image encodings for better performance:\n\n- **Model cache**: Models are loaded once and reused across requests. Use `DELETE /models` to free GPU memory.\n- **Image cache**: When the same image is sent multiple times (e.g., with different prompts), the expensive image encoding step is skipped. This makes subsequent requests significantly faster.\n\nExample timing with a 13 MB GeoTIFF:\n\n| Request | Description | Time |\n|---------|-------------|------|\n| 1st | Model load + image encoding | ~7s |\n| 2nd | Same image, different prompt | ~0.4s |\n| 3rd | Same image, another prompt | ~0.2s |\n\n## Python Client Example\n\n```python\nimport requests\n\nurl = \"http://localhost:8000/segment/text\"\n\n# Get GeoJSON mask polygons\nwith open(\"image.tif\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.tif\", f, \"image/tiff\")},\n        data={\"prompt\": \"building\", \"output_format\": \"geojson\"},\n    )\n\ngeojson = response.json()\nprint(f\"Found {len(geojson['features'])} features\")\n```\n\n```python\n# Get bounding boxes in pixel coordinates (suitable for non-georeferenced images)\nwith open(\"image.jpg\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.jpg\", f, \"image/jpeg\")},\n        data={\"prompt\": \"car\", \"output_format\": \"json\"},\n    )\n\nresult = response.json()\nfor det in result[\"detections\"]:\n    print(f\"Object {det['id']}: bbox={det['bbox']}, score={det['score']:.3f}\")\n```\n\n## API Reference\n\n::: samgeo.api\n"},"files":{"agent-harness/cli_anything/samgeo/skills/SKILL.md":"---\nname: \"cli-anything-samgeo\"\ndescription: \"CLI harness for segment-geospatial — segment satellite/aerial imagery with SAM models from the command line\"\n---\n\n# cli-anything-samgeo\n\nSegment geospatial imagery (satellite, aerial, drone) using Meta AI's Segment\nAnything Model (SAM) family from the command line. Supports SAM v1, SAM 2,\nSAM 3, FastSAM, HQ-SAM, and LangSAM (text-based).\n\n## Installation\n\nRequires Python >= 3.10.\n\n```bash\npip install segment-geospatial[all]\ncd agent-harness && pip install -e .\n```\n\n## Syntax\n\n```\ncli-anything-samgeo [--json] [--project PATH] COMMAND [ARGS...]\n```\n\nGlobal flags:\n- `--json` — Machine-readable JSON output (use this for agent consumption)\n- `--project PATH` — Path to project JSON file (required for project-scoped commands)\n\n## Command Groups\n\n### project — Project management\n```bash\ncli-anything-samgeo project new -n NAME -o PATH [-s SOURCE] [-t MODEL_TYPE] [-m MODEL_ID]\ncli-anything-samgeo --project PATH project info\ncli-anything-samgeo --project PATH project set-source IMAGE_PATH\ncli-anything-samgeo --project PATH project history [-l LIMIT]\n```\n\n### model — Model management\n```bash\ncli-anything-samgeo model list [-t TYPE]\ncli-anything-samgeo model info MODEL_TYPE [-m MODEL_ID]\ncli-anything-samgeo model check MODEL_TYPE\n```\n\nModel types: `sam`, `sam2`, `sam3`, `fast_sam`, `hq_sam`, `text_sam`\n\n### segment — Segmentation operations\n```bash\ncli-anything-samgeo --project PATH segment automatic -o OUTPUT [--min-size N] [--max-size N]\ncli-anything-samgeo --project PATH segment points -o OUTPUT -c \"x1,y1;x2,y2\" -l \"1,0\"\ncli-anything-samgeo --project PATH segment boxes -o OUTPUT -b \"x1,y1,x2,y2\"\ncli-anything-samgeo --project PATH segment text -o OUTPUT -t \"buildings\"\n```\n\n### data — Data operations\n```bash\ncli-anything-samgeo data info RASTER_PATH\ncli-anything-samgeo data download-tiles -o OUTPUT -b \"west,south,east,north\" [-z ZOOM] [-s SOURCE]\ncli-anything-samgeo data reproject INPUT OUTPUT [--crs EPSG:CODE]\ncli-anything-samgeo data split INPUT OUT_DIR [--tile-size N] [--overlap N]\ncli-anything-samgeo data basemaps [--all]\n```\n\n### vector — Vector operations\n```bash\ncli-anything-samgeo vector convert RASTER_MASK OUTPUT [--simplify TOLERANCE]\ncli-anything-samgeo vector info VECTOR_PATH\ncli-anything-samgeo vector filter INPUT OUTPUT [--min-area N] [--max-area N]\n```\n\n### export — Export operations\n```bash\ncli-anything-samgeo --project PATH export render OUTPUT [-f FORMAT] [--overwrite]\ncli-anything-samgeo export formats\n```\n\nFormats: `geotiff`, `cog`, `gpkg`, `shp`, `geojson`, `png`\n\n### session — Session management\n```bash\ncli-anything-samgeo --project PATH session status\ncli-anything-samgeo --project PATH session history [-l LIMIT]\n```\n\n## Example Workflows\n\n### Satellite image segmentation pipeline\n```bash\n# Download tiles\ncli-anything-samgeo --json data download-tiles -o image.tif -b \"-122.42,37.77,-122.40,37.79\" -z 17\n\n# Create project\ncli-anything-samgeo --json project new -n urban-seg -o project.json -s image.tif -t sam2\n\n# Run automatic segmentation\ncli-anything-samgeo --json --project project.json segment automatic -o masks.tif\n\n# Convert to GeoPackage\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg --simplify 1.0\n\n# Export as GeoJSON\ncli-anything-samgeo --json --project project.json export render output.geojson -f geojson --overwrite\n```\n\n### Text-based segmentation\n```bash\ncli-anything-samgeo --json project new -n text-seg -o proj.json -s image.tif -t text_sam\ncli-anything-samgeo --json --project proj.json segment text -o masks.tif -t \"buildings\"\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg\n```\n\n## Agent Guidance\n\n- Always use `--json` for machine-readable output\n- Create a project first before running segmentation commands\n- The `--project` flag must come before the command group\n- Check model availability with `model check TYPE` before segmenting\n- Use `data info` to inspect rasters before processing\n- Export formats are auto-detected from file extension in `vector convert`\n- For large images, use `--batch` with `segment automatic`\n","docs/api.md":"# REST API\n\nsegment-geospatial includes a built-in REST API powered by [FastAPI](https://fastapi.tiangolo.com/) that allows you to run image segmentation over HTTP. This is useful for integrating segmentation into web applications, pipelines, and non-Python clients.\n\n## Installation\n\nInstall the API dependencies with the `api` extra:\n\n```bash\npip install \"segment-geospatial[api]\"\n```\n\nTo also install a specific SAM model backend, combine extras:\n\n```bash\npip install \"segment-geospatial[api,samgeo3]\"\n```\n\n## Starting the Server\n\nUse the `samgeo-api` command:\n\n```bash\nsamgeo-api\n```\n\nOptions:\n\n```bash\nsamgeo-api --host 0.0.0.0 --port 8000        # Custom host/port\nsamgeo-api --preload sam2:sam2-hiera-large     # Preload a model at startup\nsamgeo-api --reload                            # Auto-reload for development\n```\n\nAlternatively, use `uvicorn` directly:\n\n```bash\nuvicorn samgeo.api:app --host 0.0.0.0 --port 8000\n```\n\nOnce running, interactive API docs (Swagger UI) are available at [http://localhost:8000/docs](http://localhost:8000/docs).\n\n## Endpoints\n\n### Health Check\n\n```\nGET /health\n```\n\nReturns the server status and version.\n\n```bash\ncurl http://localhost:8000/health\n```\n\n```json\n{\"status\": \"ok\", \"version\": \"1.2.3\"}\n```\n\n### List Models\n\n```\nGET /models\n```\n\nReturns available model versions/IDs and which models are currently loaded in memory.\n\n```bash\ncurl http://localhost:8000/models\n```\n\n### Clear Models\n\n```\nDELETE /models\n```\n\nClears the model cache and frees GPU memory.\n\n```bash\ncurl -X DELETE http://localhost:8000/models\n```\n\n### Automatic Segmentation\n\n```\nPOST /segment/automatic\n```\n\nRuns automatic mask generation on an uploaded image. Supports SAM, SAM2, and SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam2` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `sam2-hiera-large`, `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `foreground` | bool | `true` | Extract foreground objects only |\n| `unique` | bool | `true` | Assign unique ID to each object |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n| `points_per_side` | int | `32` | Points sampled per side (SAM/SAM2) |\n| `pred_iou_thresh` | float | `0.8` | IoU threshold for filtering |\n| `stability_score_thresh` | float | `0.95` | Stability score threshold |\n\n**Example:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/automatic \\\n  -F \"file=@image.tif\" \\\n  -F \"model_version=sam2\" \\\n  -F \"output_format=geojson\"\n```\n\n### Prompt-based Segmentation\n\n```\nPOST /segment/predict\n```\n\nRuns segmentation with point or bounding box prompts. Supports SAM, SAM2, and SAM3.\n\nFor SAM3 with bounding box prompts, the model finds **all similar objects** in the image (not just the object inside the box). Point prompts with SAM3 segment the specific object at the point location.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam3` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `point_coords` | string | none | JSON array of `[[x, y], ...]` |\n| `point_labels` | string | none | JSON array of `[1, 0, ...]` (1=foreground, 0=background) |\n| `boxes` | string | none | JSON array of `[[xmin, ymin, xmax, ymax], ...]` |\n| `point_crs` | string | none | CRS string (e.g., `EPSG:4326`) for point/box coordinates |\n| `multimask_output` | bool | `false` | Return multiple masks per prompt |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example with point prompts:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"point_coords=[[100, 200]]\" \\\n  -F \"point_labels=[1]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with box prompts (finds all similar objects):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.jpg\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 12,\n  \"detections\": [\n    {\"id\": 1, \"value\": 1, \"bbox\": [50, 80, 200, 250], \"width\": 150, \"height\": 170},\n    {\"id\": 2, \"value\": 2, \"bbox\": [310, 45, 480, 210], \"width\": 170, \"height\": 165}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 12,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"value\": 1, \"bbox_pixel\": [50.0, 80.0, 200.0, 250.0]}\n    }\n  ]\n}\n```\n\n### Text-prompt Segmentation\n\n```\nPOST /segment/text\n```\n\nRuns text-prompt segmentation using SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `prompt` | string | required | Text description (e.g., `building`, `tree`) |\n| `model_id` | string | auto | SAM3 model identifier (`facebook/sam3` or `facebook/sam3.1`) |\n| `backend` | string | `meta` | One of `meta`, `transformers`; SAM 3.1 uses `meta` |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `confidence_threshold` | float | `0.5` | Detection confidence threshold |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example (GeoJSON mask polygons):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.jpg\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 46,\n  \"detections\": [\n    {\"id\": 1, \"bbox\": [2506, 134, 2653, 324], \"width\": 147, \"height\": 190, \"score\": 0.887},\n    {\"id\": 2, \"bbox\": [1200, 450, 1380, 620], \"width\": 180, \"height\": 170, \"score\": 0.862}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 46,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"score\": 0.887, \"bbox_pixel\": [2506.47, 134.43, 2653.27, 323.52]}\n    }\n  ]\n}\n```\n\n## GeoJSON output\n\nWith `output_format=geojson`, every segmentation endpoint returns one polygon\nfeature per mask. Each feature's `properties` carry the mask's raster `value`\nand, when the model reports one, its confidence `score`, so a single request\nyields both geometry and confidence:\n\n```json\n{\"type\": \"Feature\", \"geometry\": {\"type\": \"Polygon\", \"coordinates\": [...]}, \"properties\": {\"value\": 1, \"score\": 0.887}}\n```\n\n## Caching\n\nThe API automatically caches models and image encodings for better performance:\n\n- **Model cache**: Models are loaded once and reused across requests. Use `DELETE /models` to free GPU memory.\n- **Image cache**: When the same image is sent multiple times (e.g., with different prompts), the expensive image encoding step is skipped. This makes subsequent requests significantly faster.\n\nExample timing with a 13 MB GeoTIFF:\n\n| Request | Description | Time |\n|---------|-------------|------|\n| 1st | Model load + image encoding | ~7s |\n| 2nd | Same image, different prompt | ~0.4s |\n| 3rd | Same image, another prompt | ~0.2s |\n\n## Python Client Example\n\n```python\nimport requests\n\nurl = \"http://localhost:8000/segment/text\"\n\n# Get GeoJSON mask polygons\nwith open(\"image.tif\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.tif\", f, \"image/tiff\")},\n        data={\"prompt\": \"building\", \"output_format\": \"geojson\"},\n    )\n\ngeojson = response.json()\nprint(f\"Found {len(geojson['features'])} features\")\n```\n\n```python\n# Get bounding boxes in pixel coordinates (suitable for non-georeferenced images)\nwith open(\"image.jpg\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.jpg\", f, \"image/jpeg\")},\n        data={\"prompt\": \"car\", \"output_format\": \"json\"},\n    )\n\nresult = response.json()\nfor det in result[\"detections\"]:\n    print(f\"Object {det['id']}: bbox={det['bbox']}, score={det['score']:.3f}\")\n```\n\n## API Reference\n\n::: samgeo.api\n"},"items":[{"name":"api.md","path":"docs/api.md","rawUrl":"https://raw.githubusercontent.com/opengeos/segment-geospatial/HEAD/docs/api.md","title":"docs - API Interface Contract & Specifications","category":"project-spec","format":"markdown","content":"# REST API\n\nsegment-geospatial includes a built-in REST API powered by [FastAPI](https://fastapi.tiangolo.com/) that allows you to run image segmentation over HTTP. This is useful for integrating segmentation into web applications, pipelines, and non-Python clients.\n\n## Installation\n\nInstall the API dependencies with the `api` extra:\n\n```bash\npip install \"segment-geospatial[api]\"\n```\n\nTo also install a specific SAM model backend, combine extras:\n\n```bash\npip install \"segment-geospatial[api,samgeo3]\"\n```\n\n## Starting the Server\n\nUse the `samgeo-api` command:\n\n```bash\nsamgeo-api\n```\n\nOptions:\n\n```bash\nsamgeo-api --host 0.0.0.0 --port 8000        # Custom host/port\nsamgeo-api --preload sam2:sam2-hiera-large     # Preload a model at startup\nsamgeo-api --reload                            # Auto-reload for development\n```\n\nAlternatively, use `uvicorn` directly:\n\n```bash\nuvicorn samgeo.api:app --host 0.0.0.0 --port 8000\n```\n\nOnce running, interactive API docs (Swagger UI) are available at [http://localhost:8000/docs](http://localhost:8000/docs).\n\n## Endpoints\n\n### Health Check\n\n```\nGET /health\n```\n\nReturns the server status and version.\n\n```bash\ncurl http://localhost:8000/health\n```\n\n```json\n{\"status\": \"ok\", \"version\": \"1.2.3\"}\n```\n\n### List Models\n\n```\nGET /models\n```\n\nReturns available model versions/IDs and which models are currently loaded in memory.\n\n```bash\ncurl http://localhost:8000/models\n```\n\n### Clear Models\n\n```\nDELETE /models\n```\n\nClears the model cache and frees GPU memory.\n\n```bash\ncurl -X DELETE http://localhost:8000/models\n```\n\n### Automatic Segmentation\n\n```\nPOST /segment/automatic\n```\n\nRuns automatic mask generation on an uploaded image. Supports SAM, SAM2, and SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam2` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `sam2-hiera-large`, `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `foreground` | bool | `true` | Extract foreground objects only |\n| `unique` | bool | `true` | Assign unique ID to each object |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n| `points_per_side` | int | `32` | Points sampled per side (SAM/SAM2) |\n| `pred_iou_thresh` | float | `0.8` | IoU threshold for filtering |\n| `stability_score_thresh` | float | `0.95` | Stability score threshold |\n\n**Example:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/automatic \\\n  -F \"file=@image.tif\" \\\n  -F \"model_version=sam2\" \\\n  -F \"output_format=geojson\"\n```\n\n### Prompt-based Segmentation\n\n```\nPOST /segment/predict\n```\n\nRuns segmentation with point or bounding box prompts. Supports SAM, SAM2, and SAM3.\n\nFor SAM3 with bounding box prompts, the model finds **all similar objects** in the image (not just the object inside the box). Point prompts with SAM3 segment the specific object at the point location.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam3` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `point_coords` | string | none | JSON array of `[[x, y], ...]` |\n| `point_labels` | string | none | JSON array of `[1, 0, ...]` (1=foreground, 0=background) |\n| `boxes` | string | none | JSON array of `[[xmin, ymin, xmax, ymax], ...]` |\n| `point_crs` | string | none | CRS string (e.g., `EPSG:4326`) for point/box coordinates |\n| `multimask_output` | bool | `false` | Return multiple masks per prompt |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example with point prompts:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"point_coords=[[100, 200]]\" \\\n  -F \"point_labels=[1]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with box prompts (finds all similar objects):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.jpg\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 12,\n  \"detections\": [\n    {\"id\": 1, \"value\": 1, \"bbox\": [50, 80, 200, 250], \"width\": 150, \"height\": 170},\n    {\"id\": 2, \"value\": 2, \"bbox\": [310, 45, 480, 210], \"width\": 170, \"height\": 165}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 12,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"value\": 1, \"bbox_pixel\": [50.0, 80.0, 200.0, 250.0]}\n    }\n  ]\n}\n```\n\n### Text-prompt Segmentation\n\n```\nPOST /segment/text\n```\n\nRuns text-prompt segmentation using SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `prompt` | string | required | Text description (e.g., `building`, `tree`) |\n| `model_id` | string | auto | SAM3 model identifier (`facebook/sam3` or `facebook/sam3.1`) |\n| `backend` | string | `meta` | One of `meta`, `transformers`; SAM 3.1 uses `meta` |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `confidence_threshold` | float | `0.5` | Detection confidence threshold |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example (GeoJSON mask polygons):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.jpg\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 46,\n  \"detections\": [\n    {\"id\": 1, \"bbox\": [2506, 134, 2653, 324], \"width\": 147, \"height\": 190, \"score\": 0.887},\n    {\"id\": 2, \"bbox\": [1200, 450, 1380, 620], \"width\": 180, \"height\": 170, \"score\": 0.862}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 46,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"score\": 0.887, \"bbox_pixel\": [2506.47, 134.43, 2653.27, 323.52]}\n    }\n  ]\n}\n```\n\n## GeoJSON output\n\nWith `output_format=geojson`, every segmentation endpoint returns one polygon\nfeature per mask. Each feature's `properties` carry the mask's raster `value`\nand, when the model reports one, its confidence `score`, so a single request\nyields both geometry and confidence:\n\n```json\n{\"type\": \"Feature\", \"geometry\": {\"type\": \"Polygon\", \"coordinates\": [...]}, \"properties\": {\"value\": 1, \"score\": 0.887}}\n```\n\n## Caching\n\nThe API automatically caches models and image encodings for better performance:\n\n- **Model cache**: Models are loaded once and reused across requests. Use `DELETE /models` to free GPU memory.\n- **Image cache**: When the same image is sent multiple times (e.g., with different prompts), the expensive image encoding step is skipped. This makes subsequent requests significantly faster.\n\nExample timing with a 13 MB GeoTIFF:\n\n| Request | Description | Time |\n|---------|-------------|------|\n| 1st | Model load + image encoding | ~7s |\n| 2nd | Same image, different prompt | ~0.4s |\n| 3rd | Same image, another prompt | ~0.2s |\n\n## Python Client Example\n\n```python\nimport requests\n\nurl = \"http://localhost:8000/segment/text\"\n\n# Get GeoJSON mask polygons\nwith open(\"image.tif\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.tif\", f, \"image/tiff\")},\n        data={\"prompt\": \"building\", \"output_format\": \"geojson\"},\n    )\n\ngeojson = response.json()\nprint(f\"Found {len(geojson['features'])} features\")\n```\n\n```python\n# Get bounding boxes in pixel coordinates (suitable for non-georeferenced images)\nwith open(\"image.jpg\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.jpg\", f, \"image/jpeg\")},\n        data={\"prompt\": \"car\", \"output_format\": \"json\"},\n    )\n\nresult = response.json()\nfor det in result[\"detections\"]:\n    print(f\"Object {det['id']}: bbox={det['bbox']}, score={det['score']:.3f}\")\n```\n\n## API Reference\n\n::: samgeo.api\n","isInternal":false,"tokens":2967,"sizeBytes":9840},{"name":"SKILL.md","path":"agent-harness/cli_anything/samgeo/skills/SKILL.md","rawUrl":"https://raw.githubusercontent.com/opengeos/segment-geospatial/HEAD/agent-harness/cli_anything/samgeo/skills/SKILL.md","title":"cli-anything-samgeo","category":"anthropic-skill","format":"markdown","content":"---\nname: \"cli-anything-samgeo\"\ndescription: \"CLI harness for segment-geospatial — segment satellite/aerial imagery with SAM models from the command line\"\n---\n\n# cli-anything-samgeo\n\nSegment geospatial imagery (satellite, aerial, drone) using Meta AI's Segment\nAnything Model (SAM) family from the command line. Supports SAM v1, SAM 2,\nSAM 3, FastSAM, HQ-SAM, and LangSAM (text-based).\n\n## Installation\n\nRequires Python >= 3.10.\n\n```bash\npip install segment-geospatial[all]\ncd agent-harness && pip install -e .\n```\n\n## Syntax\n\n```\ncli-anything-samgeo [--json] [--project PATH] COMMAND [ARGS...]\n```\n\nGlobal flags:\n- `--json` — Machine-readable JSON output (use this for agent consumption)\n- `--project PATH` — Path to project JSON file (required for project-scoped commands)\n\n## Command Groups\n\n### project — Project management\n```bash\ncli-anything-samgeo project new -n NAME -o PATH [-s SOURCE] [-t MODEL_TYPE] [-m MODEL_ID]\ncli-anything-samgeo --project PATH project info\ncli-anything-samgeo --project PATH project set-source IMAGE_PATH\ncli-anything-samgeo --project PATH project history [-l LIMIT]\n```\n\n### model — Model management\n```bash\ncli-anything-samgeo model list [-t TYPE]\ncli-anything-samgeo model info MODEL_TYPE [-m MODEL_ID]\ncli-anything-samgeo model check MODEL_TYPE\n```\n\nModel types: `sam`, `sam2`, `sam3`, `fast_sam`, `hq_sam`, `text_sam`\n\n### segment — Segmentation operations\n```bash\ncli-anything-samgeo --project PATH segment automatic -o OUTPUT [--min-size N] [--max-size N]\ncli-anything-samgeo --project PATH segment points -o OUTPUT -c \"x1,y1;x2,y2\" -l \"1,0\"\ncli-anything-samgeo --project PATH segment boxes -o OUTPUT -b \"x1,y1,x2,y2\"\ncli-anything-samgeo --project PATH segment text -o OUTPUT -t \"buildings\"\n```\n\n### data — Data operations\n```bash\ncli-anything-samgeo data info RASTER_PATH\ncli-anything-samgeo data download-tiles -o OUTPUT -b \"west,south,east,north\" [-z ZOOM] [-s SOURCE]\ncli-anything-samgeo data reproject INPUT OUTPUT [--crs EPSG:CODE]\ncli-anything-samgeo data split INPUT OUT_DIR [--tile-size N] [--overlap N]\ncli-anything-samgeo data basemaps [--all]\n```\n\n### vector — Vector operations\n```bash\ncli-anything-samgeo vector convert RASTER_MASK OUTPUT [--simplify TOLERANCE]\ncli-anything-samgeo vector info VECTOR_PATH\ncli-anything-samgeo vector filter INPUT OUTPUT [--min-area N] [--max-area N]\n```\n\n### export — Export operations\n```bash\ncli-anything-samgeo --project PATH export render OUTPUT [-f FORMAT] [--overwrite]\ncli-anything-samgeo export formats\n```\n\nFormats: `geotiff`, `cog`, `gpkg`, `shp`, `geojson`, `png`\n\n### session — Session management\n```bash\ncli-anything-samgeo --project PATH session status\ncli-anything-samgeo --project PATH session history [-l LIMIT]\n```\n\n## Example Workflows\n\n### Satellite image segmentation pipeline\n```bash\n# Download tiles\ncli-anything-samgeo --json data download-tiles -o image.tif -b \"-122.42,37.77,-122.40,37.79\" -z 17\n\n# Create project\ncli-anything-samgeo --json project new -n urban-seg -o project.json -s image.tif -t sam2\n\n# Run automatic segmentation\ncli-anything-samgeo --json --project project.json segment automatic -o masks.tif\n\n# Convert to GeoPackage\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg --simplify 1.0\n\n# Export as GeoJSON\ncli-anything-samgeo --json --project project.json export render output.geojson -f geojson --overwrite\n```\n\n### Text-based segmentation\n```bash\ncli-anything-samgeo --json project new -n text-seg -o proj.json -s image.tif -t text_sam\ncli-anything-samgeo --json --project proj.json segment text -o masks.tif -t \"buildings\"\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg\n```\n\n## Agent Guidance\n\n- Always use `--json` for machine-readable output\n- Create a project first before running segmentation commands\n- The `--project` flag must come before the command group\n- Check model availability with `model check TYPE` before segmenting\n- Use `data info` to inspect rasters before processing\n- Export formats are auto-detected from file extension in `vector convert`\n- For large images, use `--batch` with `segment automatic`\n","frontmatter":{"name":"cli-anything-samgeo","description":"CLI harness for segment-geospatial — segment satellite/aerial imagery with SAM models from the command line"},"isInternal":false,"tokens":1104,"sizeBytes":4115}],"systemPromptSnippet":"<yakaai_skills repo=\"opengeos/segment-geospatial\">\n<!-- File: docs/api.md (Tokens: ~2967 | Category: project-spec) -->\n# REST API\n\nsegment-geospatial includes a built-in REST API powered by [FastAPI](https://fastapi.tiangolo.com/) that allows you to run image segmentation over HTTP. This is useful for integrating segmentation into web applications, pipelines, and non-Python clients.\n\n## Installation\n\nInstall the API dependencies with the `api` extra:\n\n```bash\npip install \"segment-geospatial[api]\"\n```\n\nTo also install a specific SAM model backend, combine extras:\n\n```bash\npip install \"segment-geospatial[api,samgeo3]\"\n```\n\n## Starting the Server\n\nUse the `samgeo-api` command:\n\n```bash\nsamgeo-api\n```\n\nOptions:\n\n```bash\nsamgeo-api --host 0.0.0.0 --port 8000        # Custom host/port\nsamgeo-api --preload sam2:sam2-hiera-large     # Preload a model at startup\nsamgeo-api --reload                            # Auto-reload for development\n```\n\nAlternatively, use `uvicorn` directly:\n\n```bash\nuvicorn samgeo.api:app --host 0.0.0.0 --port 8000\n```\n\nOnce running, interactive API docs (Swagger UI) are available at [http://localhost:8000/docs](http://localhost:8000/docs).\n\n## Endpoints\n\n### Health Check\n\n```\nGET /health\n```\n\nReturns the server status and version.\n\n```bash\ncurl http://localhost:8000/health\n```\n\n```json\n{\"status\": \"ok\", \"version\": \"1.2.3\"}\n```\n\n### List Models\n\n```\nGET /models\n```\n\nReturns available model versions/IDs and which models are currently loaded in memory.\n\n```bash\ncurl http://localhost:8000/models\n```\n\n### Clear Models\n\n```\nDELETE /models\n```\n\nClears the model cache and frees GPU memory.\n\n```bash\ncurl -X DELETE http://localhost:8000/models\n```\n\n### Automatic Segmentation\n\n```\nPOST /segment/automatic\n```\n\nRuns automatic mask generation on an uploaded image. Supports SAM, SAM2, and SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam2` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `sam2-hiera-large`, `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `foreground` | bool | `true` | Extract foreground objects only |\n| `unique` | bool | `true` | Assign unique ID to each object |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n| `points_per_side` | int | `32` | Points sampled per side (SAM/SAM2) |\n| `pred_iou_thresh` | float | `0.8` | IoU threshold for filtering |\n| `stability_score_thresh` | float | `0.95` | Stability score threshold |\n\n**Example:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/automatic \\\n  -F \"file=@image.tif\" \\\n  -F \"model_version=sam2\" \\\n  -F \"output_format=geojson\"\n```\n\n### Prompt-based Segmentation\n\n```\nPOST /segment/predict\n```\n\nRuns segmentation with point or bounding box prompts. Supports SAM, SAM2, and SAM3.\n\nFor SAM3 with bounding box prompts, the model finds **all similar objects** in the image (not just the object inside the box). Point prompts with SAM3 segment the specific object at the point location.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `model_version` | string | `sam3` | One of `sam`, `sam2`, `sam3` |\n| `model_id` | string | auto | Model identifier (e.g., `facebook/sam3.1`) |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `point_coords` | string | none | JSON array of `[[x, y], ...]` |\n| `point_labels` | string | none | JSON array of `[1, 0, ...]` (1=foreground, 0=background) |\n| `boxes` | string | none | JSON array of `[[xmin, ymin, xmax, ymax], ...]` |\n| `point_crs` | string | none | CRS string (e.g., `EPSG:4326`) for point/box coordinates |\n| `multimask_output` | bool | `false` | Return multiple masks per prompt |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example with point prompts:**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"point_coords=[[100, 200]]\" \\\n  -F \"point_labels=[1]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with box prompts (finds all similar objects):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.jpg\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 12,\n  \"detections\": [\n    {\"id\": 1, \"value\": 1, \"bbox\": [50, 80, 200, 250], \"width\": 150, \"height\": 170},\n    {\"id\": 2, \"value\": 2, \"bbox\": [310, 45, 480, 210], \"width\": 170, \"height\": 165}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/predict \\\n  -F \"file=@image.tif\" \\\n  -F \"boxes=[[10, 20, 300, 400]]\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 12,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"value\": 1, \"bbox_pixel\": [50.0, 80.0, 200.0, 250.0]}\n    }\n  ]\n}\n```\n\n### Text-prompt Segmentation\n\n```\nPOST /segment/text\n```\n\nRuns text-prompt segmentation using SAM3.\n\n**Parameters (multipart form):**\n\n| Parameter | Type | Default | Description |\n|-----------|------|---------|-------------|\n| `file` | file | required | Image file (TIFF, PNG, JPEG) |\n| `prompt` | string | required | Text description (e.g., `building`, `tree`) |\n| `model_id` | string | auto | SAM3 model identifier (`facebook/sam3` or `facebook/sam3.1`) |\n| `backend` | string | `meta` | One of `meta`, `transformers`; SAM 3.1 uses `meta` |\n| `output_format` | string | `geojson` | One of `geojson`, `geotiff`, `png`, `json`, `detections` |\n| `confidence_threshold` | float | `0.5` | Detection confidence threshold |\n| `min_size` | int | `0` | Minimum mask size in pixels |\n| `max_size` | int | none | Maximum mask size in pixels |\n\n**Example (GeoJSON mask polygons):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=geojson\"\n```\n\n**Example with JSON output (pixel-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.jpg\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=json\"\n```\n\n```json\n{\n  \"image_width\": 2647,\n  \"image_height\": 1464,\n  \"num_detections\": 46,\n  \"detections\": [\n    {\"id\": 1, \"bbox\": [2506, 134, 2653, 324], \"width\": 147, \"height\": 190, \"score\": 0.887},\n    {\"id\": 2, \"bbox\": [1200, 450, 1380, 620], \"width\": 180, \"height\": 170, \"score\": 0.862}\n  ]\n}\n```\n\n**Example with detections output (geographic-coordinate bounding boxes):**\n\n```bash\ncurl -X POST http://localhost:8000/segment/text \\\n  -F \"file=@image.tif\" \\\n  -F \"prompt=building\" \\\n  -F \"output_format=detections\"\n```\n\n```json\n{\n  \"type\": \"FeatureCollection\",\n  \"crs\": \"EPSG:3857\",\n  \"num_detections\": 46,\n  \"features\": [\n    {\n      \"type\": \"Feature\",\n      \"geometry\": {\n        \"type\": \"Polygon\",\n        \"coordinates\": [[[-13609328.39, 4561446.23], [-13609284.55, 4561446.23], [-13609284.55, 4561389.77], [-13609328.39, 4561389.77], [-13609328.39, 4561446.23]]]\n      },\n      \"properties\": {\"id\": 1, \"score\": 0.887, \"bbox_pixel\": [2506.47, 134.43, 2653.27, 323.52]}\n    }\n  ]\n}\n```\n\n## GeoJSON output\n\nWith `output_format=geojson`, every segmentation endpoint returns one polygon\nfeature per mask. Each feature's `properties` carry the mask's raster `value`\nand, when the model reports one, its confidence `score`, so a single request\nyields both geometry and confidence:\n\n```json\n{\"type\": \"Feature\", \"geometry\": {\"type\": \"Polygon\", \"coordinates\": [...]}, \"properties\": {\"value\": 1, \"score\": 0.887}}\n```\n\n## Caching\n\nThe API automatically caches models and image encodings for better performance:\n\n- **Model cache**: Models are loaded once and reused across requests. Use `DELETE /models` to free GPU memory.\n- **Image cache**: When the same image is sent multiple times (e.g., with different prompts), the expensive image encoding step is skipped. This makes subsequent requests significantly faster.\n\nExample timing with a 13 MB GeoTIFF:\n\n| Request | Description | Time |\n|---------|-------------|------|\n| 1st | Model load + image encoding | ~7s |\n| 2nd | Same image, different prompt | ~0.4s |\n| 3rd | Same image, another prompt | ~0.2s |\n\n## Python Client Example\n\n```python\nimport requests\n\nurl = \"http://localhost:8000/segment/text\"\n\n# Get GeoJSON mask polygons\nwith open(\"image.tif\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.tif\", f, \"image/tiff\")},\n        data={\"prompt\": \"building\", \"output_format\": \"geojson\"},\n    )\n\ngeojson = response.json()\nprint(f\"Found {len(geojson['features'])} features\")\n```\n\n```python\n# Get bounding boxes in pixel coordinates (suitable for non-georeferenced images)\nwith open(\"image.jpg\", \"rb\") as f:\n    response = requests.post(\n        url,\n        files={\"file\": (\"image.jpg\", f, \"image/jpeg\")},\n        data={\"prompt\": \"car\", \"output_format\": \"json\"},\n    )\n\nresult = response.json()\nfor det in result[\"detections\"]:\n    print(f\"Object {det['id']}: bbox={det['bbox']}, score={det['score']:.3f}\")\n```\n\n## API Reference\n\n::: samgeo.api\n\n<!-- File: agent-harness/cli_anything/samgeo/skills/SKILL.md (Tokens: ~1104 | Category: anthropic-skill) -->\n---\nname: \"cli-anything-samgeo\"\ndescription: \"CLI harness for segment-geospatial — segment satellite/aerial imagery with SAM models from the command line\"\n---\n\n# cli-anything-samgeo\n\nSegment geospatial imagery (satellite, aerial, drone) using Meta AI's Segment\nAnything Model (SAM) family from the command line. Supports SAM v1, SAM 2,\nSAM 3, FastSAM, HQ-SAM, and LangSAM (text-based).\n\n## Installation\n\nRequires Python >= 3.10.\n\n```bash\npip install segment-geospatial[all]\ncd agent-harness && pip install -e .\n```\n\n## Syntax\n\n```\ncli-anything-samgeo [--json] [--project PATH] COMMAND [ARGS...]\n```\n\nGlobal flags:\n- `--json` — Machine-readable JSON output (use this for agent consumption)\n- `--project PATH` — Path to project JSON file (required for project-scoped commands)\n\n## Command Groups\n\n### project — Project management\n```bash\ncli-anything-samgeo project new -n NAME -o PATH [-s SOURCE] [-t MODEL_TYPE] [-m MODEL_ID]\ncli-anything-samgeo --project PATH project info\ncli-anything-samgeo --project PATH project set-source IMAGE_PATH\ncli-anything-samgeo --project PATH project history [-l LIMIT]\n```\n\n### model — Model management\n```bash\ncli-anything-samgeo model list [-t TYPE]\ncli-anything-samgeo model info MODEL_TYPE [-m MODEL_ID]\ncli-anything-samgeo model check MODEL_TYPE\n```\n\nModel types: `sam`, `sam2`, `sam3`, `fast_sam`, `hq_sam`, `text_sam`\n\n### segment — Segmentation operations\n```bash\ncli-anything-samgeo --project PATH segment automatic -o OUTPUT [--min-size N] [--max-size N]\ncli-anything-samgeo --project PATH segment points -o OUTPUT -c \"x1,y1;x2,y2\" -l \"1,0\"\ncli-anything-samgeo --project PATH segment boxes -o OUTPUT -b \"x1,y1,x2,y2\"\ncli-anything-samgeo --project PATH segment text -o OUTPUT -t \"buildings\"\n```\n\n### data — Data operations\n```bash\ncli-anything-samgeo data info RASTER_PATH\ncli-anything-samgeo data download-tiles -o OUTPUT -b \"west,south,east,north\" [-z ZOOM] [-s SOURCE]\ncli-anything-samgeo data reproject INPUT OUTPUT [--crs EPSG:CODE]\ncli-anything-samgeo data split INPUT OUT_DIR [--tile-size N] [--overlap N]\ncli-anything-samgeo data basemaps [--all]\n```\n\n### vector — Vector operations\n```bash\ncli-anything-samgeo vector convert RASTER_MASK OUTPUT [--simplify TOLERANCE]\ncli-anything-samgeo vector info VECTOR_PATH\ncli-anything-samgeo vector filter INPUT OUTPUT [--min-area N] [--max-area N]\n```\n\n### export — Export operations\n```bash\ncli-anything-samgeo --project PATH export render OUTPUT [-f FORMAT] [--overwrite]\ncli-anything-samgeo export formats\n```\n\nFormats: `geotiff`, `cog`, `gpkg`, `shp`, `geojson`, `png`\n\n### session — Session management\n```bash\ncli-anything-samgeo --project PATH session status\ncli-anything-samgeo --project PATH session history [-l LIMIT]\n```\n\n## Example Workflows\n\n### Satellite image segmentation pipeline\n```bash\n# Download tiles\ncli-anything-samgeo --json data download-tiles -o image.tif -b \"-122.42,37.77,-122.40,37.79\" -z 17\n\n# Create project\ncli-anything-samgeo --json project new -n urban-seg -o project.json -s image.tif -t sam2\n\n# Run automatic segmentation\ncli-anything-samgeo --json --project project.json segment automatic -o masks.tif\n\n# Convert to GeoPackage\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg --simplify 1.0\n\n# Export as GeoJSON\ncli-anything-samgeo --json --project project.json export render output.geojson -f geojson --overwrite\n```\n\n### Text-based segmentation\n```bash\ncli-anything-samgeo --json project new -n text-seg -o proj.json -s image.tif -t text_sam\ncli-anything-samgeo --json --project proj.json segment text -o masks.tif -t \"buildings\"\ncli-anything-samgeo --json vector convert masks.tif buildings.gpkg\n```\n\n## Agent Guidance\n\n- Always use `--json` for machine-readable output\n- Create a project first before running segmentation commands\n- The `--project` flag must come before the command group\n- Check model availability with `model check TYPE` before segmenting\n- Use `data info` to inspect rasters before processing\n- Export formats are auto-detected from file extension in `vector convert`\n- For large images, use `--batch` with `segment automatic`\n</yakaai_skills>"}