Console
Taqlyn Docs/Requirements/Credentials & SDK Authentication Specification
API v1.46 min read

Credentials & SDK Authentication Specification

Cryptographic specification for client public keys, server Ed25519 request signing, and SDK configuration.

LIVE SPECIMEN
Universal & Deferred Link Simulator
URLhttps://taqlyn.com/shop/checkout?cartId=cart_9841&promo=WELCOME20&aff=partner_8
Route: /shop/checkoutMode: Deferred Install

Taqlyn enforces an asymmetric Ed25519 cryptographic security model. Traditional deep linking providers rely on shared opaque secret tokens (sk_live_...) hashed with bcrypt or SHA-256. If a developer accidentally bundles that shared secret into an iOS or Android app, attackers can decompile the binary and mint arbitrary links or hijack traffic.

Taqlyn solves this permanently:

  1. Client / Mobile apps receive only public identifiers (client_id + public_key_id). They can resolve incoming links, but cannot forge signatures or perform mutating operations.
  2. Server backends sign administrative and link creation requests using an Ed25519 private key (PKCS#8 PEM). The private key is never stored by Taqlyn; incoming requests are validated against the stored public verifying key.

#Credential Roles Matrix

Credential ComponentTypeFormatTarget EnvironmentPermitted Operations
client_idPublic Identifierapp_test_<hex> / app_live_<hex>Mobile SDKs & Server SDKsApp identification, edge routing lookup
public_key_idPublic Key Handlepk_test_<hex> / pk_live_<hex>Mobile SDKs onlyLink resolution (POST /v1/resolve), user in-app sharing
private_keyEd25519 Private Key-----BEGIN PRIVATE KEY-----\n...Server SDKs onlyCreating short links (POST /v1/short-links), webhooks, admin APIs
sk_* handleReference Tokensk_test_<hex> / sk_live_<hex>Audit logs onlyTracking rotation history (cannot sign requests)

#Client SDK Integration Matrix

Every client SDK requires clientId and publicKeyId. Both are safe to commit to source control or embed into client binaries.

#1. Android (Kotlin) — taqlyn-sdk

Kotlin
// In your android.app.Application class
import com.taqlyn.sdk.SdkCore
import com.taqlyn.sdk.SdkOptions

class MyApplication : Application() {
    override fun onCreate() {
        super.onCreate()
        
        SdkCore.configure(
            clientId = "app_live_8f92ab140cd3",
            publicKeyId = "pk_live_a1b2c3d4e5f6",
            options = SdkOptions(
                env = "production", // "sandbox" or "production"
                linkProcessingMode = SdkOptions.Mode.ALL // ALL, WEB_ONLY, or DEFERRED_ONLY
            ),
            context = this
        )
    }
}
  • Permission Scope: Reads Google Play Install Referrer, catches App Links, and invokes POST /v1/resolve.
  • Reference: Android Platform Guide

#2. iOS (Swift) — TaqlynSDK

Swift
// In your SwiftUI App declaration or AppDelegate
import SwiftUI
import TaqlynSDK

@main
struct MyApp: App {
    init() {
        SdkCore.configure(
            clientId: "app_live_8f92ab140cd3",
            publicKeyId: "pk_live_a1b2c3d4e5f6",
            options: SdkOptions(env: .production)
        )
    }

    var body: some Scene {
        WindowGroup {
            ContentView()
                .onOpenURL { SdkCore.onOpenURL($0) }
                .task {
                    // Resolve deferred links upon first install
                    _ = await SdkCore.resolveDeferred()
                    SdkCore.setReadyForNavigation(true)
                }
        }
    }
}
  • Permission Scope: Reads pasteboard tokens (opt-in deferred), catches Universal Links, and invokes POST /v1/resolve.
  • Reference: iOS Platform Guide

#3. React Native (TypeScript) — @taqlyn/sdk-react-native

TypeScript
import { configure, resolveDeferred, setReadyForNavigation } from '@taqlyn/sdk-react-native';

// Configure public credentials across iOS and Android engines
configure('app_live_8f92ab140cd3', 'pk_live_a1b2c3d4e5f6', {
  env: 'production',
  linkProcessingMode: 'all',
});

// Resolve upon initial app mount
export async function initializeTaqlyn() {
  const link = await resolveDeferred();
  if (link) {
    console.log('Deferred deep link destination:', link.path, link.params);
  }
  setReadyForNavigation(true);
}

#4. Flutter (Dart) — taqlyn_sdk

Dart
import 'package:flutter/material.dart';
import 'package:taqlyn_sdk/taqlyn_sdk.dart';

void main() async {
  WidgetsFlutterBinding.ensureInitialized();

  await Taqlyn.configure(
    clientId: 'app_live_8f92ab140cd3',
    publicKeyId: 'pk_live_a1b2c3d4e5f6',
    env: 'production',
  );

  runApp(const MyApp());
}

#Server SDK Integration Matrix

Server SDKs sign HTTP requests with your Ed25519 Private Key. Configure them via environment variables on your backend.

#Standard Environment Variables

VariableDescription
TAQLYN_BASE_URLBase API URL (e.g. https://api.rutvik.qzz.io or your custom domain).
TAQLYN_CLIENT_IDApplication Client ID (app_test_* or app_live_*).
TAQLYN_PRIVATE_KEYPKCS#8 Ed25519 Private Key PEM (-----BEGIN PRIVATE KEY-----\n...).

#1. Node.js / TypeScript (@taqlyn/sdk-node)

TypeScript
import { TaqlynClient } from "@taqlyn/sdk-node";

const client = new TaqlynClient({
  baseUrl: process.env.TAQLYN_BASE_URL,
  clientId: process.env.TAQLYN_CLIENT_ID!,
  privateKey: process.env.TAQLYN_PRIVATE_KEY!,
});

const shortLink = await client.createShortLink({
  destinationWeb: "https://example.com/products/headphones",
  destinationPath: "/products/headphones",
  params: { utm_source: "newsletter", promo: "VIP10" },
  mode: "deferred_app",
  trackUniqueUsers: true,
  trackOpens: true,
});

console.log("Short URL:", shortLink.shortUrl);

#2. Python (taqlyn-sdk)

Python
import os
from taqlyn import TaqlynClient

client = TaqlynClient(
    base_url=os.getenv("TAQLYN_BASE_URL", "https://api.rutvik.qzz.io"),
    client_id=os.environ["TAQLYN_CLIENT_ID"],
    private_key=os.environ["TAQLYN_PRIVATE_KEY"],
)

link = client.create_short_link(
    destination_web="https://example.com/checkout",
    destination_path="/checkout",
    params={"coupon": "SPRING26"},
    mode="deferred_app",
)
print("Minted link:", link.short_url)

#3. Go (github.com/taqlyn/sdk-go)

Go
package main

import (
    "context"
    "os"
    "github.com/taqlyn/sdk-go"
)

func main() {
    client, err := taqlyn.NewClient(taqlyn.Config{
        BaseURL:    os.Getenv("TAQLYN_BASE_URL"),
        ClientID:   os.Getenv("TAQLYN_CLIENT_ID"),
        PrivateKey: os.Getenv("TAQLYN_PRIVATE_KEY"),
    })
    if err != nil {
        panic(err)
    }

    link, err := client.CreateShortLink(context.Background(), taqlyn.CreateLinkInput{
        DestinationWeb:  "https://example.com/offer",
        DestinationPath: "/offer",
        Mode:            "deferred_app",
    })
    println("Created link:", link.ShortURL)
}

#4. Java / Kotlin JVM (com.taqlyn:sdk)

JAVA
import com.taqlyn.sdk.TaqlynClient;
import com.taqlyn.sdk.model.CreateShortLinkRequest;

TaqlynClient client = TaqlynClient.builder()
    .clientId(System.getenv("TAQLYN_CLIENT_ID"))
    .privateKey(System.getenv("TAQLYN_PRIVATE_KEY"))
    .build();

var link = client.createShortLink(CreateShortLinkRequest.builder()
    .destinationWeb("https://example.com/deal")
    .destinationPath("/deal")
    .mode("deferred_app")
    .build());

#5. .NET / C# (Taqlyn.Sdk)

CSHARP
using Taqlyn;

var client = new TaqlynClient(new TaqlynOptions
{
    ClientId = Environment.GetEnvironmentVariable("TAQLYN_CLIENT_ID")!,
    PrivateKey = Environment.GetEnvironmentVariable("TAQLYN_PRIVATE_KEY")!,
});

var link = await client.CreateShortLinkAsync(new CreateShortLinkRequest
{
    DestinationWeb = "https://example.com/promo",
    DestinationPath = "/promo",
    Mode = "deferred_app",
});

#6. PHP (taqlyn/sdk-php)

PHP
use Taqlyn\TaqlynClient;

$client = new TaqlynClient([
    'client_id'   => getenv('TAQLYN_CLIENT_ID'),
    'private_key' => getenv('TAQLYN_PRIVATE_KEY'),
]);

$link = $client->createShortLink([
    'destination_web'  => 'https://example.com/item',
    'destination_path' => '/item',
    'mode'             => 'deferred_app',
]);

#7. Ruby (taqlyn)

RUBY
require 'taqlyn'

client = Taqlyn::Client.new(
  client_id: ENV['TAQLYN_CLIENT_ID'],
  private_key: ENV['TAQLYN_PRIVATE_KEY']
)

link = client.create_short_link(
  destination_web: 'https://example.com/catalog',
  destination_path: '/catalog',
  mode: 'deferred_app'
)

#Cryptographic Signed Request Protocol

If you are implementing a custom client or proxy, every request to privileged endpoints (POST/GET/PATCH/DELETE /v1/short-links) must provide three HTTP headers:

HTTP
X-Taqlyn-Client-Id: app_live_8f92ab140cd3
X-Taqlyn-Timestamp: 1725537600
X-Taqlyn-Signature: 6e98b2c41804... (128-char hex string)

#1. Canonical String Format

Construct the canonical message string as:

CODE
${timestamp}.${HTTP_METHOD}.${REQUEST_PATH}.${BODY_SHA256}
  • timestamp: Exact Unix time in seconds (1725537600).
  • HTTP_METHOD: Uppercase verb (POST, PATCH, DELETE).
  • REQUEST_PATH: URL path without query parameters (/v1/short-links).
  • BODY_SHA256: Hex-encoded SHA-256 digest of request body bytes. For empty bodies, use the hash of empty bytes (e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855).

#2. Signature Computation

Sign the UTF-8 bytes of the canonical string using your Ed25519 private key. Encode the resulting 64-byte signature as a lowercase hexadecimal string.

#3. Replay Protection Guard

The Taqlyn API gateway validates that: $$\left| \text{RequestTimestamp} - \text{ServerEpoch} \right| \le 300\text{ seconds}$$

Requests outside the ±300s skew window are rejected with credentials.timestamp_skew.


#Security Checklist

  • Client binaries never hold private keys: Only client_id and public_key_id are included in iOS, Android, React Native, and Flutter packages.
  • Private PEM stored in secrets managers: Store TAQLYN_PRIVATE_KEY in AWS Secrets Manager, GCP Secret Manager, Vault, or Kubernetes Secrets.
  • Environment Isolation: Always use sandbox credentials in CI and development environments.
  • Zero-Downtime Rotation: When rotating, roll backend servers first with the new PEM, then update mobile app releases.