Quickstart
From nothing to an agent that answers, in ten minutes, in TypeScript, Ruby or Python.
From nothing to an agent that answers, in ten minutes. You install one command, create a project in the language you like, read what the model will see, talk to the agent, and run its first test. Everything runs in your org's sandbox on Pinecall Cloud: a space of your own to try things, where nothing reaches a real caller.
Before you start#
- Node 24 or later. The
pinecallcommand is a Node program, whatever language your agent is written in.node --versiontells you which you have. - A Pinecall account. Sign up at cloud.pinecall.io if you do not have one; the quickstart signs you in from the terminal.
- For a Python agent, Python 3.11 or later and uv. For a Ruby agent, Ruby 3.2 or later and Bundler. A TypeScript agent needs nothing more than Node.
Install the CLI#
npm i -g pinecall
pinecall --version
0.9.45
One command, installed once per machine. It serves an agent in any of the three languages.
Create a project#
Pick a language. The project is the same shape in all three: the agent's class in one folder, its tests in another.
pinecall new front-desk
cd front-desk
npm install
pinecall new front-desk --python
cd front-desk
uv sync
pinecall new front-desk --ruby
cd front-desk
bundle install
▸ front-desk · a TypeScript agent
cd front-desk
npm install
pinecall link sign in, pick the org: its key goes to .env
pinecall chat talk to it here
pinecall test its goldens, against a real model
pinecall start answer calls
front-desk is the agent's name on Pinecall and the folder's name. A name is one org's on a
gateway: if pinecall chat later answers agent front-desk belongs to another org, somebody took
it first — create the project again with a name of your own (pinecall new ana-front-desk). The
lines under it are the steps that follow. npm install (or uv sync, bundle install) installs the SDK the agent is
written with; the project depends on nothing else.
Inside the folder:
agents/front-desk/agent.tsx the class: its state, its one tool, its prompt
test/front-desk/agent.test.ts a unit test: the class as software, no network
test/front-desk/goldens/ a golden: a conversation the model must hold
package.json · tsconfig.json the toolchain, with @pinecall/agents as the one dependency
agents/front-desk/agent.py the class: its state, its one tool
agents/front-desk/views/front-desk.jinja its prompt's view, a template beside the class
test/front-desk/test_agent.py a unit test: the class as software, no network
test/front-desk/goldens/ a golden: a conversation the model must hold
pyproject.toml the toolchain, with pinecall as the one dependency
agents/front-desk/agent.rb the class: its state, its one tool
agents/front-desk/views/front-desk.erb its prompt's view, a template beside the class
test/front-desk/agent_test.rb a unit test: the class as software, no network
test/front-desk/goldens/ a golden: a conversation the model must hold
Gemfile · Rakefile the toolchain, with the pinecall gem as the one dependency
The agent pinecall new writes is a front desk: it answers from the documents it is given and,
for anything else, takes a message — the caller's name and what the call is about — with its one
tool, takeMessage (take_message in Python and Ruby).
Sign in#
pinecall link
▸ front-desk · PINECALL_KEY written to .env
It opens the browser so you can sign in, asks which of your orgs this project belongs to, and
writes your key to ./.env. The project's .gitignore already keeps .env out of git. Every
pinecall command run in this folder reads the key from there.
To see which org and gateway the CLI is using at any time:
pinecall whoami
gateway https://cloud.pinecall.io · key from .env · sandbox
org front-desk · key k_4f2a1d9c66b30e17 · sandbox · ana-macbook · production: yes
The first line is where commands go and which key they use. sandbox means nothing you do here
reaches a real caller; --prod on a command acts in production instead.
Read what the model reads#
pinecall prompt
── identity (static) ──
You answer the phone for the business. Short sentences: everything you say is read aloud. …
<rules>
- Invent nothing: if it did not come from a tool or from the knowledge, do not say it.
- One question per turn, and wait for the answer.
…
</rules>
── knowledge (static) ──
── tools (static) ──
<tools>
- takeMessage: Writes down the caller's message. Call it as soon as the caller has said their name …
</tools>
── history ──
── view (dynamic) ──
Greet the caller. A question the documents answer, answer; otherwise ask for their name and what the call is about.
── tools ── stage: ask
● takeMessage ask
This is the exact text the model reads when a call opens, with no key and no network. It has four blocks: identity is your class's docstring plus rules Pinecall adds for every agent; knowledge is what the agent knows by heart (empty until you write it, in step 7); tools is every tool with its docstring; view is what your class says to do in this turn. Under the blocks, the stage the agent is in and the tools the model may call now. Change the class and run it again.
Talk to it#
pinecall chat
‹ Hi, I'm Ana Lopez. Please tell the manager my last order arrived broken.
→ takeMessage({"name":"***","about":"last order arrived broken"})
› Got it, Ana. Your message has reached the team. Goodbye!
‹ is you, typing. → is a tool the model called, with its arguments: the name shows as ***
because the class marked it as personal data, which is masked in the log. › is the agent's
answer. The agent runs on your machine, so a breakpoint in takeMessage stops there. Ctrl-D hangs
up.
Run its first test#
pinecall test
front-desk · 1 golden · the app's own model
✓ takes-the-message llm_node_ttft 380ms
1/1 · 0 judge calls · $0.0027 · 2s
A golden is a conversation written down, with what must be true at the end. This one says: a
caller leaves a message, and the agent must call takeMessage. pinecall test plays it against a
real model and checks the result. ✓ is a pass; llm_node_ttft is how long the model took to
start answering; the last line is the score, the model calls it cost, and the time. Add one
golden per behaviour you care about, in test/front-desk/goldens/.
The unit test runs with no network and no model: npm test, uv run pytest or bundle exec rake.
Give it documents#
mkdir -p docs/front-desk
printf '# Refunds\n\nA refund reaches the card it was paid with within ten working days.\n' > docs/front-desk/refunds.md
pinecall docs push
pinecall docs attach front-desk
front-desk · 1 file · 1 chunk · 212 ms
front-desk · front-desk attached · your corner v2
docs push uploads the folder as a knowledge base named after the agent; docs attach tells the
agent to search it on every turn. Run pinecall chat again and ask how long a refund takes: the
answer comes from your file, and nothing in your code changed.
Its voice, and the rest of its settings#
pinecall voices --language en # the voices, with their ids
pinecall agent set --voice <id>
pinecall agent # every setting: voice, models, language, greeting…
The voice, the models, the language and what it knows by heart are settings of the agent, not
code: changing one needs no deploy. pinecall console opens the same settings in the browser,
with every call the agent has had.
Answer calls#
pinecall start
front-desk · front-desk · sandbox · connected to https://cloud.pinecall.io · key from .env · tools 1
console https://cloud.pinecall.io/sandbox/a/front-desk
doors web
This is the process that answers: on your laptop now, on a server later. It holds the agent until
Ctrl-C and prints every call as it happens. The console line is where to see the agent in the
browser and talk to it by voice; doors is how callers reach it, the web for now, a phone number
once you point one at it.
To ship it, pinecall deploy uploads a TypeScript project and Pinecall runs it for you; a Python or
Ruby agent runs on a server of yours with pinecall start --prod.