Whiz Tools

Penyandi/Penyahkod Base64

Tukar teks kepada dan dari pengekodan Base64

Salin

Pengekod dan Penyahkod Base64

Pengenalan

Base64 adalah skema pengekodan binari-ke-teks yang mewakili data binari dalam format rentetan ASCII. Ia direka untuk membawa data yang disimpan dalam format binari merentasi saluran yang hanya menyokong kandungan teks dengan boleh dipercayai. Pengekodan Base64 menukarkan data binari menjadi satu set 64 watak (oleh itu namanya) yang boleh dihantar dengan selamat melalui protokol berasaskan teks tanpa kerosakan data.

Set watak Base64 terdiri daripada:

  • Huruf besar A-Z (26 watak)
  • Huruf kecil a-z (26 watak)
  • Digit 0-9 (10 watak)
  • Dua watak tambahan, biasanya "+" dan "/" (2 watak)

Alat ini membolehkan anda dengan mudah mengekod teks ke format Base64 atau menyahkod rentetan Base64 kembali kepada teks asalnya. Ia sangat berguna untuk pemaju, profesional IT, dan sesiapa yang bekerja dengan data yang perlu dihantar dengan selamat merentasi saluran berasaskan teks.

Cara Pengekodan Base64 Berfungsi

Proses Pengekodan

Pengekodan Base64 berfungsi dengan menukarkan setiap kumpulan tiga bait (24 bit) data binari menjadi empat watak Base64. Proses ini mengikuti langkah-langkah berikut:

  1. Tukar teks input kepada representasi binarinya (menggunakan pengekodan ASCII atau UTF-8)
  2. Kumpulkan data binari ke dalam segmen 24 bit (3 bait)
  3. Bahagikan setiap segmen 24 bit kepada empat kumpulan 6 bit
  4. Tukar setiap kumpulan 6 bit kepada watak Base64 yang sepadan

Apabila panjang input tidak boleh dibahagikan dengan 3, padding dengan watak "=" ditambah untuk mengekalkan nisbah 4:3 panjang output kepada input.

Perwakilan Matematik

Untuk urutan bait b1,b2,b3b_1, b_2, b_3, watak Base64 yang sepadan c1,c2,c3,c4c_1, c_2, c_3, c_4 dikira sebagai:

c1=Base64[(b1>>2)]c_1 = \text{Base64}[(b_1 >> 2)] c2=Base64[((b1&3)<<4)(b2>>4)]c_2 = \text{Base64}[((b_1 \& 3) << 4) | (b_2 >> 4)] c3=Base64[((b2&15)<<2)(b3>>6)]c_3 = \text{Base64}[((b_2 \& 15) << 2) | (b_3 >> 6)] c4=Base64[(b3&63)]c_4 = \text{Base64}[(b_3 \& 63)]

Di mana Base64[i]\text{Base64}[i] mewakili watak ke-ii dalam abjad Base64.

Proses Penyahkodan

Penyahkodan Base64 membalikkan proses pengekodan:

  1. Tukar setiap watak Base64 kepada nilai 6 bitnya
  2. Gabungkan nilai 6 bit ini
  3. Kumpulkan bit kepada kumpulan 8 bit (bait)
  4. Tukar setiap bait kepada watak yang sepadan

Padding

Apabila bilangan bait untuk dikodkan tidak boleh dibahagikan dengan 3, padding digunakan:

  • Jika terdapat satu bait yang tinggal, ia ditukarkan kepada dua watak Base64 diikuti dengan "=="
  • Jika terdapat dua bait yang tinggal, ia ditukarkan kepada tiga watak Base64 diikuti dengan "="

Contoh

Mari kita kodkan teks "Hello" ke Base64:

  1. Representasi ASCII bagi "Hello": 72 101 108 108 111
  2. Representasi binari: 01001000 01100101 01101100 01101100 01101111
  3. Pengelompokan kepada kumpulan 6 bit: 010010 000110 010101 101100 011011 000110 1111
  4. Kumpulan terakhir hanya mempunyai 4 bit, jadi kita tambah padding dengan nol: 010010 000110 010101 101100 011011 000110 111100
  5. Menukarkan kepada perpuluhan: 18, 6, 21, 44, 27, 6, 60
  6. Mencari dalam abjad Base64: S, G, V, s, b, G, 8
  7. Hasilnya adalah "SGVsbG8="

Perhatikan padding "=" di akhir kerana panjang input (5 bait) tidak boleh dibahagikan dengan 3.

Formula

Formula umum untuk mengira panjang rentetan yang dikodkan dalam Base64 adalah:

encoded_length=4×input_length3\text{encoded\_length} = 4 \times \lceil \frac{\text{input\_length}}{3} \rceil

Di mana x\lceil x \rceil mewakili fungsi siling (pembulatan ke atas kepada integer terdekat).

Kes Penggunaan

Pengekodan Base64 digunakan secara meluas dalam pelbagai aplikasi:

  1. Lampiran E-mel: MIME (Multipurpose Internet Mail Extensions) menggunakan Base64 untuk mengodkan lampiran binari dalam e-mel.

  2. URL Data: Menyematkan imej kecil, fon, atau sumber lain secara langsung dalam HTML, CSS, atau JavaScript menggunakan skema URL data:.

  3. Komunikasi API: Menghantar data binari dengan selamat dalam muatan JSON atau format API berasaskan teks lain.

  4. Menyimpan Data Binari dalam Format Teks: Apabila data binari perlu disimpan dalam XML, JSON, atau format berasaskan teks lain.

  5. Sistem Pengesahan: Pengesahan Asas dalam HTTP menggunakan pengekodan Base64 (walaupun ia bukan untuk keselamatan, hanya untuk pengekodan).

  6. Kriptografi: Sebagai sebahagian daripada pelbagai protokol dan sistem kriptografi, sering untuk mengekod kunci atau sijil.

  7. Nilai Cookie: Mengesahkan struktur data yang kompleks untuk disimpan dalam cookie.

Alternatif

Walaupun Base64 digunakan secara meluas, terdapat alternatif yang mungkin lebih sesuai dalam situasi tertentu:

  1. Base64 Selamat URL: Variasi yang menggunakan "-" dan "_" sebagai ganti "+" dan "/" untuk mengelakkan isu pengkodan URL. Berguna untuk data yang akan disertakan dalam URL.

  2. Base32: Menggunakan set 32 watak, menghasilkan output yang lebih panjang tetapi dengan kebolehan bacaan manusia yang lebih baik dan tidak sensitif kepada kes.

  3. Pengekodan Hex: Penukaran mudah kepada heksadesimal, yang kurang cekap (menggandakan saiz) tetapi sangat mudah dan banyak disokong.

  4. Pemindahan Binari: Untuk fail besar atau apabila kecekapan adalah penting, protokol pemindahan binari langsung seperti HTTP dengan header Content-Type yang sesuai adalah lebih baik.

  5. Pemampatan + Base64: Untuk data teks besar, memampatkan sebelum mengekod boleh mengurangkan peningkatan saiz.

  6. Penyusunan JSON/XML: Untuk data terstruktur, menggunakan penyusunan JSON atau XML asli mungkin lebih sesuai daripada pengekodan Base64.

Sejarah

Pengekodan Base64 mempunyai akar dalam sistem pengkomputeran awal dan sistem telekomunikasi di mana data binari perlu dihantar melalui saluran yang direka untuk teks.

Spesifikasi rasmi Base64 pertama kali diterbitkan pada tahun 1987 sebagai sebahagian daripada RFC 989, yang mendefinisikan E-mel yang Ditingkatkan Privasi (PEM). Ini kemudian dikemas kini dalam RFC 1421 (1993) dan RFC 2045 (1996, sebagai sebahagian daripada MIME).

Istilah "Base64" berasal dari hakikat bahawa pengekodan menggunakan 64 watak ASCII yang berbeza untuk mewakili data binari. Pilihan 64 watak ini adalah sengaja, kerana 64 adalah kuasa 2 (2^6), yang menjadikan penukaran antara binari dan Base64 cekap.

Seiring berjalannya waktu, beberapa variasi Base64 telah muncul:

  • Base64 Standard: Seperti yang ditakrifkan dalam RFC 4648, menggunakan A-Z, a-z, 0-9, +, / dan = untuk padding
  • Base64 Selamat URL: Menggunakan - dan _ sebagai ganti + dan / untuk mengelakkan isu pengkodan URL
  • Base64 Selamat Nama Fail: Serupa dengan Base64 selamat URL, direka untuk digunakan dalam nama fail
  • Base64 yang Diubahsuai untuk IMAP: Digunakan dalam protokol IMAP dengan set watak khas yang berbeza

Walaupun telah berusia lebih tiga dekad, Base64 tetap menjadi alat asas dalam pengkomputeran moden, terutama dengan kebangkitan aplikasi web dan API yang bergantung kepada format data berasaskan teks seperti JSON.

Contoh Kod

Berikut adalah contoh pengekodan dan penyahkodan Base64 dalam pelbagai bahasa pengaturcaraan:

// Pengekodan/Penyahkodan Base64 JavaScript
function encodeToBase64(text) {
  return btoa(text);
}

function decodeFromBase64(base64String) {
  try {
    return atob(base64String);
  } catch (e) {
    throw new Error("Rentetan Base64 tidak sah");
  }
}

// Contoh penggunaan
const originalText = "Hello, World!";
const encoded = encodeToBase64(originalText);
console.log("Terkod:", encoded);  // SGVsbG8sIFdvcmxkIQ==

try {
  const decoded = decodeFromBase64(encoded);
  console.log("Didekod:", decoded);  // Hello, World!
} catch (error) {
  console.error(error.message);
}
# Pengekodan/Penyahkodan Base64 Python
import base64

def encode_to_base64(text):
    # Tukar rentetan kepada bait dan kemudian kodkan
    text_bytes = text.encode('utf-8')
    base64_bytes = base64.b64encode(text_bytes)
    return base64_bytes.decode('utf-8')

def decode_from_base64(base64_string):
    try:
        # Tukar rentetan base64 kepada bait dan kemudian dekodkan
        base64_bytes = base64_string.encode('utf-8')
        text_bytes = base64.b64decode(base64_bytes)
        return text_bytes.decode('utf-8')
    except Exception as e:
        raise ValueError(f"Rentetan Base64 tidak sah: {e}")

# Contoh penggunaan
original_text = "Hello, World!"
encoded = encode_to_base64(original_text)
print(f"Terkod: {encoded}")  # SGVsbG8sIFdvcmxkIQ==

try:
    decoded = decode_from_base64(encoded)
    print(f"Didekod: {decoded}")  # Hello, World!
except ValueError as e:
    print(e)
// Pengekodan/Penyahkodan Base64 Java
import java.util.Base64;
import java.nio.charset.StandardCharsets;

public class Base64Example {
    public static String encodeToBase64(String text) {
        byte[] textBytes = text.getBytes(StandardCharsets.UTF_8);
        byte[] encodedBytes = Base64.getEncoder().encode(textBytes);
        return new String(encodedBytes, StandardCharsets.UTF_8);
    }
    
    public static String decodeFromBase64(String base64String) {
        try {
            byte[] base64Bytes = base64String.getBytes(StandardCharsets.UTF_8);
            byte[] decodedBytes = Base64.getDecoder().decode(base64Bytes);
            return new String(decodedBytes, StandardCharsets.UTF_8);
        } catch (IllegalArgumentException e) {
            throw new IllegalArgumentException("Rentetan Base64 tidak sah: " + e.getMessage());
        }
    }
    
    public static void main(String[] args) {
        String originalText = "Hello, World!";
        String encoded = encodeToBase64(originalText);
        System.out.println("Terkod: " + encoded);  // SGVsbG8sIFdvcmxkIQ==
        
        try {
            String decoded = decodeFromBase64(encoded);
            System.out.println("Didekod: " + decoded);  // Hello, World!
        } catch (IllegalArgumentException e) {
            System.err.println(e.getMessage());
        }
    }
}
<?php
// Pengekodan/Penyahkodan Base64 PHP
function encodeToBase64($text) {
    return base64_encode($text);
}

function decodeFromBase64($base64String) {
    $decoded = base64_decode($base64String, true);
    if ($decoded === false) {
        throw new Exception("Rentetan Base64 tidak sah");
    }
    return $decoded;
}

// Contoh penggunaan
$originalText = "Hello, World!";
$encoded = encodeToBase64($originalText);
echo "Terkod: " . $encoded . "\n";  // SGVsbG8sIFdvcmxkIQ==

try {
    $decoded = decodeFromBase64($encoded);
    echo "Didekod: " . $decoded . "\n";  // Hello, World!
} catch (Exception $e) {
    echo "Ralat: " . $e->getMessage() . "\n";
}
?>
// Pengekodan/Penyahkodan Base64 C#
using System;
using System.Text;

class Base64Example
{
    public static string EncodeToBase64(string text)
    {
        byte[] textBytes = Encoding.UTF8.GetBytes(text);
        return Convert.ToBase64String(textBytes);
    }
    
    public static string DecodeFromBase64(string base64String)
    {
        try
        {
            byte[] base64Bytes = Convert.FromBase64String(base64String);
            return Encoding.UTF8.GetString(base64Bytes);
        }
        catch (FormatException)
        {
            throw new FormatException("Rentetan Base64 tidak sah");
        }
    }
    
    static void Main()
    {
        string originalText = "Hello, World!";
        string encoded = EncodeToBase64(originalText);
        Console.WriteLine($"Terkod: {encoded}");  // SGVsbG8sIFdvcmxkIQ==
        
        try
        {
            string decoded = DecodeFromBase64(encoded);
            Console.WriteLine($"Didekod: {decoded}");  // Hello, World!
        }
        catch (FormatException e)
        {
            Console.WriteLine($"Ralat: {e.Message}");
        }
    }
}
# Pengekodan/Penyahkodan Base64 Ruby
require 'base64'

def encode_to_base64(text)
  Base64.strict_encode64(text)
end

def decode_from_base64(base64_string)
  begin
    Base64.strict_decode64(base64_string)
  rescue ArgumentError => e
    raise "Rentetan Base64 tidak sah: #{e.message}"
  end
end

# Contoh penggunaan
original_text = "Hello, World!"
encoded = encode_to_base64(original_text)
puts "Terkod: #{encoded}"  # SGVsbG8sIFdvcmxkIQ==

begin
  decoded = decode_from_base64(encoded)
  puts "Didekod: #{decoded}"  # Hello, World!
rescue StandardError => e
  puts "Ralat: #{e.message}"
end
// Pengekodan/Penyahkodan Base64 Go
package main

import (
    "encoding/base64"
    "fmt"
)

func encodeToBase64(text string) string {
    return base64.StdEncoding.EncodeToString([]byte(text))
}

func decodeFromBase64(base64String string) (string, error) {
    bytes, err := base64.StdEncoding.DecodeString(base64String)
    if err != nil {
        return "", fmt.Errorf("rentetan Base64 tidak sah: %v", err)
    }
    return string(bytes), nil
}

func main() {
    originalText := "Hello, World!"
    encoded := encodeToBase64(originalText)
    fmt.Println("Terkod:", encoded)  // SGVsbG8sIFdvcmxkIQ==
    
    decoded, err := decodeFromBase64(encoded)
    if err != nil {
        fmt.Println("Ralat:", err)
    } else {
        fmt.Println("Didekod:", decoded)  // Hello, World!
    }
}
// Pengekodan/Penyahkodan Base64 Swift
import Foundation

func encodeToBase64(_ text: String) -> String? {
    if let data = text.data(using: .utf8) {
        return data.base64EncodedString()
    }
    return nil
}

func decodeFromBase64(_ base64String: String) -> String? {
    if let data = Data(base64Encoded: base64String) {
        return String(data: data, encoding: .utf8)
    }
    return nil
}

// Contoh penggunaan
let originalText = "Hello, World!"
if let encoded = encodeToBase64(originalText) {
    print("Terkod: \(encoded)")  // SGVsbG8sIFdvcmxkIQ==
    
    if let decoded = decodeFromBase64(encoded) {
        print("Didekod: \(decoded)")  // Hello, World!
    } else {
        print("Ralat: Tidak dapat menyahkod rentetan Base64")
    }
} else {
    print("Ralat: Tidak dapat mengekod teks")
}
' Pengekodan/Penyahkodan Base64 Excel VBA
' Nota: Ini memerlukan rujukan kepada Microsoft XML, v6.0
Function EncodeToBase64(text As String) As String
    Dim xmlObj As Object
    Set xmlObj = CreateObject("MSXML2.DOMDocument")
    
    Dim xmlNode As Object
    Set xmlNode = xmlObj.createElement("b64")
    
    xmlNode.DataType = "bin.base64"
    xmlNode.nodeTypedValue = StrConv(text, vbFromUnicode)
    
    EncodeToBase64 = xmlNode.text
    
    Set xmlNode = Nothing
    Set xmlObj = Nothing
End Function

Function DecodeFromBase64(base64String As String) As String
    On Error GoTo ErrorHandler
    
    Dim xmlObj As Object
    Set xmlObj = CreateObject("MSXML2.DOMDocument")
    
    Dim xmlNode As Object
    Set xmlNode = xmlObj.createElement("b64")
    
    xmlNode.DataType = "bin.base64"
    xmlNode.text = base64String
    
    DecodeFromBase64 = StrConv(xmlNode.nodeTypedValue, vbUnicode)
    
    Set xmlNode = Nothing
    Set xmlObj = Nothing
    Exit Function
    
ErrorHandler:
    DecodeFromBase64 = "Ralat: Rentetan Base64 tidak sah"
End Function

' Penggunaan dalam helaian:
' =EncodeToBase64("Hello, World!")
' =DecodeFromBase64("SGVsbG8sIFdvcmxkIQ==")
# Pengekodan/Penyahkodan Base64 R
# Memerlukan pakej 'base64enc'
# install.packages("base64enc")
library(base64enc)

encode_to_base64 <- function(text) {
  # Tukar teks kepada bait mentah, kemudian kodkan
  text_raw <- charToRaw(text)
  base64_encoded <- base64encode(text_raw)
  return(rawToChar(base64_encoded))
}

decode_from_base64 <- function(base64_string) {
  tryCatch({
    # Tukar rentetan base64 kepada mentah, kemudian dekodkan
    base64_raw <- charToRaw(base64_string)
    decoded_raw <- base64decode(base64_raw)
    return(rawToChar(decoded_raw))
  }, error = function(e) {
    stop(paste("Rentetan Base64 tidak sah:", e$message))
  })
}

# Contoh penggunaan
original_text <- "Hello, World!"
encoded <- encode_to_base64(original_text)
cat("Terkod:", encoded, "\n")  # SGVsbG8sIFdvcmxkIQ==

tryCatch({
  decoded <- decode_from_base64(encoded)
  cat("Didekod:", decoded, "\n")  # Hello, World!
}, error = function(e) {
  cat("Ralat:", e$message, "\n")
})
% Pengekodan/Penyahkodan Base64 MATLAB
function demo_base64()
    originalText = 'Hello, World!';
    
    % Pengekodan
    encoded = encode_to_base64(originalText);
    fprintf('Terkod: %s\n', encoded);  % SGVsbG8sIFdvcmxkIQ==
    
    % Penyahkodan
    try
        decoded = decode_from_base64(encoded);
        fprintf('Didekod: %s\n', decoded);  % Hello, World!
    catch e
        fprintf('Ralat: %s\n', e.message);
    end
end

function encoded = encode_to_base64(text)
    % Tukar teks kepada array uint8 dan kodkan
    bytes = uint8(text);
    encoded = base64encode(bytes);
end

function decoded = decode_from_base64(base64String)
    try
        % Dekod rentetan base64 kepada array uint8
        bytes = base64decode(base64String);
        decoded = char(bytes);
    catch
        error('Rentetan Base64 tidak sah');
    end
end
// Pengekodan/Penyahkodan Base64 menggunakan OpenSSL C
#include <stdio.h>
#include <string.h>
#include <openssl/bio.h>
#include <openssl/evp.h>
#include <openssl/buffer.h>
#include <stdint.h>

char* encode_to_base64(const char* input) {
    BIO *bio, *b64;
    BUF_MEM *bufferPtr;
    
    b64 = BIO_new(BIO_f_base64());
    bio = BIO_new(BIO_s_mem());
    bio = BIO_push(b64, bio);
    
    BIO_set_flags(bio, BIO_FLAGS_BASE64_NO_NL);
    BIO_write(bio, input, strlen(input));
    BIO_flush(bio);
    BIO_get_mem_ptr(bio, &bufferPtr);
    
    char* result = (char*)malloc(bufferPtr->length + 1);
    memcpy(result, bufferPtr->data, bufferPtr->length);
    result[bufferPtr->length] = '\0';
    
    BIO_free_all(bio);
    
    return result;
}

char* decode_from_base64(const char* input) {
    BIO *bio, *b64;
    size_t length = strlen(input);
    char* buffer = (char*)malloc(length);
    
    b64 = BIO_new(BIO_f_base64());
    bio = BIO_new_mem_buf(input, -1);
    bio = BIO_push(b64, bio);
    
    BIO_set_flags(bio, BIO_FLAGS_BASE64_NO_NL);
    int decoded_length = BIO_read(bio, buffer, length);
    
    if (decoded_length <= 0) {
        free(buffer);
        BIO_free_all(bio);
        return NULL; // Rentetan Base64 tidak sah
    }
    
    buffer[decoded_length] = '\0';
    
    BIO_free_all(bio);
    
    return buffer;
}

int main() {
    const char* original_text = "Hello, World!";
    
    char* encoded = encode_to_base64(original_text);
    printf("Terkod: %s\n", encoded);  // SGVsbG8sIFdvcmxkIQ==
    
    char* decoded = decode_from_base64(encoded);
    if (decoded) {
        printf("Didekod: %s\n", decoded);  // Hello, World!
        free(decoded);
    } else {
        printf("Ralat: Rentetan Base64 tidak sah\n");
    }
    
    free(encoded);
    
    return 0;
}
// Pengekodan/Penyahkodan Base64 Rust
use base64::{encode, decode};
use std::str;

fn encode_to_base64(text: &str) -> String {
    encode(text)
}

fn decode_from_base64(base64_string: &str) -> Result<String, String> {
    match decode(base64_string) {
        Ok(bytes) => {
            match str::from_utf8(&bytes) {
                Ok(text) => Ok(text.to_string()),
                Err(e) => Err(format!("Urutan UTF-8 tidak sah: {}", e))
            }
        },
        Err(e) => Err(format!("Rentetan Base64 tidak sah: {}", e))
    }
}

fn main() {
    let original_text = "Hello, World!";
    let encoded = encode_to_base64(original_text);
    println!("Terkod: {}", encoded);  // SGVsbG8sIFdvcmxkIQ==
    
    match decode_from_base64(&encoded) {
        Ok(decoded) => println!("Didekod: {}", decoded),  // Hello, World!
        Err(e) => println!("Ralat: {}", e)
    }
}

Kes-Kes Tepi dan Pertimbangan

Apabila bekerja dengan pengekodan dan penyahkodan Base64, ambil perhatian terhadap pertimbangan penting ini:

  1. Karakter Unicode dan Bukan ASCII: Apabila mengekod teks dengan karakter bukan ASCII, pastikan pengekodan karakter yang betul (biasanya UTF-8) sebelum mengekod Base64.

  2. Padding: Base64 standard menggunakan padding dengan watak "=" untuk memastikan panjang output adalah kelipatan 4. Beberapa pelaksanaan membenarkan penghapusan padding, yang boleh menyebabkan isu keserasian.

  3. Pemisahan Baris: Pelaksanaan Base64 tradisional menyisipkan pemisahan baris (biasanya setiap 76 watak) untuk kebolehan bacaan, tetapi aplikasi moden sering mengabaikannya.

  4. Base64 Selamat URL: Base64 standard menggunakan watak "+" dan "/" yang mempunyai makna khas dalam URL. Untuk konteks URL, gunakan Base64 selamat URL yang menggantikan ini dengan "-" dan "_".

  5. Ruang Putih: Apabila menyahkod, beberapa pelaksanaan bersifat toleran dan mengabaikan ruang putih, manakala yang lain memerlukan input yang tepat.

  6. Peningkatan Saiz: Pengekodan Base64 meningkatkan saiz data sekitar 33% (4 bait output untuk setiap 3 bait input).

  7. Prestasi: Pengekodan/penyahkodan Base64 boleh menjadi intensif dari segi pengkomputeran untuk data yang sangat besar. Pertimbangkan pendekatan aliran untuk fail besar.

Rujukan

  1. RFC 4648 - Pengekodan Data Base16, Base32, dan Base64
  2. RFC 2045 - MIME Bahagian Satu: Format Badan Mesej Internet
  3. MDN Web Docs: Pengekodan dan Penyahkodan Base64
  4. Base64 - Wikipedia
  5. MIME - Wikipedia
Feedback