Membuat tanda tangan

Panduan ini menjelaskan cara membuat tanda tangan, serta kolom wajib dan opsional untuk tanda tangan.

Untuk membuat tanda tangan, Anda harus membuat string yang akan ditandatangani, yang kami sebut sebagai nilai yang ditandatangani dalam panduan ini. Nilai yang ditandatangani mencakup parameter yang mendeskripsikan konten yang Anda lindungi, waktu habis masa berlaku nilai yang ditandatangani, dan sebagainya.

Anda menggunakan nilai yang ditandatangani saat membuat string tanda tangan. Anda membuat string tanda tangan dengan menyusun parameter untuk tanda tangan, seperti tanda tangan Ed25519 kunci asimetris dari nilai yang ditandatangani.

Media CDN menggunakan tanda tangan yang disusun akhir untuk membantu melindungi konten Anda.

Format penandatanganan yang didukung

Media CDN mendukung format permintaan yang ditandatangani berikut.

Format Perilaku Contoh
Parameter kueri (URL persis)

URL persis, untuk memberikan akses ke URL tertentu.

Persis:

https://media.example.com/content/manifest.m3u8?
Expires=EXPIRATION
&KeyName=KEY_NAME
&Signature=SIGNATURE

Parameter kueri (awalan URL) Dengan menentukan URLPrefix, Anda dapat menandatangani awalan dan menambahkan parameter kueri yang sama ke beberapa URL dalam pembuatan pemain atau manifes.

Yang harus ditandatangani:

URLPrefix=PREFIX
&Expires=EXPIRATION
&KeyName=KEY_NAME
&Signature=SIGNATURE

Ganti PREFIX dengan awalan untuk memberikan akses ke, termasuk skema, host, dan jalur sebagian.

Komponen jalur

Awalan: memungkinkan akses ke URL apa pun dengan awalan sebelum komponen "/edge-cache-token=[...]".

Hal ini memungkinkan URL manifes relatif otomatis mewarisi komponen URL yang ditandatangani saat mengambil sub-resource.

https://media.example.com/video/edge-cache-token=Expires=EXPIRATION
&KeyName=KEY_NAME
&Signature=SIGNATURE/manifest_12382131.m3u8
Cookie bertanda tangan Awalan: cookie mengizinkan akses ke URL apa pun dengan awalan yang ditentukan dalam nilai URLPrefix yang ditandatangani.

Edge-Cache-Cookie:

URLPrefix=PREFIX:
Expires=EXPIRATION:
KeyName=KEY_NAME:
Signature=SIGNATURE

Membuat tanda tangan

  1. Buat nilai yang ditandatangani dengan menggabungkan string yang berisi kolom tanda tangan yang diperlukan dan kolom tanda tangan opsional yang diinginkan.

    Jika ditentukan, URLPrefix harus muncul terlebih dahulu, diikuti dengan Expires, KeyName, lalu parameter opsional apa pun.

    Pisahkan setiap kolom dan parameter dengan hal berikut:

    • Untuk cookie, gunakan karakter titik dua :.
    • Untuk parameter kueri dan komponen jalur, gunakan karakter ampersand &.
  2. Tanda tangani nilai yang ditandatangani dengan tanda tangan Ed25519.

  3. Tambahkan pemisah kolom (: atau &) diikuti dengan Signature= dan tanda tangan Ed25519 ke akhir string.

Membuat URL yang ditandatangani

Contoh kode berikut menunjukkan cara membuat URL yang ditandatangani secara terprogram.

Go

Untuk mengautentikasi ke Media CDN, siapkan Kredensial Default Aplikasi. Untuk mengetahui informasi selengkapnya, baca Menyiapkan autentikasi untuk lingkungan pengembangan lokal.

import (
	"crypto/ed25519"
	"encoding/base64"
	"fmt"
	"io"
	"strings"
	"time"
)

// signURL prints the signed URL string for the specified URL and configuration.
func signURL(w io.Writer, url, keyName string, privateKey []byte, expires time.Time) error {
	// url := "http://example.com"
	// keyName := "your_key_name"
	// privateKey := "[]byte{34, 31, ...}"
	// expires := time.Unix(1558131350, 0)

	sep := '?'
	if strings.ContainsRune(url, '?') {
		sep = '&'
	}
	toSign := fmt.Sprintf("%s%cExpires=%d&KeyName=%s", url, sep, expires.Unix(), keyName)
	sig := ed25519.Sign(privateKey, []byte(toSign))

	fmt.Fprintf(w, "%s&Signature=%s", toSign, base64.RawURLEncoding.EncodeToString(sig))

	return nil
}

Python

Untuk mengautentikasi ke Media CDN, siapkan Kredensial Default Aplikasi. Untuk mengetahui informasi selengkapnya, baca Menyiapkan autentikasi untuk lingkungan pengembangan lokal.

import base64
import datetime

import cryptography.hazmat.primitives.asymmetric.ed25519 as ed25519


from six.moves import urllib

def sign_url(
    url: str, key_name: str, base64_key: str, expiration_time: datetime.datetime
) -> str:
    """Gets the Signed URL string for the specified URL and configuration.

    Args:
        url: URL to sign as a string.
        key_name: name of the signing key as a string.
        base64_key: signing key as a base64 encoded byte string.
        expiration_time: expiration time as a UTC datetime object.

    Returns:
        Returns the Signed URL appended with the query parameters based on the
        specified configuration.
    """
    stripped_url = url.strip()
    parsed_url = urllib.parse.urlsplit(stripped_url)
    query_params = urllib.parse.parse_qs(parsed_url.query, keep_blank_values=True)
    epoch = datetime.datetime.utcfromtimestamp(0)
    expiration_timestamp = int((expiration_time - epoch).total_seconds())
    decoded_key = base64.urlsafe_b64decode(base64_key)

    url_pattern = "{url}{separator}Expires={expires}&KeyName={key_name}"

    url_to_sign = url_pattern.format(
        url=stripped_url,
        separator="&" if query_params else "?",
        expires=expiration_timestamp,
        key_name=key_name,
    )

    digest = ed25519.Ed25519PrivateKey.from_private_bytes(decoded_key).sign(
        url_to_sign.encode("utf-8")
    )
    signature = base64.urlsafe_b64encode(digest).decode("utf-8")
    signed_url = "{url}&Signature={signature}".format(
        url=url_to_sign, signature=signature
    )

    return signed_url

Membuat awalan URL yang ditandatangani

Contoh kode berikut menunjukkan cara membuat awalan URL yang ditandatangani secara terprogram.

Go

Untuk mengautentikasi ke Media CDN, siapkan Kredensial Default Aplikasi. Untuk mengetahui informasi selengkapnya, baca Menyiapkan autentikasi untuk lingkungan pengembangan lokal.

import (
	"crypto/ed25519"
	"encoding/base64"
	"fmt"
	"io"
	"strings"
	"time"
)

// signURLPrefix prints the signed URL string for the specified URL prefix and configuration.
func signURLPrefix(w io.Writer, urlPrefix, keyName string, privateKey []byte, expires time.Time) error {
	// urlPrefix := "https://examples.com"
	// keyName := "your_key_name"
	// privateKey := "[]byte{34, 31, ...}"
	// expires := time.Unix(1558131350, 0)

	sep := '?'
	if strings.ContainsRune(urlPrefix, '?') {
		sep = '&'
	}

	toSign := fmt.Sprintf(
		"URLPrefix=%s&Expires=%d&KeyName=%s",
		base64.RawURLEncoding.EncodeToString([]byte(urlPrefix)),
		expires.Unix(),
		keyName,
	)
	sig := ed25519.Sign(privateKey, []byte(toSign))

	fmt.Fprintf(
		w,
		"%s%c%s&Signature=%s",
		urlPrefix,
		sep,
		toSign,
		base64.RawURLEncoding.EncodeToString(sig),
	)

	return nil
}

Python

Untuk mengautentikasi ke Media CDN, siapkan Kredensial Default Aplikasi. Untuk mengetahui informasi selengkapnya, baca Menyiapkan autentikasi untuk lingkungan pengembangan lokal.

import base64
import datetime

import cryptography.hazmat.primitives.asymmetric.ed25519 as ed25519


from six.moves import urllib

def sign_url_prefix(
    url: str,
    url_prefix: str,
    key_name: str,
    base64_key: str,
    expiration_time: datetime.datetime,
) -> str:
    """Gets the Signed URL string for the specified URL prefix and configuration.

    Args:
        url: URL of request.
        url_prefix: URL prefix to sign as a string.
        key_name: name of the signing key as a string.
        base64_key: signing key as a base64 encoded string.
        expiration_time: expiration time as a UTC datetime object.

    Returns:
        Returns the Signed URL appended with the query parameters based on the
        specified URL prefix and configuration.
    """
    stripped_url = url.strip()
    parsed_url = urllib.parse.urlsplit(stripped_url)
    query_params = urllib.parse.parse_qs(parsed_url.query, keep_blank_values=True)
    encoded_url_prefix = base64.urlsafe_b64encode(
        url_prefix.strip().encode("utf-8")
    ).decode("utf-8")
    epoch = datetime.datetime.utcfromtimestamp(0)
    expiration_timestamp = int((expiration_time - epoch).total_seconds())
    decoded_key = base64.urlsafe_b64decode(base64_key)

    policy_pattern = (
        "URLPrefix={encoded_url_prefix}&Expires={expires}&KeyName={key_name}"
    )
    policy = policy_pattern.format(
        encoded_url_prefix=encoded_url_prefix,
        expires=expiration_timestamp,
        key_name=key_name,
    )

    digest = ed25519.Ed25519PrivateKey.from_private_bytes(decoded_key).sign(
        policy.encode("utf-8")
    )
    signature = base64.urlsafe_b64encode(digest).decode("utf-8")
    signed_url = "{url}{separator}{policy}&Signature={signature}".format(
        url=stripped_url,
        separator="&" if query_params else "?",
        policy=policy,
        signature=signature,
    )
    return signed_url

Contoh kode berikut menunjukkan cara membuat cookie URL yang ditandatangani secara terprogram.

Membuat komponen jalur yang ditandatangani

Contoh kode berikut menunjukkan cara membuat komponen jalur yang ditandatangani secara terprogram.

Python

Untuk mengautentikasi ke Media CDN, siapkan Kredensial Default Aplikasi. Untuk mengetahui informasi selengkapnya, baca Menyiapkan autentikasi untuk lingkungan pengembangan lokal.

import base64
import datetime
import hashlib
import hmac

import cryptography.hazmat.primitives.asymmetric.ed25519 as ed25519


def base64_encoder(value: bytes) -> str:
    """
    Returns a base64-encoded string compatible with Media CDN.

    Media CDN uses URL-safe base64 encoding and strips off the padding at the
    end.
    """
    encoded_bytes = base64.urlsafe_b64encode(value)
    encoded_str = encoded_bytes.decode("utf-8")
    return encoded_str.rstrip("=")


def sign_path_component(
    url_prefix: str,
    filename: str,
    key_name: str,
    base64_key: str,
    expiration_time: datetime.datetime,
) -> str:
    """Gets the Signed URL string for the specified URL prefix and configuration.

    Args:
        url_prefix: URL Prefix to sign as a string.
        filename: The filename of the sample request
        key_name: The name of the signing key as a string.
        base64_key: The signing key as a base64 encoded string.
        expiration_time: Expiration time as a UTC datetime object with timezone.

    Returns:
        Returns the Signed URL appended with the query parameters based on the
        specified URL prefix and configuration.
    """

    expiration_duration = expiration_time.astimezone(
        tz=datetime.timezone.utc
    ) - datetime.datetime.fromtimestamp(0, tz=datetime.timezone.utc)
    decoded_key = base64.urlsafe_b64decode(base64_key)

    policy_pattern = "{url_prefix}edge-cache-token=Expires={expires}&KeyName={key_name}"
    policy = policy_pattern.format(
        url_prefix=url_prefix,
        expires=int(expiration_duration.total_seconds()),
        key_name=key_name,
    )

    digest = ed25519.Ed25519PrivateKey.from_private_bytes(decoded_key).sign(
        policy.encode("utf-8")
    )
    signature = base64_encoder(digest)

    signed_url = "{policy}&Signature={signature}/{filename}".format(
        policy=policy, signature=signature, filename=filename
    )

    return signed_url

Kolom tanda tangan yang wajib diisi

Kolom berikut wajib diisi untuk setiap tanda tangan:

  • Expires
  • KeyName
  • Signature

Jika ada, parameter kueri harus dikelompokkan bersama sebagai parameter terakhir di URL. Kecuali ditentukan lain, nama parameter dan nilainya peka huruf besar/kecil.

Tabel berikut menjelaskan setiap parameter:

Nama kolom Parameter tanda tangan Nilai yang ditandatangani
Expires Detik bilangan bulat yang telah berlalu sejak epoch Unix (1970-01-01T00:00:00Z) Expires=EXPIRATION_TIME, setelah itu tanda tangan tidak lagi valid.
KeyName Nama EdgeCacheKeyset yang digunakan untuk menandatangani permintaan ini. KeyName mengacu pada seluruh kumpulan kunci, bukan kunci individual dalam kumpulan kunci itu sendiri. KeyName=EDGE_CACHE_KEYSET
Signature Versi tanda tangan yang dienkode base-64. Tidak berlaku

Kolom tanda tangan opsional

Jika ada, parameter kueri harus dikelompokkan bersama sebagai parameter terakhir di URL. Kecuali ditentukan lain, nama parameter dan nilainya peka huruf besar/kecil.

Tabel berikut menjelaskan nama dan detail setiap parameter untuk parameter tanda tangan opsional:

Nama kolom Parameter tanda tangan Nilai yang ditandatangani
HeaderName

Nama kolom header permintaan yang harus ada dalam permintaan.

Harus menggunakan huruf kecil saat ditandatangani karena nama kolom header peka huruf besar/kecil. Media CDN mengubah header menjadi huruf kecil sebelum memvalidasi tanda tangan.

HeaderName=HEADER_NAME
HeaderValue Nilai kolom header permintaan bernama yang harus ada dalam permintaan. Ini biasanya berupa ID pengguna atau ID buram lainnya. Permintaan dengan HeaderValue, tetapi tanpa HeaderName, akan ditolak. HeaderValue=HEADER_VALUE
IPRanges

Daftar hingga lima alamat IPv4 dan IPv6 dalam format CIDR yang valid untuk URL ini dalam format base64 yang aman untuk web. Misalnya, untuk menentukan rentang IP "192.6.13.13/32,193.5.64.135/32", Anda menentukan IPRanges=MTkyLjYuMTMuMTMvMzIsMTkzLjUuNjQuMTM1LzMy.

IPRanges mungkin tidak membantu untuk disertakan dalam tanda tangan jika klien berisiko terkena migrasi WAN atau kasus saat jalur jaringan ke front-end aplikasi Anda berbeda dengan jalur pengiriman. Media CDN menolak klien dengan kode HTTP 403 saat mereka terhubung dengan alamat IP yang bukan bagian dari permintaan yang ditandatangani.

Berikut adalah kasus yang dapat menyebabkan Media CDN menolak klien dengan kode HTTP 403:

  • Lingkungan stack ganda (IPv4, IPv6)
  • Migrasi koneksi (Wi-Fi ke seluler, dan seluler ke Wi-Fi)
  • Jaringan seluler yang menggunakan NAT Gateway Operator (CGNAT atau CGN)
  • Multi-jalur TCP (MPTCP)

Semua faktor ini dapat berkontribusi pada klien tertentu yang memiliki alamat IP non-deterministik selama sesi pemutaran video. Jika alamat IP klien berubah setelah Anda memberikan akses, dan klien mencoba mendownload segmen video ke buffering pemutaran, klien akan menerima HTTP 403 dari Media CDN.

IPRanges=BASE_64_IP_RANGES
URLPrefix Awalan URL base64 (aman untuk URL) yang akan diberi akses. Dengan menentukan URLPrefix, Anda dapat menandatangani awalan dan menambahkan parameter kueri yang sama ke beberapa URL dalam pembuatan manifes atau pemutar. URLPrefix diperlukan saat menggunakan format cookie yang ditandatangani. URLPrefix=BASE_64_URL_PREFIX