Post-Install Configuration

After you created the database and installed PowerAuth Cloud in the Docker, you need to perform mandatory post-installation steps. Most of those steps are performed in the database. While the Liquibase script bundled in the Docker image can create a correct database scheme, it does not populate it with the data. The contents of the database define particular customer setup. This is something that only you know and this is why you need to perform the configuration manually after the installation.

Creating the PowerAuth Application

Populating the tables related to PowerAuth applications is probably the most complicated step of the configuration. Basically, this is where you need to generate your cryptographic material related to the authenticator mobile app.

The easiest way to perform this step is to connect inside the Docker image and call the internal API provided by the PowerAuth Server component.

Connect inside the Docker image like so:

docker exec -it ${YOUR_CONTAINER_ID} /bin/sh; exit

After you connect to the internal Docker console, you can call cURL on the internal services to create the PowerAuth application:

curl -s -H "Content-Type: application/json" -X POST \
    -d '{ "requestObject": { "applicationName": "demo-application" } }' \
    http://localhost:8080/powerauth-java-server/rest/v3/application/create | json_pp

Output will look like this:

  "status": "OK",
  "responseObject": {
    "applicationId": 1,
    "applicationName": "demo-application",
    "applicationRoles": []

Tip: Note the json_pp command in the end - it formats the JSON output of the API call to a more readable format.

You can obtain full application details (in our case, the application ID is equal to 1, as per the previous call) by calling:

curl -s -H "Content-Type: application/json" -X POST \
    -d '{ "requestObject": { "applicationId": 1 } }' \
    http://localhost:8080/powerauth-java-server/rest/v3/application/detail | json_pp

Output will look like this:

  "status" : "OK",
  "responseObject" : {
    "versions" : [
        "applicationSecret" : "8N4AxX7Cyiqz1mN0sgjnjQ==",
        "applicationKey" : "xKm5Okqf7gM075d0uOvFMw==",
        "supported" : true,
        "applicationVersionId" : 1,
        "applicationVersionName" : "default"
    "applicationId" : 1,
    "applicationRoles" : [],
    "masterPublicKey" : "BJQ8G+0UoX08RvrU/9rOGtEDiiwZB28mk54hfPxXiImdqUQhIsHkfnYIfp64Zs52xsoDFIznvz01PNCPy79NC9w=",
    "applicationName" : "demo-application"

You need to pay attention to the following keys:

  • responseObject.masterPublicKey
  • responseObject.versions[0].applicationKey
  • responseObject.versions[0].applicationSecret

Provide these values to the mobile application developer.

You can now disconnect from the Docker container and review the impact of these steps on the database. You should see changes in the following tables:

  • pa_application - New record for your application.
  • pa_application_version - New record for the application version.
  • pa_master_keypair - New record for the master key pair related to the application.

You can read more about those tables in the PowerAuth Server database reference documentation.

Creating API User Credentials

When calling APIs provided by the PowerAuth Cloud application from various systems, basic HTTP authentication is required. This why we need to add users (which, in this case, are basically server applications calling the PowerAuth Cloud APIs) and their passwords in the database. We also need to assign access to the particular PowerAuth application created in the previous step.

First, we need to decide on the username value. Use some technical value that clearly represents some particular application connected to the APIs, such as internet-banking. Now, we need to generate the user password.

A good way to generate the password is via openssl:

openssl rand -base64 12

Output will look like this:


Do not forget to keep this password so that you can set it to the internet-banking application. However, in order to store the password in the database, we need to encode it using bcrypt first. You can use the htpasswd command tp achieve this:

htpasswd -bnBC 12 "" 0k4Vyn4A87VtOkEG | tr -d ':'

Output will look like this:


You can now put this all together and store the user in the database:

INSERT INTO pa_cloud_user (id, username, password, enabled)
VALUES (1, 'internet-banking', '$2y$12$Z518q.eUxqYO.KnIfr72aOVjWXcclNjfsYyMGh9upsg.Gv2menrTK', true);

INSERT INTO pa_cloud_user_authority (id, user_id, authority)
VALUES (1, 1, 'USER');

INSERT INTO pa_cloud_user_application (id, username, app_id)
VALUES (1, 'internet-banking', 1);

Things to notice:

  • We used ID=1 for all record types, since the database is empty.
  • The app_id value is set to 1, since this is our PowerAuth application ID.
  • We stored the brypted password for the internet-banking user.

You can now check the changes in the database:

  • pa_cloud_user - New user record with the bcrypt-hashed password.
  • pa_cloud_user_authority - New user authority record.
  • pa_cloud_user_application - Assignment of internet-banking application to PowerAuth application with ID=1.

At this point, you can open http://localhost:8080/powerauth-cloud/ and use internet-banking as username and 0k4Vyn4A87VtOkEG, your password value respectively (plaintext) as the password.

Configuring Push Server Credentials

In order to configure the Push Server credentials, you need to first obtain the required value from Apple and Google.

To obtain APNS credentials for iOS apps, visit the Apple’s developer portal to find:

  • Key ID
  • Team ID
  • Your iOS app bundle (used as a “topic”)
  • Private key for push notifications (*.p8 file)

To obtain FCM credentials for Android, visit the Firebase Console by Google to find:

  • Project ID
  • Private key (stored in the full *.json file)

You can now set the values in the database by entering the data in push_app_credentials table. Since you need to work with the files, we recommend using some visual console for the SQL commands. Working with binary data is tricky and we do not need to be heroes.

The table schema is the following:

create table push_app_credentials (
  id integer not null constraint push_app_credentials_pkey primary key,
  app_id integer not null,
  ios_key_id varchar(255),
  ios_team_id varchar(255),
  ios_bundle varchar(255),
  ios_private_key varchar(255),
  android_project_id varchar(255),
  android_private_key bytea

Use the following values:

  • id = 1 (The first record in the table).
  • app_id = 1 (ID of our PowerAuth application).
  • ios_key_id = Key ID value from Apple Developer Portal.
  • ios_team_id = Team ID value from Apple Developer Portal.
  • ios_bundle = Bundle ID value from Apple Developer Portal (topic).
  • ios_private_key = Upload the full content of the *.p8 file with private key.
  • android_project_id = Project ID obtained from Firebase Console.
  • android_private_key = Upload the full content of the *.json file with private key.

Configuring Push Server Callback

To make sure Push Server is notified about registration status change whenever it happens, we recommend adding the following callback URL to the database:

INSERT INTO pa_application_callback (id, application_id, name, callback_url, attributes)
VALUES (uuid_generate_v4(), 1, 'push-server', 'http://localhost:8080/powerauth-push-server/push/device/status/update', '["activationId","activationStatus"]');

Configuring Operations Templates

Finally, you need to configure the templates used while working with operations. The operation templates are technically stored in three separate tables.

Operation Template

The pa_operation_template table contains templates used for signing. The template is rather technical. The values are not visible to the end user but they are a critical part of the underlying cryptography. Let’s create two operations for the start: login and payment approval.

INSERT INTO pa_operation_template (id, template_name, operation_type, data_template, signature_type, max_failure_count, expiration)
VALUES (1, 'login', 'login', 'A2', 'possession_knowledge,possession_biometry', 5, 300);

INSERT INTO pa_operation_template (id, template_name, operation_type, data_template, signature_type, max_failure_count, expiration)
VALUES (2, 'payment', 'authorize_payment', 'A1*A${amount}${currency}*I${iban}', 'possession_knowledge,possession_biometry', 5, 300);

Of course, you can insert many other operation types, and even the same operation types with different template name (for example, to create payment type that does not allow biometric authentication used for any riskier payment types).

Operation data column uses a specially defined format shared accross all Wultra components. In the PowerAuth Cloud database definition, you can use named variables in the operation data to bind resulting signature with specific attributes of a particular operation. The syntax for the variables is ${name}. As you can see, the operation data for payment contains three named variables: amount, currency and iban, resulting in the A1*A${amount}${currency}*I${iban} data.

To disable biometry for a particular operation, use just possession_knowledge in the signature_type column.

Operation Summary Localization

You can easily localize operation summary (used for the push messages sent through the system, and for offline approvals) by adding localization records for the particular templates. You need to provide at least English localization (en), any other localizations are optional, non-existing localizations will fallback to English keys.

To create English localization for the two operations we created earlier, run the following script:

INSERT INTO pa_cloud_localization (id, placeholder, language, title, summary)
VALUES (1, 'login', 'en', 'Approve Login', 'Please confirm the login request.');

INSERT INTO pa_cloud_localization (id, placeholder, language, title, summary)
VALUES (2, 'payment', 'en', 'Approve Payment', 'Please approve the payment of ${amount} ${currency} to account ${iban}.');

Just as with operation templates, you can use named variables in the localizable strings to display the important values to the user (in both title and summary). The syntax for the variables is ${name}. As you can see, the payment approval summary again contains the three named variables: amount, currency and iban.

Mobile Token Operation Localization

When mobile token requests the list of operations that are pending approval, additional attributes can be rendered to the end user. To define precise looks of the particular operation, you need to configure the localized mobile API operation template.

Again, you need to provide at least the English localization. Also, note that the operations are addressed not by a template name at this level, but by the operation type.

We will create the data for the operations we created earlier.

INSERT INTO es_operation_template (id, placeholder, language, title, message, attributes)
VALUES (1, 'login', 'en', 'Login Approval', 'Are you logging in to the internet banking?', null);

INSERT INTO es_operation_template (id, placeholder, language, title, message, attributes)
VALUES (2, 'authorize_payment', 'en', 'Payment Approval', 'Please confirm the payment', '[
    "id": "operation.amount",
    "type": "AMOUNT",
    "text": "Amount",
    "params": {
      "amount": "amount",
      "currency": "currency"
    "id": "operation.account",
    "type": "KEY_VALUE",
    "text": "To Account",
    "params": {
      "value": "iban"

Most of the columns in the table are straight forward. The only complex column is the last one - the attributes column. It is a JSON serialized array of object that define attributes that are rendered in the mobile app. The object structure is the following:

  • id - ID of the attribute.
  • type - Type of the attribute.
  • text - The text (localized) that will be displayed as the attribute static text in the mobile app.
  • params - Attribute parameters, differ according to the type. Note that the parameters only define what names of operation named variables are assigned to particular attribute. For example, if you create payments with named variable iban, the value parameter of the KEY_VALUE attribute is set to iban.

The following attribute types are supported:

  • AMOUNT - Represent the amount of money, for example during a money transfer. It has two parameters: amount and currency.
  • HEADING - Represent the static text heading, does not have any parameters.
  • KEY_VALUE - Represent the key-value attribute displayed on a single line. It has one parameter value.
  • NOTE - Represent the key-value attribute displayed on multiple lines. It has one parameter note.

REST API Configuration

The version of REST API which is published is controlled using following configuration property:
Version Default Description
v2 true Multi-Device REST API, multiple device registrations per user are allowed.
v1 false Single-Device REST API, only one device registration per user is allowed.
Last updated on Mar 15, 2022 (17:03) View product


PowerAuth Cloud