We’re experiencing OAuth2 authentication failures when posting billing transactions through the REST API. Our billing-mgmt module integration worked fine in twx-96, but after upgrading to twx-97, we’re getting consistent 401 Unauthorized responses. The OAuth2 token claims appear valid when we decode them, but the API gateway seems to be rejecting them during header validation. We’re in a multi-tenant setup with three separate tenant domains, and the token generation process hasn’t changed. The error happens specifically when calling /Thingworx/Things/BillingService/Services/PostTransaction with a valid bearer token. Has anyone encountered similar OAuth2 token validation issues with the billing API after the 97 upgrade? We need to resolve this quickly as it’s blocking our entire billing sync process.
The signature verification error is your smoking gun. ThingWorx 97 updated the JWT validation library and now requires RS256 signing algorithm explicitly. If you’re using HS256, that’s your problem. Here’s the comprehensive fix addressing all three focus areas:
OAuth2 Token Claims Fix: Update your token provider to include these exact claims:
{
"iss": "https://your-oauth-provider.com",
"aud": "thingworx-billing-api",
"sub": "billing-service-account",
"tenant_id": "prod-tenant-01",
"scope": "billing:write"
}
Note the aud must be ‘thingworx-billing-api’ not ‘thingworx-api’ in 97.
API Gateway Header Validation: Add these headers to every billing API request:
Authorization: Bearer {your_token}
X-Tenant-ID: prod-tenant-01
Content-Type: application/json
X-Api-Version: v2
The X-Api-Version header is new in 97 and defaults to v1 which has different validation rules.
Multi-Tenant Authentication: In your ThingWorx tenant configuration (ApplicationSettings.json), register your OAuth provider:
"oauth": {
"issuer": "https://your-oauth-provider.com",
"audience": "thingworx-billing-api",
"signingAlgorithm": "RS256",
"publicKeyUrl": "https://your-oauth-provider.com/.well-known/jwks.json"
}
The key changes: 1) RS256 algorithm requirement, 2) specific audience claim for billing API, 3) mandatory X-Tenant-ID and X-Api-Version headers, 4) registered OAuth issuer in tenant config. After making these changes, tokens should validate correctly. The 401 errors were happening because the gateway couldn’t verify signatures using the old HS256 keys, and the missing headers caused the request to fail tenant context validation even when the signature was valid.
Also ensure your OAuth provider’s JWKS endpoint is accessible from ThingWorx servers for public key retrieval. We had to whitelist the OAuth provider domain in our firewall rules. Test with a fresh token after all config changes.
Thanks for the suggestion. I decoded the token and the aud claim shows ‘thingworx-api’ which is what we’ve always used. The scope includes ‘billing:write’ and ‘billing:read’. Here’s what I see:
{
"aud": "thingworx-api",
"scope": "billing:write billing:read",
"tenant_id": "prod-tenant-01"
}
Still getting 401 errors. Could this be related to API gateway header forwarding?
Check your token audience claim. ThingWorx 97 introduced stricter validation for multi-tenant setups. The aud claim must exactly match your tenant’s registered API identifier. Also verify the scope includes ‘billing:write’ permission.
Added the X-Tenant-ID header and still seeing 401s. Could this be a token expiration timing issue? Our tokens have 3600s TTL. Also noticed the gateway logs mention ‘invalid signature verification’ occasionally. Wondering if the signing key configuration changed between versions.
I’ve seen this before. In twx-97, the API gateway now requires explicit tenant context in the X-Tenant-ID header, separate from the token. The multi-tenant authentication model changed to prevent token reuse across tenants. Your token might be valid, but without the matching header, the gateway rejects it. Try adding the X-Tenant-ID header with your tenant identifier to each API call. Also double-check that your OAuth2 provider is issuing tokens with the new tenant-scoped claims format that 97 expects.