tursodatabase/turso · error · TursoServerlessException
HTTP error! status: {(int)response.StatusCode}
Error message
HTTP error! status: {(int)response.StatusCode} What it means
ExecutePipelineAsync posts the JSON pipeline to {baseUrl}/v3/pipeline and, on any non-2xx response, throws TursoServerlessException containing only the numeric HTTP status. The response body — which for Turso errors usually carries a JSON message — is not read on this path, so authentication, URL, and request-shape failures all surface as this one generic message.
Source
Thrown at bindings/dotnet/src/Turso.Serverless.Client/HranaHttp.cs:32
/// <summary>HTTP header carrying the encryption key of an encrypted Turso Cloud database.</summary>
internal const string EncryptionKeyHeader = "x-turso-encryption-key";
private static readonly JsonSerializerOptions JsonOptions = new(JsonSerializerDefaults.Web);
internal static async Task<HranaPipelineResponse> ExecutePipelineAsync(
HttpClient httpClient,
string baseUrl,
string? authToken,
string? remoteEncryptionKey,
HranaPipelineRequest request,
CancellationToken cancellationToken)
{
using var httpRequest = CreateRequest($"{baseUrl}/v3/pipeline", authToken, remoteEncryptionKey, request);
using var response = await httpClient.SendAsync(httpRequest, HttpCompletionOption.ResponseContentRead, cancellationToken).ConfigureAwait(false);
if (!response.IsSuccessStatusCode)
{
throw new TursoServerlessException($"HTTP error! status: {(int)response.StatusCode}");
}
var body = await response.Content.ReadAsStringAsync(cancellationToken).ConfigureAwait(false);
return JsonSerializer.Deserialize<HranaPipelineResponse>(body, JsonOptions)
?? throw new TursoServerlessException("Empty pipeline response");
}
internal static async Task<(HranaCursorResponse Response, IAsyncEnumerable<HranaCursorEntry> Entries)> ExecuteCursorAsync(
HttpClient httpClient,
string baseUrl,
string? authToken,
string? remoteEncryptionKey,
HranaCursorRequest request,
CancellationToken cancellationToken)
{
var httpRequest = CreateRequest($"{baseUrl}/v3/cursor", authToken, remoteEncryptionKey, request);
HttpResponseMessage? response = null;View on GitHub (pinned to 244cde92a7)
Solutions
- Verify the URL: https://<database>-<org>.turso.io (or your libsql endpoint) with no trailing path.
- Verify the auth token is present, current, and scoped to the database (turso db tokens create / show).
- For encrypted databases, supply the encryption key so the x-turso-encryption-key header is set.
- Reproduce with curl -H 'Authorization: Bearer <token>' -d @pipeline.json <url>/v3/pipeline to see the server's JSON error body, which this code path discards.
Example fix
// before: token null or stale -> 401 -> HTTP error! status: 401
var conn = new TursoConnection("Data Source=https://db-org.turso.io;AuthToken=");
// after: load the token from the environment
var conn = new TursoConnection($"Data Source=https://db-org.turso.io;AuthToken={Environment.GetEnvironmentVariable("TURSO_AUTH_TOKEN")}"); Defensive patterns
Strategy: try-catch
Validate before calling
// validate endpoint and token shape before first use
if (!Uri.TryCreate(baseUrl, UriKind.Absolute, out var u) || u.Scheme != Uri.UriSchemeHttps)
throw new ArgumentException("baseUrl must be an https:// URL");
if (string.IsNullOrWhiteSpace(authToken))
throw new InvalidOperationException("Auth token missing; set TURSO_AUTH_TOKEN"); Try / catch
catch (TursoServerlessException ex) when (ex.Message.Contains("status: 401"))
{
// refresh the database token and rebuild the client/connection
}
catch (TursoServerlessException ex) when (ex.Message.Contains("status: 5"))
{
// server incident: retry with backoff
} Prevention
- Load the auth token from environment/secret store at startup and fail fast when empty.
- Regenerate tokens before expiry; store the database URL next to the token in config.
- Smoke-test the endpoint with curl to see the JSON error body the client discards.
- Supply the encryption key header for encrypted databases.
When it happens
Trigger: 401 from a missing/invalid/expired Bearer token; 404 from a wrong baseUrl or database name; 403 from a token without access to the database; 400 from a malformed pipeline body; 5xx from server incidents; missing x-turso-encryption-key header for an encrypted database.
Common situations: Expired Turso auth token in CI; URL copied without the https:// scheme or with a typo'd org/database slug; environment-specific token mix-ups; encrypted database accessed without the key; gateways returning 502 during maintenance.
Related errors
- Empty pipeline response
- No cursor response received
- Only finite numbers (not Infinity or NaN) can be passed as a
- Unexpected token for last_insert_rowid: {reader.TokenType}
- Describe execution failed
AI-assisted analysis of tursodatabase/turso@244cde92a7 (2026-08-20).
Data as JSON: /api/errors/4a9559b5ab46a508.
Report an issue: GitHub.