Documentation: 0.5.0 (source: v0.5.0).
# Your first read

> Install the SDK and read a real fleet out of the live game in about five minutes.

Markdown source of https://docs-v0-5-0.atlas-kit-docs.pages.dev/start-here/first-read/ — see https://docs-v0-5-0.atlas-kit-docs.pages.dev/ai/ for the full machine-readable surface.

By the end of this page you will have read a real fleet out of the live game.
No wallet, no keys, no setup beyond an install.

## Install

```bash
pnpm add @aephia/atlas-kit@0.5.0 @solana/kit
```

`@solana/kit` is a peer dependency: it provides the RPC client and the `Address`
type. Installing it yourself means you control its version.

## Read a fleet

```ts
import { createSolanaRpc, address } from '@solana/kit';
import { createSageClient } from '@aephia/atlas-kit';

const rpc = createSolanaRpc('https://testnet-rpc.z.ink');
const sage = createSageClient({ cluster: 'zink-ptr', rpc });

const profileAddress = address('J4r2s9QA2SHWf8zLPmvPhVphiK92h3rVmoXxcSM8M2vv');
const character = await sage.characters.forProfile(profileAddress);
const fleets = await character.fleets.all();

const fleet = fleets[0];
if (!fleet) throw new Error('That profile has no fleets.');

console.log(fleet.name); // "Ravager"
console.log(fleet.state); // { kind: 'docked', system: … }
```

That address is a real profile on the test realm. It should work as written.

In your own application that address is the thing you have to supply. If your
users arrive holding a wallet and nothing else, getting from one to the other is
a search rather than a calculation — nothing about a wallet predicts its
profile, so there is no offline answer. [You](/guides/identity/) covers how
that search works and what you have to bring to it; it is worth reading before
you design a sign-in flow.

## Try it here

You do not have to leave the page. Press Run and this executes against the live
test realm, in your browser. Change the address to read a different profile.

> **Runnable example — Read a fleet.** Walk from a profile to its character, then to the fleets that character owns. Run it in the browser at https://docs-v0-5-0.atlas-kit-docs.pages.dev/start-here/first-read/.

The documentation playground remains read-only: it uses only read capability
entries, with no wallet or signing surface. The SDK itself is non-custodial and
can execute transactions when you explicitly supply a write transport and
external Kit signers to a write call.

## What just happened

Four things, worth naming because the rest of the SDK works the same way.

**`createSageClient` did no network work.** It is synchronous and allocates a
context: a cache, an RPC binding, and the cluster's known addresses. Nothing is
fetched until you ask for something.

**`cluster: 'zink-ptr'` filled in the game.** The preset knows the program
address and the Game account, so you did not have to.

**`forProfile` returned a loaded object.** Not a handle you have to `load()`
first — the data is already there. Every read in this SDK works that way.

**`.fleets.all()` followed a relationship.** Going from a character to its
fleets is a separate read, so it is a separate `await`. Anything that costs a
network round trip is a method you call, not a property you touch.

:::game[Profiles, characters, and fleets]
A **profile** is a player's on-chain identity. A **character** is that
profile's presence inside SAGE specifically — the thing that owns fleets and
accrues progress. A **fleet** is a group of ships travelling together; ships
move as fleets, never individually.

One profile has one SAGE character, and a character can own many fleets.
:::

## Reading a bit more

Cargo is a relationship too:

```ts
const inventory = await fleet.inventory.get();
console.log(inventory.cargoHold.items[0]?.quantityRaw);
```

Quantities are `bigint`, not `number`. Game amounts routinely exceed what a
JavaScript number can hold exactly, and silently rounding someone's ore count
is worse than making you type `n`.

> **Runnable example — Read a fleet's cargo.** Follow a relationship one step further: from a fleet to what it is carrying. Run it in the browser at https://docs-v0-5-0.atlas-kit-docs.pages.dev/start-here/first-read/.

Both examples on this page share one client, so the second reuses what the
first already fetched rather than reading the same accounts again.

## If it did not work

**A network or CORS error** usually means the RPC endpoint rejected the request.
See [setting up your RPC](/start-here/rpc/).

**`MissingGameContextError`** means a cluster other than `zink-ptr` was used
without supplying a Game address. Use the preset unless you know you need
otherwise.

**An empty `fleets` array** is a valid answer: that profile currently has no
fleets. Try another address.

## Where to go next

[How the SDK thinks](/start-here/how-it-thinks/) explains caching, entry points,
and why reads are shaped the way they are.

If your users will arrive with a wallet rather than a profile address, read
[identity](/guides/identity/) first. Wallet-to-profile discovery is the one step
the SDK cannot answer by itself, and it shapes everything downstream of your
sign-in.
