Alpaca Paper Trading First Order in Python with alpaca-py
Before connecting a live trading strategy to a broker, you need to understand the API’s authentication model, order lifecycle, and error surfaces. This walkthrough shows the structure of a minimal alpaca-py session: connect to the paper endpoint, fetch account info, place a market order, and cancel it. All keys are read from environment variables and never stored anywhere. AlgoDrill never executes trades or holds credentials.
Regulatory firewall: AlgoDrill teaches the architecture of broker integration. This page and its script use Alpaca’s paper endpoint only. The script requires your own API keys, read from environment variables on your own machine. AlgoDrill never holds credentials, never proxies API calls, and never executes trades. Past backtest results do not predict future returns. Disclosure: AlgoDrill is unaffiliated with Alpaca Markets, Inc.
"""AlgoDrill — Alpaca paper account: connect, fetch account, place + cancel one order.
REGULATORY FIREWALL: AlgoDrill never executes trades, never holds broker
credentials, and never connects to a live account. This script is purely
architectural — it shows the code structure so you can run it yourself
against your own paper account.
Keys are read from environment variables. Never hard-code credentials.
Versions: alpaca-py 0.43.4 (run locally against your paper account)
Install: pip install alpaca-py
Setup (one-time):
1. Sign up at alpaca.markets (free)
2. Go to Paper Trading → click "View" on API Key
3. Copy Key ID and Secret Key
4. Export before running:
export ALPACA_PAPER_KEY="YOUR_KEY_ID_HERE"
export ALPACA_PAPER_SECRET="YOUR_SECRET_KEY_HERE"
Paper endpoint: https://paper-api.alpaca.markets (no real money)
Disclosure: AlgoDrill has no affiliation with Alpaca Markets, Inc.
"""
import os
from alpaca.trading.client import TradingClient
from alpaca.trading.requests import MarketOrderRequest
from alpaca.trading.enums import OrderSide, TimeInForce
KEY = os.environ["ALPACA_PAPER_KEY"] # never hard-code credentials
SECRET = os.environ["ALPACA_PAPER_SECRET"]
# ── 1. Connect to paper endpoint (paper=True routes to paper-api.alpaca.markets)
client = TradingClient(KEY, SECRET, paper=True)
# ── 2. Fetch account info ──────────────────────────────────────────────────────
account = client.get_account()
print("=== Alpaca Paper Account ===")
print(f"Status: {account.status}")
print(f"Equity: ${float(account.equity):,.2f}")
print(f"Buying power: ${float(account.buying_power):,.2f}")
print(f"Day trade count: {account.daytrade_count}")
print()
# ── 3. Place one paper market order (1 share of SPY) ──────────────────────────
order_req = MarketOrderRequest(
symbol="SPY",
qty=1,
side=OrderSide.BUY,
time_in_force=TimeInForce.DAY,
)
order = client.submit_order(order_request=order_req)
print("=== Order Placed ===")
print(f"Order ID: {order.id}")
print(f"Symbol: {order.symbol}")
print(f"Qty: {order.qty}")
print(f"Side: {order.side}")
print(f"Status: {order.status}")
print()
# ── 4. Cancel the paper order (clean up after the demonstration) ───────────────
client.cancel_order_by_id(order.id)
cancelled = client.get_order_by_id(order.id)
print("=== Order Cancelled ===")
print(f"Order ID: {cancelled.id}")
print(f"Status: {cancelled.status}")
print()
print("Architecture verified. No real money moved; paper account only.")Setup: Getting Paper API Keys
Alpaca paper trading is free, requires no minimum deposit, and provides $100,000 of simulated cash immediately. To get your keys:
- Create a free account at alpaca.markets.
- Navigate to Paper Trading in your dashboard.
- Click View next to API Key. Copy both the Key ID and the Secret Key immediately — the Secret is shown only once.
- Export the keys to your shell before running the script:
export ALPACA_PAPER_KEY="YOUR_KEY_ID_HERE"
export ALPACA_PAPER_SECRET="YOUR_SECRET_KEY_HERE"
python alpaca_paper_first_order.py
Never paste keys directly into source code. Never commit them to git. The os.environ["ALPACA_PAPER_KEY"] pattern raises a KeyError if the variable is not set — which is intentional: silent fallback to an empty string would let you run against live accidentally.
Line-by-Line Walkthrough
Lines 1–18: Docstring and imports
The docstring documents the regulatory firewall and setup steps directly in the script, so anyone who reads the file understands the architecture before running it. The imports come from alpaca.trading, the live/paper trading subpackage of alpaca-py. alpaca.data (not used here) is the separate market data subpackage.
Lines 20–21: Key loading
KEY = os.environ["ALPACA_PAPER_KEY"]
SECRET = os.environ["ALPACA_PAPER_SECRET"]
os.environ["KEY"] reads the value from the shell environment. If the variable is not set, Python raises KeyError: 'ALPACA_PAPER_KEY' before any network call is made. This is the correct pattern for credential loading: fail loudly at startup, never silently.
Lines 23–24: TradingClient with paper=True
client = TradingClient(KEY, SECRET, paper=True)
paper=True routes all requests to https://paper-api.alpaca.markets instead of https://api.alpaca.markets. Paper keys do not work on the live endpoint, and live keys do not work on the paper endpoint — the separation is enforced at the API level. If you ever switch to live, change only the keys and the paper flag. All other code remains identical.
Alpaca’s authentication model is a static API key in an Authorization header — there is no session management, no keepalive, and no daily reset. This is simpler than Interactive Brokers, which requires a Client Portal Gateway with 2FA and a ~6-minute session timeout. See Alpaca vs Interactive Brokers for a detailed comparison of the authentication burden and API architecture.
Lines 26–32: Fetching account info
account = client.get_account()
Returns an Account object. The key fields are:
- status:
ACTIVEmeans the account is funded and can trade. Other states includeACCOUNT_UPDATED(processing a change) andONBOARDING(new account setup). - equity: total portfolio value including cash and open positions at current market prices. Paper accounts start at $100,000.
- buying_power: for a Reg-T margin account, buying_power = 2x equity for day trades and 1x equity for overnight positions. For a cash account, buying_power = settled cash balance.
- daytrade_count: number of day trades in the last 5 business days. This field exists because of the legacy FINRA Pattern Day Trader rule. The PDT $25,000 equity floor was eliminated when FINRA Rule 4210 amendments took effect June 4, 2026 (FINRA Regulatory Notice 26-10), replaced by an intraday margin standard — but brokers may continue applying the old $25,000 policy through October 20, 2027, so check Alpaca’s current margin policy. Paper accounts are unaffected in practice.
Lines 34–43: Placing a paper market order
order_req = MarketOrderRequest(
symbol="SPY",
qty=1,
side=OrderSide.BUY,
time_in_force=TimeInForce.DAY,
)
order = client.submit_order(order_request=order_req)
MarketOrderRequest builds a JSON payload for a market order. Key parameters:
- symbol: the ticker. Alpaca supports US stocks (NYSE, NASDAQ, OTC), ETFs, US options (via a separate options order API), and a set of crypto pairs. It does not support futures.
- qty: number of shares. Fractional shares are supported for some securities (use
notionalinstead ofqtyto specify a dollar amount). - side:
OrderSide.BUYorOrderSide.SELL. Short selling on paper uses the same syntax as buying. - time_in_force:
DAYmeans the order expires at the end of the current trading day if not filled.GTC(Good Till Cancelled) stays open until manually cancelled or filled.IOC(Immediate or Cancel) fills immediately or cancels.
submit_order returns an Order object immediately with status = OrderStatus.PENDING_NEW. The order is routed to Alpaca’s paper matching engine asynchronously. You can poll client.get_order_by_id(order.id) or subscribe to the WebSocket order stream to track status transitions: PENDING_NEW → NEW → PARTIALLY_FILLED → FILLED (for market orders during market hours, fill typically happens within milliseconds).
Lines 45–50: Cancelling the paper order
client.cancel_order_by_id(order.id)
cancelled = client.get_order_by_id(order.id)
cancel_order_by_id sends a DELETE request to the order. A market order that has already been filled cannot be cancelled — if the order fills before your cancel request reaches the matching engine, the cancel will return a 422 error. In the paper environment, market orders placed outside regular trading hours (9:30 AM–4:00 PM ET) queue until market open, giving ample time to cancel. The final get_order_by_id confirms the status is OrderStatus.CANCELED.
From Paper to Live: What Changes
| Component | Paper | Live |
|---|---|---|
| TradingClient flag | paper=True |
paper=False |
| API keys | Paper keys (separate set) | Live keys (generated from live dashboard) |
| Endpoint | paper-api.alpaca.markets |
api.alpaca.markets |
| Fills | Simulated against real prices | Real exchange routing (NMS, NBBO) |
| Capital at risk | None | Real money |
| Order/account API | Identical — same Python code | |
Next Architecture Steps
This walkthrough covers the minimum viable connection. A production paper-trading loop adds:
- WebSocket order stream:
alpaca.trading.stream.TradingStreamfor real-time order status updates instead of polling. - Data stream:
alpaca.data.live.StockDataStreamfor live bars and quotes to trigger strategy signals. - Error handling: Alpaca API errors return
alpaca.common.exceptions.APIError. Wrapsubmit_orderin a try/except to catch insufficient buying power, invalid symbol, or market-closed errors gracefully. - Position management:
client.get_all_positions()returns current open positions. Use this to check existing exposure before placing new orders.
For a comparison of Alpaca’s paper environment against Interactive Brokers paper and other sandboxes, see Best Paper Trading Sandboxes. For the Alpaca vs IBKR API architecture comparison (authentication complexity, asset class coverage, fill quality), see Alpaca vs Interactive Brokers.
Frequently Asked Questions
- Is Alpaca paper trading free?
- Yes. Alpaca paper trading is free with no minimum deposit and no time limit. You sign up at alpaca.markets, generate paper API keys from the dashboard, and gain access to the paper endpoint (paper-api.alpaca.markets) immediately. The paper account is pre-funded with $100,000 of simulated cash. Paper trading supports market orders, limit orders, stop orders, and bracket orders on US stocks, ETFs, options, and crypto. There are no commissions on paper trades. Alpaca Markets, Inc. is a FINRA-registered broker-dealer; the paper endpoint is distinct from the live endpoint and no real money moves. AlgoDrill is unaffiliated with Alpaca Markets, Inc.
- What is the difference between Alpaca paper and live trading in alpaca-py?
- The only code difference between paper and live in alpaca-py is the paper=True flag in TradingClient: TradingClient(KEY, SECRET, paper=True) routes to paper-api.alpaca.markets; TradingClient(KEY, SECRET, paper=False) routes to api.alpaca.markets. Paper uses different API keys than live -- you generate them separately in the Alpaca dashboard under 'Paper Trading'. The order submission API (submit_order), account API (get_account), and order management API (cancel_order_by_id) are identical in both environments. The paper environment simulates fills using real market prices but does not route to any exchange. Switching from paper to live requires only changing the keys and the paper flag.
- How do I get Alpaca paper API keys?
- Go to alpaca.markets and create a free account. After email verification, navigate to the Paper Trading section of your dashboard. Click 'View' next to API Key. You will see a Key ID and a Secret Key. The Secret Key is shown only once at creation time -- copy it immediately. If you lose it, you must regenerate a new key pair. Export the keys to your shell before running any script: export ALPACA_PAPER_KEY='your_key_id_here' and export ALPACA_PAPER_SECRET='your_secret_key_here'. Never put these values in your source code, commit history, or any file that might be shared.
- Does this script execute real trades?
- No. The script uses Alpaca's paper endpoint (paper=True), which routes to paper-api.alpaca.markets -- a simulated environment that uses real market prices but moves no real money. AlgoDrill is a publisher and does not hold or transmit broker credentials; the keys in this walkthrough are read from your local environment variables and never leave your machine. AlgoDrill never connects to any broker on your behalf and never executes trades. This page documents the code architecture; you run the script on your own machine against your own paper account.
See how Alpaca’s API architecture compares to Interactive Brokers across authentication, asset coverage, and fill quality.
Alpaca vs Interactive Brokers → All Code Walkthroughs →