Skip to main content

API Integration

sslTrus provides a remote code signing API, suitable for developers who need to build their own signing clients, build systems, or other signing integration programs.

The API receives the file digest computed by the client, uses the specified code signing certificate to complete private key signing through the remote code signing service, and returns the signing result.

The client is responsible for:

  • Computing the digest of the data to be signed.
  • Constructing the signature structure required by the target file.
  • Calling the remote signing API.
  • Writing the returned signing result into the target file or signature structure.
  • Reporting the client's final processing result as needed.

The code signing private key is always stored in the cloud HSM and will never be returned to the client through the API.

Access Endpoint

Default production environment address:

https://ssl.face.racent.com

NICSRS environment:

https://ssl.face.nicsrs.com

Complete signature interface:

POST https://ssl.face.racent.com/v1/codesign/sign

Result reporting interface:

POST https://ssl.face.racent.com/v1/codesign/report-sign

If the actual deployment environment uses a different service address, use the address provided by the delivery or operations team.

Authentication

The API uses HTTP Basic Auth.

Mapping:

Username = Access Key
Password = Access Secret

Request Header:

Authorization: Basic <base64(accessKey:accessSecret)>

For example:

printf "%s:%s" "$ACCESS_KEY:$ACCESS_SECRET" | base64

When actually using curl, you can provide it directly through the -u parameter:

curl -u "$ACCESS_KEY:$ACCESS_SECRET"

Access Secret is a sensitive credential and should not be written into source code, public configuration files, logs, or front-end pages.

General Request Format

The API uses:

HTTPS
POST
JSON

Request headers:

Content-Type: application/json
Accept: application/json
Authorization: Basic <credentials>

Common Response Format

The API returns a unified JSON structure:

{
"code": 0,
"message": "ok",
"data": {}
}

Field descriptions:

FieldTypeDescription
codeintegerBusiness status code. 0 indicates success.
messagestringStatus or error message
dataobjectBusiness data returned by the API

The client needs to check both the HTTP status code and the business status code.

We recommend handling this as follows:

HTTP 非 2xx

HTTP 请求失败

HTTP 2xx + code != 0

业务失败

HTTP 2xx + code == 0

读取 data

Do not judge the success of a signing request solely based on HTTP 200.

Signing API

API:

POST /v1/codesign/sign

This interface is used to submit the digest to be signed and obtain the remote private key signing result.

Request Parameters

Request example:

{
"code": "CERT_CODE",
"digest": "BASE64_ENCODED_HASH",
"algorithm": "SHA256",
"padding": "PKCS1",
"extra": {
"platform": "windows/amd64",
"version": "1.0.0",
"revision": "abcdef0",
"time": "2026-06-12T10:00:00+08:00",
"hostname": "build-host-01",
"signing_filename": "Example.exe",
"signing_filesize": 1048576
}
}

Main parameters:

ParameterTypeRequiredDescription
codestringYesCode signing certificate ID
digeststringYesBase64 encoding of the raw bytes of the digest to be signed
algorithmstringYesDigest algorithm
paddingstringYesRSA padding mode, currently fixed as PKCS1
extraobjectNoClient context and audit information

Digest Algorithms

Currently supported:

SHA1
SHA256
SHA384
SHA512

For example, when using SHA-256:

{
"algorithm": "SHA256"
}

algorithm must be consistent with the digest algorithm actually used by digest.

digest format

digest must be:

Hash raw bytes → Base64

No.

文件内容 Base64

Neither is it:

十六进制哈希字符串

For example, if a SHA-256 digest itself is 32 bytes, you should Base64-encode these 32 raw bytes and then pass them to the API.

padding

Currently fixed to:

PKCS1

That is:

{
"padding": "PKCS1"
}

Do not pass in other padding methods.

extra

extra is used to record client context, audit information, and assist with troubleshooting.

Supports:

FieldTypeDescription
platformstringClient platform
versionstringClient version
revisionstringClient build revision
timestringBuild time or request-side recorded time
hostnamestringHostname that initiated the request
signing_filenamestringSigned file name or local path
signing_filesizeintegerFile size in bytes

For example:

{
"extra": {
"platform": "linux/amd64",
"version": "1.2.0",
"hostname": "github-runner-01",
"signing_filename": "app.exe",
"signing_filesize": 5242880
}
}

If the signing_filename contains internal directories, usernames, or other sensitive information, it is recommended to apply masking based on the customer-side security policy.

Signature Request Example

Using curl:

curl -u "$ACCESS_KEY:$ACCESS_SECRET" \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
-d '{
"code": "CERT_CODE",
"digest": "BASE64_ENCODED_HASH",
"algorithm": "SHA256",
"padding": "PKCS1",
"extra": {
"platform": "linux/amd64",
"version": "1.0.0",
"hostname": "build-host-01",
"signing_filename": "Example.exe",
"signing_filesize": 1048576
}
}' \
https://ssl.face.racent.com/v1/codesign/sign

Signature Response

Success response:

{
"code": 0,
"message": "ok",
"data": {
"id": "735985894427246592",
"signature": "BASE64_ENCODED_SIGNATURE"
}
}

Returned fields:

FieldTypeDescription
idstringSignature record ID
signaturestringBase64 encoding of the RSA signature result

For actual signing capabilities, the client primarily uses:

data.signature

If you need to report the final status after processing locally, you also need to save:

data.id

Client-Side Processing Flow

Typical flow:

读取待签名文件

按照目标格式生成待签名数据

计算摘要

Base64 编码摘要

POST /v1/codesign/sign

获得 signature

构造最终签名结构

写回目标文件

POST /v1/codesign/report-sign

Note:

/v1/codesign/sign

Only responsible for the underlying remote private key signing.

How PE Authenticode, JAR, PDF, or other file formats organize the signature structure is handled by the client according to the target format.

Report signing results

Interface:

POST /v1/codesign/report-sign

After the client receives the remote signing result, failures may still occur in subsequent processes, such as:

  • Failure to construct the final signature structure.
  • Failure to write to the target file.
  • Incorrect local file permissions.
  • Subsequent client processing exceptions.

You can use this API to report the final processing status back to the server.

Request Parameters

{
"id": "735985894427246592",
"status": 1
}

Parameters:

FieldTypeRequiredDescription
idstringYesThe signature record ID returned by /v1/codesign/sign
statusintegerYesThe final processing status on the client

Status values:

StatusDescription
1The client processed successfully
2The client failed to process

Request Example

curl -u "$ACCESS_KEY:$ACCESS_SECRET" \
-H "Content-Type: application/json" \
-H "Accept: application/json" \
-d '{
"id": "735985894427246592",
"status": 1
}' \
https://ssl.face.racent.com/v1/codesign/report-sign

Success Response

{
"code": 0,
"message": "ok",
"data": null
}

Number of Signatures

The number of API signatures is determined by whether the remote signing operation is successful.

When:

HTTP 2xx
code == 0
data.signature 非空

When both conditions are met simultaneously, it is considered a successful signature:

签名次数 +1

The following situations do not consume signature quota:

  • Authentication failure.
  • Parameter errors.
  • Network request failure.
  • Business request failure.
  • The server does not successfully return the signature content.

Special attention is required:

/v1/codesign/report-sign

It only reports the final processing status of the client. It does not constitute a new signing operation, nor does it increase or decrease the signing count.

Even if the client has successfully obtained the remote signing result but then fails to write the file locally, the previously completed remote private key signing has still generated one signing count.

For more counting rules, please refer to Reference Materials.

Error Handling

The client should handle the following separately:

  1. Network errors.
  2. HTTP errors.
  3. API business errors.
  4. Client-side local processing errors.

Authentication Failure

For example:

{
"code": 401,
"message": "unauthorized",
"data": null
}

Should check:

  • Whether the Access Key is correct.
  • Whether the Access Secret is correct.
  • Whether the request correctly carries the Authorization Header.

Parameter error

For example:

{
"code": 400,
"message": "invalid request",
"data": null
}

Focus on checking:

  • Whether code is correct.
  • Whether digest is valid Base64.
  • Whether algorithm matches the summary.
  • Whether padding is PKCS1.

The client should not rely on fixed:

message

Strings execute program logic.

Business processing should prioritize status codes and interface contracts.

Timeouts and Retries

When calling remote signing interfaces, configure reasonable network timeouts.

When retries are needed, pay special attention to:

签名接口不是普通查询接口

If the client does not receive a response due to a network exception, it does not necessarily mean that the server did not complete the signing.

Therefore, when designing an automatic retry mechanism, avoid unlimited or unconditional repeated signing requests.

It is recommended to record the following separately:

  • Request start time.
  • Target certificate number.
  • Digest identifier.
  • HTTP status.
  • Business status code.
  • Returned signing record ID.
  • Client's final processing status.

Do not record the complete Access Secret in logs.

Logging and Auditing

It is recommended to record necessary signing context, for example:

certificate code
platform
client version
hostname
filename
filesize
sign record id
result

For:

digest
signature

For data of this length, it is not recommended to write the complete content into regular logs.

You may record:

  • Length.
  • Hash.
  • Masked prefix and suffix.

File paths may also contain usernames, project names, or internal directory information, and should be masked according to actual security requirements.

Security Notes

The following principles are recommended for API integration:

  • Access Secret should not be stored in frontend code.
  • Access Secret should not be committed to Git repositories.
  • Do not record the complete Authorization Header in regular logs.
  • Do not record the complete Access Secret.
  • Apply necessary log masking to digest and signature.
  • Call the remote signing service over HTTPS.
  • The client should validate HTTP status and business status.
  • Set reasonable timeout and retry policies for network requests.

The remote code signing API returns the signing result, not the private key.

The code signing private key always remains in the remote HSM.

When to Use the API

If the existing integration method already meets your needs, you can usually use the corresponding tool directly.

ScenarioRecommended Approach
Direct signing of EXE, DLL, MSI, and other filesClient Tool
Windows software such as Microsoft SignTool, Visual Studio, etc.Windows Provider
JAR file signingJava Integration
Automated builds such as GitHub Actions, Electron Builder, etc.CI/CD and Build Tools
Developing your own signing clientAPI
Implementing a custom file format signing processAPI
Needing direct control over digest and signing resultAPI

The API is more suitable for developers who need to control the underlying signing process.

If you only need code signing for regular files, using existing clients or standard Providers first can reduce the effort of handling signing file formats yourself.