Examples¶
Base URL examples assume Apache mounts GeoVault at /geovault on https://app.example. Direct process access uses http://127.0.0.1:8085 without the prefix.
All mutating and listing calls require a Central session cookie unless noted. Replace [SESSION] and [REDACTED] placeholders.
curl¶
Login through Central, then list datasets¶
# Obtain session via Central login UI or your platform login API, then:
export BASE='https://app.example/geovault'
export COOKIE='acugis_session=[SESSION]'
curl -sS -b "$COOKIE" "$BASE/datasets-summary" | jq .
curl -sS -b "$COOKIE" "$BASE/api/discovery" | jq .
Upload a new dataset version¶
curl -sS -b "$COOKIE" \
-F 'file=@./neighborhoods.geojson' \
-F 'message=initial load' \
"$BASE/datasets/neighborhoods/upload"
Import from HTTPS URL¶
curl -sS -b "$COOKIE" \
-H 'Content-Type: application/json' \
-d '{
"dataset_name": "parcels",
"url": "https://example.com/data/parcels.geojson",
"version_label": "initial URL import"
}' \
"$BASE/import-url"
URL imports require dataset_name and url; version_label is optional. These are JSON fields, not multipart fields.
Download a version¶
# Resolve version id from datasets versions, then:
curl -sS -b "$COOKIE" \
-OJ \
"$BASE/versions/123/download"
Filter → new version¶
curl -sS -b "$COOKIE" \
-H 'Content-Type: application/json' \
-d '{"layer":"neighborhoods","where":"TYPE = '\''park'\''"}' \
"$BASE/datasets/neighborhoods/versions/1/filter"
The response is 200 {"success":true,"new_version":2} (with the actual next version number).
GeoServer job poll¶
JavaScript (browser session)¶
Runs in the GeoVault UI origin so the session cookie is sent automatically:
const base = window.BASE_PATH || '';
async function listDatasets() {
const res = await fetch(`${base}/datasets-summary`, { credentials: 'same-origin' });
if (!res.ok) throw new Error(await res.text());
return res.json();
}
async function archiveDataset(name) {
const res = await fetch(`${base}/datasets/${encodeURIComponent(name)}/archive`, {
method: 'POST',
credentials: 'same-origin',
});
if (!res.ok) throw new Error(await res.text());
return res.json();
}
async function importURL() {
const res = await fetch(`${base}/import-url`, {
method: 'POST',
credentials: 'same-origin',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
dataset_name: 'parcels',
url: 'https://example.com/data/parcels.geojson',
version_label: 'initial URL import',
}),
});
if (!res.ok) throw new Error(await res.text());
return res.json();
}
listDatasets().then(console.log).catch(console.error);
Python¶
import requests
BASE = "https://app.example/geovault"
COOKIES = {"acugis_session": "[SESSION]"}
def datasets_summary():
r = requests.get(f"{BASE}/datasets-summary", cookies=COOKIES, timeout=60)
r.raise_for_status()
return r.json()
def download_version(version_id: int, dest: str):
with requests.get(
f"{BASE}/versions/{version_id}/download",
cookies=COOKIES,
stream=True,
timeout=300,
) as r:
r.raise_for_status()
with open(dest, "wb") as f:
for chunk in r.iter_content(1024 * 1024):
if chunk:
f.write(chunk)
def filter_version(dataset: str, version: int):
r = requests.post(
f"{BASE}/datasets/{dataset}/versions/{version}/filter",
cookies=COOKIES,
json={"layer": dataset, "where": "TYPE = 'park'"},
timeout=300,
)
r.raise_for_status()
return r.json()
print(datasets_summary())
CLI equivalent for many read workflows:
acugis login https://app.example
acugis datasets info neighborhoods
acugis datasets download neighborhoods --directory ./out
Go¶
package main
import (
"bytes"
"encoding/json"
"fmt"
"io"
"net/http"
"os"
)
func main() {
payload, _ := json.Marshal(map[string]any{"version_id": 123, "dataset": "elevation"})
req, _ := http.NewRequest(http.MethodPost, "https://app.example/geovault/versions/ignored/publish", bytes.NewReader(payload))
req.Header.Set("Content-Type", "application/json")
req.AddCookie(&http.Cookie{Name: "acugis_session", Value: os.Getenv("ACUGIS_SESSION")})
resp, err := http.DefaultClient.Do(req)
if err != nil {
panic(err)
}
defer resp.Body.Close()
body, _ := io.ReadAll(resp.Body)
fmt.Println(resp.Status, string(body))
}
PHP¶
<?php
$base = 'https://app.example/geovault';
$session = getenv('ACUGIS_SESSION');
$ch = curl_init($base . '/datasets-summary?type=vector&archived=include');
curl_setopt_array($ch, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
'Accept: application/json',
'Cookie: acugis_session=' . $session,
],
]);
$body = curl_exec($ch);
$status = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
echo $status, PHP_EOL, $body, PHP_EOL;
Common workflows¶
A. Register PostGIS table as dataset¶
- Create connection:
POST /api/connections - List tables:
GET /api/connections/{id}/tables - Register:
POST /api/datasets/register - Open UI
/datasets/{name}Edit Data tab or call/api/table/*
Requires metadata DB and service admin for connection routes.
B. Publish raster to QGIS¶
- Upload raster version
POST /versions/{id}/publishwithQGIS_PUBLISH_URLconfigured- List runtime projects:
GET /api/qgis-projects
C. Publish vector to GeoServer¶
- Ensure GeoServer connection exists (
/api/geoserver/connections) POST /api/geoserver/publishfor an existing version- Poll
GET /api/geoserver/jobs/{id}
Notes¶
- Use cookie auth. Bearer PAT authentication is not operational in GeoVault.
- Large imports honor
GEOVAULT_IMPORT_MAX_BYTES(default 500 MiB). - Exact multipart field names for upload may include PostGIS/GeoServer sidecar fields consumed by ingest helpers; inspect
web/upload.htmland matching handlers when embedding sidecars.