Integration Guide | VectorGOLF.ai — Partner API & Import Token System

Developer Integration Guide

Connect Your App to
VectorGOLF.ai

Send scorecard and shot-level data from any golf app directly into a golfer's VectorGOLF.ai account. One endpoint, one token — unlock Strokes Gained, proximity analytics, and pro-grade insights.

Partner brief (Tangent & similar): golfer connection journey — when to open Vector sign-in, how import tokens work with in-app Post to Vector, and recommended URLs — is documented for your team at docs/integrations/tangent-vector-connect-golfer-journey.md (GitHub).

How It Works

1

Golfer Creates Token

On the VectorGOLF.ai dashboard, under Player Profile → API Access

2

Golfer Shares Token

Pastes the token into your app's "Connect to Vector" settings

3

Your App POSTs Data

After each round, POST the scorecard JSON to our API

4

Round in Vector

The round appears instantly in their Scorecard & Teebox Insights

No OAuth required. The import token system is designed for simplicity. A golfer generates a personal token, shares it with your app, and you use it as a Bearer token. That's it.

PRO at no charge for integration-sourced rounds. Authenticated POST of round JSON to the scorecards API with Authorization: Bearer ${VECTOR_IMPORT_TOKEN} (full import token from the dashboard; value always begins vg_imp_) qualifies the round; that golfer gets VECTOR GOLF ANALYTICS /// PRO at no subscription cost (Strokes Gained, teebox, proximity, AI plans). Partners get co-branding and enhanced AI analytics on JSON submissions. Offer runs 6–12 months while VectorGOLF.ai scales as a performance hub.


For Golfers

How to generate a token and connect your favorite app.

1

Sign in to your dashboard

Go to vectorgolf.ai/dashboard and sign in with your Google account.

2

Open Player Profile → API Access & Integrations

Scroll down past your profile info and billing. You'll see the API Access & Integrations section. Click to expand it.

3

Name your token and generate it

Type a label like "Tangent" or "TheGrint" so you know which app it's for. Click Generate Token.

4

Copy the token immediately

A yellow banner will show your full token starting with vg_imp_. Copy it now — it will not be shown again for security.

5

Paste into your partner app

Open your golf app (Tangent, TheGrint, Hole19, etc.) and find their "Connect to VectorGOLF" or "Import Token" setting. Paste the token there. After each round, the app will automatically send your scorecard to Vector.

Security note: Treat your import token like a password. Anyone who has it can add scorecards to your account. You can revoke a token at any time from the same API Access section — it's instant and permanent.

Token Management

5

Max active tokens

100/day

Requests per token

Instant

Revoke anytime


For Developers & Partners

Everything you need to build a "Send to Vector" feature in your app.

Endpoint

POST https://api.vectorgolf.ai/scorecards
Content-Type application/json
Authorization Bearer + one space + the golfer’s full import token (always starts with vg_imp_)
Success 201  { "success": true, "round_id": 123 }
Errors 401 invalid token  |  400 bad JSON  |  403 scope denied

How to set Authorization. The golfer copies one long string from Dashboard → Player Profile → API Access & Integrations. That entire string is the token—send it verbatim after Bearer (include the vg_imp_ prefix). Omitting the prefix or pasting only part of the string returns 401. In the cURL example below, that full string is stored in VECTOR_IMPORT_TOKEN.

JSON Body

{
  "course_name": "Wildhorse Golf Club",
  "course_id": 45,             // optional — Vector course ID
  "tee_id": 112,               // optional — Vector tee ID
  "played_at": "2026-04-08",
  "total_score": 82,
  "total_par": 72,
  "front_nine_score": 40,
  "back_nine_score": 42,
  "round_type": "course",       // "course" or "simulator"

  "holes": [
    {
      "hole_num": 1,
      "par": 4,
      "score": 5,
      "putts": 2,
      "gir": 0,
      "fairway_hit": 1
    },
    // ... holes 2–18
  ],

  "shots": [                      // shot-level data — highly recommended
    {
      "hole_num": 1, "shot_index": 1,
      "club": "Driver", "start_lie": "Tee",
      "distance_to_target_y": 405, "proximity_y": 140
    }
    // ... all shots for holes 1–18
  ]
}

Round Fields

Field Type Required Notes
course_name string Yes Full course name as displayed to the golfer
course_id number No VectorGOLF course ID for precise tee matching
tee_id number No VectorGOLF tee ID (slope/rating/yardage auto-fill)
played_at string Yes ISO date YYYY-MM-DD
total_score number Yes Gross strokes for the round
total_par number Yes Course par (typically 72)
front_nine_score number No Auto-computed from holes if omitted
back_nine_score number No Auto-computed from holes if omitted
round_type string No "course" (default) or "simulator"
holes array Yes 1–18 hole objects (see below)

Hole Fields

Field Type Notes
hole_num number 1–18
par number 3, 4, or 5
score number | null Strokes on this hole
putts number | null Number of putts
gir 0 | 1 | null Green in regulation (can be derived from score/putts/par)
fairway_hit 0 | 1 | null Par 4/5 tee shots only
fairway_miss "L" | "R" | null Direction of miss (when fairway_hit = 0)

Shot-Level Data Recommended

This is what makes the integration truly valuable.

If your app tracks GPS coordinates, club selection, or shot-by-shot data on the course, including shots[] in your payload unlocks the full power of VectorGOLF analytics:

Strokes Gained
vs Pro

Proximity
to Pin

Club Selection
Analytics

SG Breakdown
by Lie

Without shot data, the golfer still gets scorecard history and basic stats. With shot data, they get professional-grade analytics — Strokes Gained breakdowns, approach proximity trends, club distance tracking, and AI-powered improvement zones.

Each shot is an object in the shots[] array. The only required fields per shot are hole_num and shot_index — everything else can be null or omitted. Send whatever your app captures.

Example: shots with a few key fields

"shots": [
  {
    "hole_num": 1,
    "shot_index": 1,
    "club": "Driver",
    "start_lie": "Tee",
    "end_lie": "Fairway",
    "distance_to_target_y": 405,
    "distance_traveled_y": 265,
    "proximity_y": 140,
    "strokes_gained_pro": 0.12
  },
  {
    "hole_num": 1,
    "shot_index": 2,
    "club": "8 Iron",
    "start_lie": "Fairway",
    "end_lie": "Green",
    "distance_to_target_y": 140,
    "proximity_y": 18,
    "strokes_gained_pro": 0.35
  },
  // ... all shots for holes 1–18
]

Full Shot Field Reference

Send any combination of these fields per shot. The more you include, the richer the analytics.

Field Type Notes
hole_num number Required — 1–18
shot_index number Required — Shot order within the hole (1, 2, 3…)
club string | null Club used (e.g. "Driver", "7 Iron", "56° Wedge")
club_type string | null Category: "Driver", "Wood", "Iron", "Wedge", "Putter"
club_brand string | null Manufacturer (e.g. "Titleist", "Callaway")
club_model string | null Specific model (e.g. "TSR3", "Paradym")
start_lie string | null "Tee", "Fairway", "Rough", "Sand", "Green", etc.
end_lie string | null Lie after the shot
distance_to_target_y number | null Distance to target before the shot (yards)
distance_traveled_y number | null How far the ball traveled (yards)
proximity_y number | null Remaining distance to target after the shot (yards)
strokes_gained_pro number | null SG vs PGA Tour baseline for this shot
quality string | null Shot quality rating (app-defined)
shot_quality string | null Alternate quality field
category string | null Shot category (app-defined)
shape string | null Shot shape: "Draw", "Fade", "Straight", etc.
trajectory string | null Ball flight trajectory: "High", "Mid", "Low"
degrees_offline number | null Degrees offline from target line
penalties number | null Penalty strokes on this shot
committed number | null Whether golfer committed to the shot (app-defined)
wind_bearing number | null Wind direction in degrees
wind_strength number | null Wind speed
elevation_ft number | null Elevation change in feet
hole_par number | null Par for this hole (redundant with holes[] but accepted)
hole_score number | null Final score for this hole
hole_length_y number | null Hole length in yards (from tee played)
hole_putts number | null Putts on this hole
hole_putts_ft number | null Total putt distance in feet for this hole
hole_handicap number | null Handicap stroke index for this hole
rating number | null Course rating from tee played
slope number | null Slope rating from tee played
tee_name string | null Tee name (e.g. "Blue", "White")
tee_color string | null Tee color
tee_number number | null Tee ordinal (1 = longest, etc.)
golfer string | null Golfer name (from export)
date_played string | null Date (redundant with round played_at but accepted)
course string | null Course name per shot row
round_type string | null Round type per shot row
round_par number | null Course par per shot row
round_score number | null Total round score per shot row
coach_tags string | null Coach-assigned tags (comma-separated)

High-value fields for most GPS apps: club, start_lie, end_lie, distance_to_target_y, distance_traveled_y, proximity_y, and strokes_gained_pro. If you can only send a few fields beyond hole_num / shot_index, prioritize these — they power the majority of Vector's advanced analytics.


Quick Test with cURL

Set an environment variable (example: VECTOR_IMPORT_TOKEN) to the full token (starts with vg_imp_), then run curl:

# Paste the complete token from the golfer's dashboard (must include vg_imp_)
export VECTOR_IMPORT_TOKEN='vg_imp_your_complete_token_from_dashboard'

curl -X POST https://api.vectorgolf.ai/scorecards \
  -H "Authorization: Bearer ${VECTOR_IMPORT_TOKEN}" \
  -H "Content-Type: application/json" \
  -d '{
    "course_name": "Test Golf Club",
    "played_at": "2026-04-08",
    "total_score": 82,
    "total_par": 72,
    "round_type": "course",
    "holes": [
      {"hole_num":1,"par":4,"score":5,"putts":2,"gir":0,"fairway_hit":1},
      {"hole_num":2,"par":3,"score":3,"putts":1,"gir":1},
      {"hole_num":3,"par":5,"score":6,"putts":2,"gir":0,"fairway_hit":1},
      {"hole_num":4,"par":4,"score":4,"putts":2,"gir":1,"fairway_hit":1},
      {"hole_num":5,"par":4,"score":5,"putts":2,"gir":0,"fairway_hit":0},
      {"hole_num":6,"par":3,"score":4,"putts":2,"gir":0},
      {"hole_num":7,"par":4,"score":4,"putts":1,"gir":1,"fairway_hit":1},
      {"hole_num":8,"par":5,"score":5,"putts":2,"gir":1,"fairway_hit":1},
      {"hole_num":9,"par":4,"score":4,"putts":2,"gir":1,"fairway_hit":1},
      {"hole_num":10,"par":4,"score":5,"putts":2,"gir":0,"fairway_hit":0},
      {"hole_num":11,"par":3,"score":3,"putts":2,"gir":1},
      {"hole_num":12,"par":5,"score":6,"putts":2,"gir":0,"fairway_hit":1},
      {"hole_num":13,"par":4,"score":4,"putts":1,"gir":1,"fairway_hit":1},
      {"hole_num":14,"par":4,"score":5,"putts":2,"gir":0,"fairway_hit":0},
      {"hole_num":15,"par":3,"score":4,"putts":2,"gir":0},
      {"hole_num":16,"par":4,"score":4,"putts":2,"gir":1,"fairway_hit":1},
      {"hole_num":17,"par":5,"score":5,"putts":2,"gir":1,"fairway_hit":1},
      {"hole_num":18,"par":4,"score":5,"putts":2,"gir":0,"fairway_hit":0}
    ]
  }'

# Expected: 201 { "success": true, "round_id": ... }

Example: iOS (Swift)

Step-by-step for a Send to VectorGOLF flow in a native iOS app: Keychain storage for the import token, Codable models that match this guide’s JSON keys, URLSession POST, parsing round_id on 201, lie mapping, deduplication, and error UX (401 / 429 / 400).

Full Swift guide (copy-paste) — open for repository link

Complete step-by-step Swift (models, URLSession, round_id handling) lives in the repo Markdown — not a separate marketing page:

github.com/VectorLabs-ai/VectorGolf.ai/blob/main/docs/integrations/ios-send-to-vector.md

  • Store the golfer’s full import token (starts with vg_imp_) in the Keychain, not UserDefaults.
  • Send Authorization: Bearer <full token> — same value you would put in VECTOR_IMPORT_TOKEN for shell tests.
  • On 201, decode round_id for deep links and to avoid double-posting the same round.
  • Map your lie labels to the strings Vector expects (see shot field table above); include shots[] when you have club and distance data.

Error Handling

Status Meaning Action
201 Round created Show success. Use round_id to deep-link.
400 Invalid JSON / missing required fields Check your JSON payload structure.
401 Invalid or revoked token Ask user to check/regenerate their token on the VectorGOLF.ai dashboard.
403 Scope denied (import tokens are POST-only) Import tokens only allow creating scorecards, not reading.
429 Rate limit exceeded Max 100 requests per token per day. Resets at midnight UTC. Back off and retry tomorrow.
500 Server error Retry with backoff. Contact [email protected] if persistent.

Best Practices

Avoid Duplicates

Each POST creates a new round. Deduplicate on your side (e.g. track sent round_ids per user). Vector does not reject duplicate rounds.

Course Matching

If you know the Vector course_id and tee_id, include them for precise slope/rating auto-fill. Otherwise, just send course_name and Vector will fuzzy-match.

Send All 18 Holes

Always send 18 hole objects. If the golfer didn't finish, set score: null for unplayed holes. Partial rounds (9 holes) are supported — send holes 1–9 or 10–18.

Token Storage

Store the user's import token encrypted or in your app's secure credential store. Never log it or expose it in client-side code.

What the Golfer Gets

Every round you POST automatically unlocks these features in their VectorGOLF.ai dashboard:

With scorecard data (holes[])

Scorecard Insights

Round history, trends, GIR/FIR, putts per round

Teebox Insights

Net scoring analysis per tee, tee-fit scale

Improvement Zones

Strokes lost analysis, AI-generated drills

Round Recap Email

Automated email with hole-by-hole breakdown

+ With shot data (shots[]) — the real value

Strokes Gained vs Pro

Full SG breakdown: Tee, Approach, Short Game, Putting

Proximity Analytics

Distance to pin by club, lie, and distance band

Club Analytics

Avg distance, dispersion, and selection patterns per club

Detailed Round Recap

Shot-by-shot narrative with lie transitions and decisions


Ready to Integrate?

Add a "Send to VectorGOLF" button to your app. Include shot-level data and your users get Strokes Gained, proximity analytics, club selection trends, and AI-powered improvement — analytics that keep them coming back to both your app and Vector.

Custom integrations. Beyond the standard JSON POST and import-token flow, we can work with your product and engineering teams on approaches tailored to your organization—batch or backfill pipelines, alternative auth boundaries, staging reviews, or other constraints. Email [email protected] with a short summary of your environment and timeline.