Set up AWS PrivateLink
AWS PrivateLink gives you a direct, private connection from your VPC to Bitvavo — bypassing the public internet entirely. This is a one-time setup that improves connectivity reliability and latency for the following APIs:
- Exchange WebSocket API
- Market Data Pro WebSocket API
- Exchange FIX API
- Request for Quote WebSocket API
Because PrivateLink connections are application and protocol agnostic, you only need to point your client at the private endpoint address and connect as usual.
PrivateLink is available to institutional clients. You need to contact Bitvavo to approve your account that connects through PrivateLink.
Step 1: Request account allowlisting
Before you can connect to the Bitvavo VPC Endpoint Service, we must allowlist your AWS account:
- Send your AWS account ARN to Bitvavo at
[email protected]. - Wait for confirmation that we have allowlisted your account.
arn:aws:iam::123456789012:root
Step 2: Create a VPC endpoint
In your AWS console, select the AWS account and region for which you want to create the endpoint:
-
Go to VPC > PrivateLink and Lattice > Endpoints and select Create endpoint.
-
For Service type, select Endpoint services that use NLBs and GWLBs.
-
At the top, from the region dropdown, select the region where you want to create the endpoint.
-
Under Service Settings, enter the Service name provided by Bitvavo for your region.
-
Select Verify service:
Bitvavo Environment AWS Region Bitvavo service name UAT eu-central-1 (Frankfurt) com.amazonaws.vpce.eu-central-1.vpce-svc-0622fcf84ef3d295aPROD eu-central-1 (Frankfurt) com.amazonaws.vpce.eu-central-1.vpce-svc-033d30cbb20346118 -
Under Network settings, select the VPC where you want to deploy the endpoint.
importantPrivateLink only supports connections from private subnets with RFC 1918 address ranges (
10.0.0.0/8,172.16.0.0/12,192.168.0.0/16). -
Select Enable private DNS name so you can access the service through the private hostname.
-
Under Subnets, select the Availability Zone in which to enable the endpoint. For example:
AWS Region Availability Zones eu-central-1 (Frankfurt) euc1-az3
Under Security groups, make sure your endpoint allows inbound traffic from your VPC to the destination port specific to the API you use:
- Exchange WebSocket API:
8003 - Market Data Pro WebSocket API:
8002 - Exchange FIX API:
8001 - Request for Quote WebSocket API:
8004or9004
Step 3: Request connection acceptance
Next, Bitvavo must accept the connection you created in Step 2. To request acceptance:
- Send an email Bitvavo at
[email protected]with the following details:- In the subject, specify:
Acceptance request – <your company name>. - In the body, specify:
- Your VPC endpoint ID (for example,
vpce-xxxxxxxx) - The AWS region
- Your VPC endpoint ID (for example,
- In the subject, specify:
- Wait for confirmation that the endpoint is Available.
Step 4: Test the connection
Once the endpoint is available, verify connectivity from an EC2 instance or AWS Lambda function inside your VPC.
Check connectivity
Run a basic network check against the private endpoint and port:
# UAT
nc -v connection.bitvavo-uat.com 8003
# PROD
nc -v connection.bitvavo.com 8003
Ncat: Version 7.93 ( https://nmap.org/ncat )
Ncat: Connected to 10.x.x.x:8003.
Test connection
You can use the below JavaScript sample to test your WebSocket connection:
- Open a WebSocket connection to the private endpoint.
- Subscribe to the BTC-EUR order book.
- Wait for a single book event.
- Print the received event to the console.
- Disconnect from the WebSocket.
Update WS_BASE with the private endpoint hostname provided by Bitvavo.
const WS_BASE = 'wss://connection.bitvavo-uat.com:8003/v2';
const state = {
ws: null,
wsConnected: false,
currentMarket: 'BTC-EUR',
};
const subscribeMessage = {
action: 'subscribe',
channels: [
{ name: 'book', markets: [state.currentMarket] },
],
};
async function connectWebSocket() {
const ws = new WebSocket(WS_BASE);
state.ws = ws;
ws.addEventListener('open', () => {
if (ws !== state.ws) return;
state.wsConnected = true;
ws.send(JSON.stringify(subscribeMessage));
});
ws.addEventListener('message', (event) => {
let payload;
if (ws !== state.ws) return;
try {
payload = JSON.parse(event.data);
if (payload.market === 'BTC-EUR') {
console.info('Received book update for BTC-EUR:', payload);
console.info('======= Connection OK =======');
return closeWebSocket();
}
} catch (err) {
console.error('Failed to parse websocket message:', event.data);
return closeWebSocket();
}
});
ws.addEventListener('error', () => {
if (ws !== state.ws) return;
state.wsConnected = false;
return closeWebSocket();
});
}
function closeWebSocket() {
if (state.ws) {
console.warn('Disconnecting...');
state.ws.close();
}
state.ws = null;
state.wsConnected = false;
}
connectWebSocket();
If you see ======= Connection OK ======= in the output, the PrivateLink endpoint is working correctly.
Troubleshooting
Timeout or connection closed
This typically happens when the connection is established without TLS.
The Bitvavo VPC Endpoint Service exposes TLS-enabled TCP ports only, and all clients must initiate communication using TLS.
Resolution: Ensure that your application or test tool supports TLS. For example, validate connectivity using:
openssl s_client -connect connection.bitvavo-uat.com:8003 -brief
echo 'exit' | openssl s_client -connect connection.bitvavo-uat.com:8003 -brief
CONNECTION ESTABLISHED
Protocol version: TLSv1.2
Ciphersuite: ECDHE-RSA-AES128-GCM-SHA256
Peer certificate: CN = connection.bitvavo-uat.com
Hash used: SHA256
Signature type: RSA
Verification: OK
Supported Elliptic Curve Point Formats: uncompressed
Server Temp Key: ECDH, prime256v1, 256 bits
DONE