Glossary
Environment Variables
Some environment variables are required for all Polaris deployments, some are required for a specific set of SEPs, and others are optional.
Environment variables can be set within the environment itelf, in a .env
file, or specified in your Django settings file.
A .env
file must be within the directory specified by Django’s BASE_DIR
setting or specified explitly using the POLARIS_ENV_PATH
setting.
To set the variables in the project’s settings file, the variable name must be prepended with POLARIS_
. Make sure not to put sensitive information in the project’s settings file, such as Stellar secret keys, encryption keys, etc.
- ACTIVE_SEPS
Required.
A list of Stellar Ecosystem Proposals (SEPs) to run using Polaris. Polaris uses this list to configure various aspects of the deployment, such as the endpoint available and settings required.
Ex.
ACTIVE_SEPS=sep-1,sep-10,sep-24
- ADDITIVE_FEES_ENABLED
A boolean value indicating whether or not fee amounts returned from the registered fee function should be added to
Transaction.amount_in
, the amount the user should send to the anchor. Only used for SEP-24 transactions, specifically when aTransactionForm
is submitted. If this functionality is desired for SEP-6 or SEP-31 transactions, the anchor can implement the logic themselves in the provided integration functions.Defaults to
False
. By default, fees are subtracted from the amount initially specified by the client application or user.Ex.
ADDITIVE_FEES_ENABLED=1
,ADDITIVE_FEES_ENABLED=True
- CALLBACK_REQUEST_DOMAIN_DENYLIST
A list of home domains to check before accepting an
on_change_callback
parameter in SEP-6 and SEP-24 requests. This setting can be useful when a client is providing a callback URL that consistently reaches the CALLBACK_REQUEST_TIMEOUT limit, slowing down the rate at which transactions are processed. Requests containing denied callback URLs will not be rejected, but the URLs will not be saved toTransaction.on_change_callback
and requests will not be made.- CALLBACK_REQUEST_TIMEOUT
An integer for the number of seconds to wait before canceling a server-side callback request to
Transaction.on_change_callback
if present. Only used for SEP-6 and SEP-24. Polaris makes server-side requests toTransaction.on_change_callback
from CLI commands such asprocess_pending_deposits
andexecute_outgoing_transactions
. Server-side callbacks requests are not made from the API server.Defaults to 3 seconds.
Ex.
CALLBACK_REQUEST_TIMEOUT=10
- INTERACTIVE_JWT_EXPIRATION
An integer for the number of seconds a one-time-token used to authenticate the client with a SEP-24 interactive flow is valid for. This token (JWT) is distinct from the JWT returned by SEP-10, which should not be included in URLs.
Defaults to 30 seconds.
Ex.
INTERACTIVE_JWT_EXPIRATION=180
- LOCAL_MODE
A boolean value indicating if Polaris is in a local environment. Defaults to
False
. The value will be read from the environment usingenviron.Env.bool()
.Ex.
LOCAL_MODE=True
,LOCAL_MODE=1
- HORIZON_URI
A URL (protocol + hostname) for the Horizon instance Polaris should connect to.
Defaults to
https://horizon-testnet.stellar.org
.Ex.
HORIZON_URI=https://horizon.stellar.org
- HOST_URL
Required.
The URL (protocol + hostname) that this Polaris instance will run on.
Ex.
HOST_URL=https://testanchor.stellar.org
,HOST_URL=http://localhost:8000
- MAX_TRANSACTION_FEE_STROOPS
An integer limit for submitting Stellar transactions. Increasing this will increases the probability of the transaction being included in a ledger.
Defaults to the return value Python SDK’s
Server().fetch_base_fee()
, which is the most recent ledger’s base fee, usually 100.Ex.
MAX_TRANSACTION_FEE_STROOPS=300
- SEP6_USE_MORE_INFO_URL
A boolean value indicating whether or not to provide the
more_info_url
response attribute in SEP-6GET /transaction(s)
responses and make thesep6/transaction/more_info
endpoint available.Defaults to
False
.Ex.
SEP6_USE_MORE_INFO_URL=1
,SEP6_USE_MORE_INFO_URL=True
- SEP10_CLIENT_ATTRIBUTION_REQUIRED
A boolean that if true, requires client applications to verify their identity by passing a domain in the challenge transaction request and signing the challenge with the
SIGNING_KEY
on that domain’s SEP-1 stellar.toml. See the SEP-10 section Verifying Client Application Identity for more information.Defaults to
False
.Ex.
SEP10_CLIENT_ATTRIBUTION_REQUIRED=True
,SEP10_CLIENT_ATTRIBUTION_REQUIRED=1
- SEP10_CLIENT_ATTRIBUTION_REQUEST_TIMEOUT
An integer for the number of seconds to wait before canceling a server-side request to the
client_domain
parameter specified in the request, if present. This request is made from the API server and therefore an unresponsiveclient_domain
can slow down request processing.Defaults to 3 seconds.
Ex.
SEP10_CLIENT_ATTRIBUTION_REQUEST_TIMEOUT=10
- SEP10_CLIENT_ATTRIBUTION_ALLOWLIST
A list of domains that the server will issue challenge transactions containing
client_domain
Manage Data operations for. IfSEP10_CLIENT_ATTRIBUTION_REQUIRED
isTrue
, client applications must pass aclient_domain
parameter whose value matches one of the elements in this list, otherwise the request will be rejected. IfSEP10_CLIENT_ATTRIBUTION_REQUIRED
isFalse
, Polaris will return a challenge transaction without the requestedclient_domain
Manage Data operation.Ex.
SEP10_CLIENT_ATTRIBUTION_ALLOWLIST=approvedwallet1.com,approvedwallet2.com
- SEP10_CLIENT_ATTRIBUTION_DENYLIST
A list of domains that the server will not issue challenge transactions containing
client_domain
Manage Data operations for. IfSEP10_CLIENT_ATTRIBUTION_REQUIRED
isTrue
, client applications that pass aclient_domain
parameter value that matches one of the elements in this list will be rejected. IfSEP10_CLIENT_ATTRIBUTION_REQUIRED
isFalse
, Polaris will return a challenge transaction without the requestedclient_domain
Manage Data operation.Ex.
SEP10_CLIENT_ATTRIBUTION_DENYLIST=maliciousclient.com
- SEP10_HOME_DOMAINS
A list of home domains (no protocol, only hostname) that Polaris should consider valid when verifying SEP-10 challenge transactions sent by clients. The first domain will be used to build SEP-10 challenge transactions if the client request does not contain a
home_domain
parameter. Polaris will reject client requests that contain ahome_domain
value not included in this list. The value will be read from the environment usingenviron.Env.list()
.Defaults to a list containing the hostname of
HOST_URL
defined above if not specified.Ex.
SEP10_HOME_DOMAINS=testanchor.stellar.org,example.com
- SERVER_JWT_KEY
Required for SEP-10.
A secret string used to sign the encoded SEP-10 JWT contents. This should not be checked into version control.
Ex.
SERVER_JWT_KEY=supersecretstellarjwtsecret
- SIGNING_SEED
Required for SEP-10.
A Stellar secret key used to sign challenge transactions before returning them to clients. This should not be checked into version control.
Ex.
SIGNING_SEED=SAEJXYFZOQT6TYDAGXFH32KV6GLSMLCX2E2IOI3DXY7TO2O63WFCI5JD
- STELLAR_NETWORK_PASSHRASE
The string identifying the Stellar network to use.
Defaults to
Test SDF Network ; September 2015
.Ex.
STELLAR_NETWORK_PASSPHRASE="Public Global Stellar Network ; September 2015"
Internationalization
Polaris currently supports English and Portuguese. Note that this feature depends on the GNU gettext library. This page assumes you understand how translations work in Django.
If you’d like to add support for another language, make a pull request to Polaris with the necessary translation files. If Polaris supports the language you wish to provide, make sure the text content rendered from your app supports translation to that language.
To enable this support, add the following to your settings.py:
from django.utils.translation import gettext_lazy as _
USE_I18N = True
USE_L10N = True
USE_THOUSAND_SEPARATOR = True
LANGUAGES = [("en", _("English")), ("pt", _("Portuguese"))]
Note that adding the LANGUAGE
setting is required. Without this,
Django assumes your application supports every language Django itself
supports.
You must also add django.middleware.locale.LocaleMiddleware
to your
settings.MIDDLEWARE
after SessionMiddleware
:
MIDDLEWARE = [
...,
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.locale.LocaleMiddleware',
'corsheaders.middleware.CorsMiddleware',
...
]
Once your project is configured to support translations, compile the translation files:
python anchor/manage.py compilemessages
Finally, configure your browser to use the targeted language. You should then see the translated text.
Logging
You can add Polaris’ logger to your LOGGING configuration. For example:
LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'formatters': {
'simple': {
'format': '{levelname} {message}',
'style': '{',
},
},
'handlers': {
'console': {
'level': 'DEBUG',
'class': 'logging.StreamHandler',
'formatter': 'simple'
}
},
'loggers': {
'myapp': {
'handlers': ['console'],
'propogate': True,
'LEVEL': 'DEBUG'
},
'polaris': {
'handlers': ['console'],
'propagate': True,
'LEVEL': 'INFO'
},
}
}
You may want to configure the LEVEL
of the Polaris logger differently depending on whether you’re running the service locally or in production. One way to do this by reading a POLARIS_LOG_LEVEL
variable, or something similar, from the project’s environment.
Multisignature Assets
Background and Definitions
In the broader Stellar context, a multisignature account has more than one Stellar public key listed in it’s signers list. In an effort not to rephrase good documentation, a good quote from our Stellar dev documentation is:
In two cases, a transaction may need more than one signature. If the transaction has operations that affect more than one account, it will need authorization from every account in question. A transaction will also need additional signatures if the account associated with the transaction has multiple public keys.
This optional feature adds security but also complexity to an anchor’s application logic.
Multisignature Assets in Polaris
In the context of Polaris, multisignature assets refer to anchored assets that use distribution accounts that require multiple signatures in order to be successfully submitted to the Stellar network. Specifically, Polaris defines multisignatures assets as those whose distribution account’s medium threshold is not met by the master key’s weight.
Anchors can optionally configure each of their assets’ distribution accounts to require more than one (or many) signatures from valid signers in order to improve security around the flow of outgoing payments. The signers for each asset’s distribution account may or may not include the account’s public key as a master signer on the account by reducing it’s weight to zero.
Thresholds, signers, and more are configured on a Stellar account using the Set Options operation.
Note that anchors that issue their own assets may configure the issuing account to require multiple signatures as well. However, this is outside the scope of Polaris’ multisignature asset support.
Channel Accounts
A channel account as defined by the documentation,
[is] simply another Stellar account that is used not to send the funds but as the “source” account of the transaction. Remember transactions in Stellar each have a source account that can be different than the accounts being effected by the operations in the transaction. The source account of the transaction pays the fee and consumes a sequence number [and is not affected in any other way.]
Using channel accounts for transactions that need multiple signatures allows for a good deal of flexibility in terms of how signatures are collected for a transaction, but the reason why they are necessary is best explained by walking through what the process would look like without channel accounts.
A client application makes a POST /deposit request and creates a transaction record
The client application sends the funds to be deposited to the anchor’s off-chain account
The anchor detects the received funds
The anchor uses the current sequence number of the asset’s distribution account to create a transaction envelope in their database
The anchor collects the necessary signatures on the transaction envelope
Meanwhile, the distribution account submits another transaction to the Stellar Network
When all signatures have been collected, the envelope XDR is submitted to the network
The transaction fails with a 400 HTTP status code
This is due to the fact that the sequence number used for the transaction in step 3 is less than the current sequence number on the account as a direct result of step 4. Remember, when a Stellar account submits a transaction, the source account’s sequence number must be greater than the last sequence number used for that account.
Therefore, when a sequence number is used in an envelope to be submitted later, the sequence number in the envelope is likely less than the sequence number on the account when the anchor eventually gets around to submitting the transaction. This will cause the transaction to fail.
All this context is necessary to state the following:
Polaris uses channel accounts created by the anchor the source accounts on transactions using multisig distribution accounts as the source of funds so that transaction envelopes can be serialized, signed, and submitted on any schedule.
Using channel accounts, Polaris supports the following process for multisignature transactions:
A client application makes a POST /deposit request and creates a transaction record
The client application sends the funds to be deposited to the anchor’s off-chain account
The anchor detects the received funds
Polaris detects that the transaction requires more than one signature
Polaris calls
create_channel_account()
for the transaction recordThe anchor funds a Stellar account using another Stellar account that doesn’t require multiple signatures
Polaris uses the channel account as the transaction’s source account when building and saving the envelope XDR
The anchor collects signatures on the transaction and updates it as ‘ready for submission’
Polaris retrieves multisig transactions ready to be submitted in process_pending_deposits and submits them
Multisig transactions succeed assuming it has proper signatures
Polaris calls
after_deposit()
, in which the anchor can optionally merge the channel account back into another distribution account.
Currently, multisignature asset support is only relevant in the context of SEP-6 and 24 deposit transactions. Withdraw transaction flows don’t involve the anchor making any Stellar transaction using an asset’s distribution account, and SEP-31 outbound payments are not yet supported in Polaris.
Rate Limiting
It is highly encouraged to employ a rate limiting strategy when running Polaris to ensure the service remains available for all client applications. Many endpoints retrieve and create database records on each request, and some endpoints make outgoing web requests to Horizon or a client application’s callback endpoint.
Rate limiting can be particularly important for SEP-6 or SEP-24 deposit requests because the anchor is expected to poll their off-chain rails to detect if any of the funds from pending transactions initiated in these requests have arrived in the anchor’s account, which can be a resource-intensive process.
Rate limiting can be deployed using a number of strategies that often depend on the anchor’s deployment infrastructure. Optionally, the anchor could also implement a rate limiting policy using Django custom middleware support.