Deprecations
Deprecated Features
The following table lists deprecated features and their respective shutdown dates.
Feature | Deprecated Date | Shutdown Date | Details |
---|---|---|---|
request_reactor_id and response_reactor_id removed from Proxies | November 30, 2022 | March 31, 2023 | In order to simplify management of Proxies, use of request_transform and response_tramsform has been recommended over Reactors. |
Token Privacy Settings | October 13, 2022 | February 1, 2023 | Privacy settings (i.e. classification, impact level, and restriction policy) have been deprecated and replaced by a more flexible authorization model based upon Containers and Access Rules. For more information, see the section below on Migrating from Privacy Settings. |
Reactor Formulas | October 16, 2022 | February 14, 2024 | Reactor Formulas have been deprecated in favor of Reactors with code . For more information, see the section below on Migrating from Reactor Formulas. |
Application Key Regenerate | April 17, 2024 | October 17, 2024 | Regenerating API Keys for an Application has been replaced with Application Keys, to Migrate you will Create a new Application Key and remove the old key. |
Old Rate Limits | June 10, 2024 | July 16, 2024 | Rate limits have been deprecated in favor of Rate Limits. |
Async Reactor callback_url | November 1, 2024 | January 15, 2025 | Async Reactors will no longer support the callback_url attribute. For more information, see the section below on Async Reactor callback_url Deprecation. |
Multiple Terms in a single query | November 11, 2024 | March 1, 2025 | Multiple Terms in a single query is deprecated. |
Migrating From Mulitple Search Terms
Query on single field, filter the response
Remove one of the terms from the query
and filter the results from Token Search by the other property once returned to your system:
Original Search Query: metadata.type:phone AND metadata.customer_id:1234
New Query: metadata.customer_id:1234
Filter in your system: metadata.type = "phone"
Aliases
Use Aliases to create a single identifier from the multiple terms currently required in a query
.
Example:
A query with the following multiple terms:
metadata.type:phone AND metadata.customer_id:1234
Can be converted to the following Alias when creating a token:
{
"id": "1234_phone",
...
}
Now systems are capable of requesting this token by the id
attribute:
GET /tokens/1234_phone
Moving from metadata searching to using an alias will require migrating tokens to the new alias.
Combine metadata
Combine the multiple terms into a single metadata
field and continue to use the query
with a single term:
Original metadata
field:
{
"type": "phone",
"customer_id": "1234"
}
New metadata
field:
{
"type": "phone",
"customer_id": "1234",
"type_customer_id": "phone_1234"
}
Original Search Query: metadata.type:phone AND metadata.customer_id:1234
New Query: metadata.type:phone AND metadata.customer_id:1234
Moving from metadata searching to a single metadata term will require migrating tokens include the new combined metadata field.
Migrating to New Rate Limits
Learn more about these Rate Limit changes in our blog Introducing New Rate Limits.
Production Tenants
- Private Applications
- You must rotate Private API keys to the new format to maintain your existing Rate Limits.
- Public and Management Applications
- While it is suggested to rotate these keys, this is an option to change for these Applications - based on our findings, no active customers will see any reduction in service.
- Whitelabel Proxies
- No action is required for these tenants
- Reactors
- If your Reactor specifies an Application, you'll need to generate a new key for that application to ensure it has the correct rate limit. No other change is required.
Test Tenants
No changes are required for Test Tenants. If you need a higher rate limit for these tenants, please contact support@basistheory.com
or your account representative.
How to rotate your Private API keys
Rotate via our Portal
If you created your keys via the Portal - follow this guide:
- Go to the Applications List
- Find the Applications needing keys rotated and click the "edit" icon ✏️.
- In the Application details page, find the "API Keys" section and create a new API Key. (Don't worry, this will not stop the existing keys from working.)
- Copy the new generated key and update your systems with the new value.
- Once you are done updating all your systems with the new value, click the "trash" 🗑️ icon to delete the "Legacy" key. (Only do this once all usages of the keys have been updated)
Rotate via Terraform
You are able to manage API Keys via Terraform with the Guide found in v2 of our Terraform Provider.
- Create a new key for the Applications
- Update your systems with the new key
- Once all systems have been updated, delete the old key
Application Key Regenerate Deprecation
Regenerating an application's API key used to involve calling the Regenerate
endpoint on the Application. With the introduction of Application keys, this functionality has been replaced with the ability to create new Application Keys and remove the old key.
To recreate the Regeneration action you'll need to:
Old Rate Limit Deprecation
The existing rate limits will be deprecated in favor of new rate limits capable of being customized.
- Globale Rate Limit
- Counter: IP
- Rate: 1000 Requests / 10 Seconds
- Block Duration: 10 Seconds
- Portal:
- Counter: IP
- Rate: 600 Requests / 10 Seconds
- Block Duration: 10 Seconds
- API
- POST /tokens/search
- Counter: IP
- Rate 50 Requests / 10 Seconds
- Block Duration: 10 Seconds
- GET /tokens
- Counter: IP
- Rate 100 Requests / 10 Seconds
- Block Duration: 10 Seconds
- POST (/tokens | /tokenize)
- Counter: IP
- Rate 200 Requests / 10 Seconds
- Block Duration: 10 Seconds
- POST /tokens/search
Migrating From Privacy Settings
Privacy settings were previously used to scope access to Tokens based on their data classification and impact levels.
In order to provide a more flexible access control model that can be customized per Application, we have introduced
Token Containers
to logically group Tokens according to any data governance requirements. A Token may be explicitly added to a container
when creating the Token, or if unspecified, a Token will be placed within the container /<classification>/<impact_level>/
by default. If you were previously customizing a Token's classification or impact level, please update your systems to
directly set the containers
attribute instead.
Restriction policies were previously used in conjunction with impact level based read
permissions (e.g., token:general:read:low
) to define how Token data should be transformed when reading Tokens with
a higher impact level than your permission allows. This model proved to be too inflexible as it was a global setting
applied at the Token level and could not be customized per actor. Restriction policies no longer have any functional
impact, and were replaced by transforms applied via Access Rules.
If your systems are using the privacy
attribute of the Token Object in API responses, please
update your integration to ignore this attribute as it will be removed on February 1, 2023.
Migrating From Reactor Formulas
Reactor Formulas were how you added code to a Reactor and configured some of its behavior.
To offer less friction when creating Reactors, we have introduced a new code
attribute to the Reactor Object.
This attribute is a string
containing the code that will be executed when the Reactor is triggered.
Alongside not having to create a new formula for each Reactor with different code, this new approach also removes some previous restrictions on configuration
and request_parameters
.
Reactors with code
will not provide validation of the configuration
attribute or its request parameters, so you will need to perform this validation directly in your code if necessary.
If your systems are using the formula
attribute of the Reactor Object in API responses, please update to use code
instead.
This can be done simply by taking the value for the code
attribute on the formula and setting it as the value for the code
attribute on the Reactor.
Below there are some examples on how this operation can be performed by retrieving the formula object and performing a [patch operation] in the Reactor:
- cURL
- JavaScript
- C#
- Java
- Python
- Go
curl "https://api.basistheory.com/reactor-formulas/17069df1-80f4-439e-86a7-4121863e4678" \
-H "BT-API-KEY: <MANAGEMENT_API_KEY>"
import { BasisTheory } from "@basis-theory/basis-theory-js";
const bt = await new BasisTheory().init("<MANAGEMENT_API_KEY>");
const reactor = await bt.reactors.retrieve(
"5b493235-6917-4307-906a-2cd6f1a90b13"
);
const reactorFormula = await bt.reactorFormulas.retrieve(reactor.formula.id);
const patchedReactor = await bt.reactors.patch(reactor.id,
{
code: reactorFormula.code,
}
);
using BasisTheory.net.Reactors;
using BasisTheory.net.ReactorFormulas;
var reactorClient = new ReactorClient("<MANAGEMENT_API_KEY>");
var reactor = await reactorClient.GetByIdAsync("5b493235-6917-4307-906a-2cd6f1a90b13");
var formulaClient = new ReactorFormulaClient("<MANAGEMENT_API_KEY>");
var reactorFormula = await formulaClient.GetByIdAsync(reactor.Formula.Id);
var patchedReactor = await reactorClient.PatchAsync(Reactor.Id,
new Reactor {
Code = reactorFormula.Code
});
import com.basistheory.*;
import com.basistheory.auth.*;
import java.util.UUID;
public class Example {
public static void main(String[] args) throws Exception {
ApiClient defaultClient = Configuration.getDefaultApiClient();
defaultClient.setBasePath("https://api.basistheory.com");
ApiKeyAuth ApiKey = (ApiKeyAuth) defaultClient.getAuthentication("ApiKey");
ApiKey.setApiKey("<MANAGEMENT_API_KEY>");
ReactorsApi apiInstance = new ReactorsApi(defaultClient);
Reactor reactor = apiInstance.getById(UUID.fromString("5b493235-6917-4307-906a-2cd6f1a90b13"));
ReactorFormulasApi apiInstance = new ReactorFormulasApi(defaultClient);
ReactorFormula reactorFormula = apiInstance.getById(reactor.getFormula().getId());
PatchReactorRequest patchReactorRequest = new PatchReactorRequest();
Reactor patchedReactor = apiInstance.patch(reactor.getId(), patchReactorRequest
.code(reactorFormula.getCode()));
}
}
import basistheory
from basistheory.api import reactors_api
from basistheory.api import reactor_formulas_api
with basistheory.ApiClient(configuration=basistheory.Configuration(api_key="<MANAGEMENT_API_KEY>")) as api_client:
reactors_client = reactors_api.ReactorsApi(api_client)
reactor = reactors_client.get_by_id("5b493235-6917-4307-906a-2cd6f1a90b13")
reactor_formulas_client = reactor_formulas_api.ReactorFormulasApi(api_client)
reactor_formula = reactor_formulas_client.get_by_id(reactor.formula.id)
patched_reactor = reactors_client.patch(reactor.id, patch_reactor_request=PatchReactorRequest(
code=reactor_formula.code
))
package main
import (
"context"
"github.com/Basis-Theory/basistheory-go/v3"
)
func main() {
configuration := basistheory.NewConfiguration()
apiClient := basistheory.NewAPIClient(configuration)
contextWithAPIKey := context.WithValue(context.Background(), basistheory.ContextAPIKeys, map[string]basistheory.APIKey{
"ApiKey": {Key: "<MANAGEMENT_API_KEY>"},
})
reactor, httpResponse, err := apiClient.ReactorsApi.GetById(contextWithAPIKey, "5b493235-6917-4307-906a-2cd6f1a90b13").Execute()
reactorFormula, httpResponse, err := apiClient.ReactorFormulasApi.GetById(contextWithAPIKey, reactor.GetFormula().GetId()).Execute()
patchReactorRequest := *basistheory.NewPatchReactorRequest()
patchReactorRequest.SetCode(reactorFormula.GetCode())
patchedReactor, httpResponse, err := apiClient.ReactorsApi.Patch(contextWithAPIKey, reactor.GetId()).PatchReactorRequest(patchReactorRequest).Execute()
}
You can continue to use your existing Reactors with formula
until they are removed on a future date, but we advise you to migrate to code
as soon as possible.
Keep in mind that after migrating to code
the formula
will be removed from the Reactor but can still be retrieved for consulting purposes until the shutdown date.
Async Reactor callback_url
Deprecation
Async Reactors will no longer support the callback_url
attribute and will be replaced by the Reactor Webhooks Events.
To migrate your Async Reactors, you will need to:
- Create a new Webhook either with our Management API/Terraform Provider or in the Portal.
- You may be able to use the existing URL for your rector processing
- Invoke a Reactor Asynchronously with the new
/reactors/:id/react-async
endpoint. - Once your webhook is invoked, retrieve the Async Reactor Results
- This ensures the system receiving the webhook has access to the results of the reactor.
- Process the results in the same way you are currently doing with the
callback_url
To coordinate a rollout of these changes, we suggest you stop sending requests with callback_url
and change the request path from /react
to /react-async
when you roll out the new webhook handler code. This will avoid any overlap or duplication of processing.