Java’da PDF’ye Barkod Ekle – GroupDocs ile İmzala ve Doğrula

İç iş akışları için belgeleri hızlı ve görsel bir şekilde etiketlemeniz gerekiyorsa, Java’da bir PDF’ye barkod eklemek mükemmel bir çözümdür. GroupDocs.Signature ile tam PKI‑tabanlı dijital imzaların getirdiği yük olmadan barkod imzalarını ekleyebilir, doğrulayabilir, arayabilir, güncelleyebilir ve silebilirsiniz. Bu öğretici, ortam kurulumundan üretim‑hazır en iyi uygulamalara kadar her adımı size gösterir.

Hızlı Yanıtlar

  • Java’da PDF’lere barkod ekleyen kütüphane nedir? GroupDocs.Signature for Java.
  • PDF, Word ve görselleri imzalayabilir miyim? Evet – API 30+ formatı destekler.
  • Geliştirme için lisansa ihtiyacım var mı? 30‑günlük geçici lisans ücretsizdir; üretim için tam lisans gereklidir.
  • PDF imzalamak için kaç satır kod gerekir? Sadece iki satır: bir Signature nesnesi oluşturup sign metodunu çağırmak.
  • Barkod doğrulaması büyük/küçük harfe duyarlı mı? Evet – metin tam olarak, büyük/küçük harf ve boşluklar dahil, eşleşmelidir.

Java’da PDF’ye barkod ekleme nedir?

add barcode pdf java, bir PDF dosyasına barkod (örneğin Code128, QR veya Data Matrix) yerleştirmek için Java kodu kullanma sürecine denir. Bu teknik, taranabilir veya programlı olarak doğrulanabilir bir makine‑okunur etiket sağlar ve iç sistemlerde hızlı belge takibini mümkün kılar.

Tam dijital imzalar yerine neden barkod imzaları kullanılmalı?

Barkod imzaları, PKI‑tabanlı dijital imzalara göre oluşturulup doğrulanması %30‑50 daha hızlıdır ve bir yazdır‑tara döngüsünden sonra güvenilir bir şekilde çalışır. Ayrıca sertifika yönetimi gerektirmez, bu da kriptografik kanıtın zorunlu olmadığı yüksek hacimli, iç iş akışları için ideal kılar.

Önkoşullar

  • Java Development Kit (JDK) 8+ – Daha iyi performans için Java 11 veya 17 önerilir.
  • IDE – IntelliJ IDEA veya Eclipse (örnekler IntelliJ sözdizimini kullanır).
  • Build aracı – Bağımlılık yönetimi için Maven veya Gradle.

Projenize GroupDocs.Signature Ekleme

Başlamak için en kolay yol, kütüphaneyi build aracınız üzerinden eklemektir. İşte nasıl:

Maven Kullanıcıları – pom.xml dosyanıza şunu ekleyin:

<dependency>
    <groupId>com.groupdocs</groupId>
    <artifactId>groupdocs-signature</artifactId>
    <version>23.12</version>
</dependency>

Gradle Kullanıcıları – build.gradle dosyanıza şunu ekleyin:

implementation 'com.groupdocs:groupdocs-signature:23.12'

Doğrudan JAR İndirme – Manuel kurulum tercih ediyorsanız, JAR dosyasını GroupDocs.Signature releases adresinden indirin ve sınıf yolunuza ekleyin.

Lisansınızı Alın

GroupDocs.Signature üretim kullanımı için ücretsiz değildir, ancak esnek seçenekleriniz var:

Pro ipucu: Geliştirme için geçici lisansla başlayın; kalıcı bir anahtara geçtiğinizde filigranları kaldırır.

Hızlı Ortam Kontrolü

Bağımlılığı ekledikten sonra basit bir duman testi çalıştırın:

import com.groupdocs.signature.Signature;

public class SignatureTest {
    public static void main(String[] args) {
        try {
            Signature signature = new Signature("test.pdf");
            System.out.println("GroupDocs.Signature initialized successfully!");
            signature.dispose();
        } catch (Exception e) {
            System.err.println("Setup issue: " + e.getMessage());
        }
    }
}

Program hatasız çalışıyorsa ortamınız hazır demektir. Sorunla karşılaşırsanız JDK sürümünü ve eklediğiniz kütüphane sürümünü doğrulayın.

Barkod İmzalarını Ne Zaman Kullanmalı

Barkod imzaları belirli senaryolarda öne çıkar:

  • İç Belge İş Akışları – Faturaları, satın alma emirlerini veya notları onay zincirleri üzerinden izleyin.
  • Yüksek Hacimli İşlem – Binlerce belgeyi hızlıca imzalayın; barkod oluşturma, tam dijital imzalamaya göre 2× daha hızlıdır.
  • Yazdır‑Tara Köprüleri – Barkodlar yazdır‑tara döngüsünden sonra da ayakta kalır, bu da hibrit kağıt‑dijital süreçler için idealdir.
  • Eski Sistem Entegrasyonu – Mevcut barkod tarayıcıları ek yazılım olmadan etiketleri okuyabilir.
  • Denetim İzleri – Denetçilerin anında doğrulayabileceği işlem kimlikleri veya zaman damgalarını gömün.

PKI‑tabanlı dijital imzaların gerektiği yasal sözleşmeler, yüksek güvenlikli belgeler veya dış ortak değişimleri için barkod imzalarından kaçının.

GroupDocs.Signature’ı Java için Kurma

Temel Sınıf Tanımı

Signature sınıfı, GroupDocs.Signature içinde tüm imzalama, doğrulama, arama, güncelleme ve silme işlemlerinin giriş noktasıdır.

import com.groupdocs.signature.Signature;

Temel Başlatma

Hedef dosyayı işaret eden bir Signature nesnesi oluşturun:

Signature signature = new Signature("path/to/your/document.pdf");

Önemli notlar

  • Yollar mutlak ya da göreli olabilir; çapraz‑platform uyumluluğu için System.getProperty("user.home") kullanın.
  • GroupDocs 30+ giriş ve çıkış formatını destekler; PDF, DOCX, XLSX, PPTX ve PNG bunlara dahildir.
  • Her zaman kaynakları signature.dispose() ile veya try‑with‑resources bloğu ile serbest bırakın:
try (Signature signature = new Signature("path/to/your/document.pdf")) {
    // Your signing operations here
} catch (Exception e) {
    System.err.println("Error working with document: " + e.getMessage());
}

Artık barkod eklemeye hazırsınız.

Java’da bir PDF’ye barkod nasıl eklenir?

new Signature("input.pdf") ile kaynak PDF’yi yükleyin, bir BarcodeSignature nesnesi (örneğin “John Smith” metniyle Code128) yapılandırın ve imzalı dosyayı üretmek için sign metodunu çağırın – tümü üç kısa kod satırında. Bu yaklaşım, orijinal belge düzenini bozmadan makine‑okunur bir etiket eklemenizi sağlar ve sadece PDF’ler değil, desteklenen tüm formatlarda çalışır.

Adım‑Adım Uygulama

1. Dosya Yollarını Tanımla

Kaynak ve çıktı dosyalarının konumlarını ayarlayın:

String filePath = "YOUR_DOCUMENT_DIRECTORY/sample.docx";
String outputFilePath = "YOUR_OUTPUT_DIRECTORY/signed_sample.docx";

2. İmza İşleyicisini Oluştur

İşleyiciyi kaynak belgeyle başlatın:

Signature signature = new Signature(filePath);

3. Barkod Seçeneklerini Yapılandır

Bir BarcodeSignature nesnesi, gömülecek barkodun görsel ve veri özelliklerini tanımlar. Barkod tipini, kodlanacak metni, konumu, boyutu, rengi ve isteğe bağlı insan‑okunur fontu ayarlayın:

BarcodeSignOptions signOptions = new BarcodeSignOptions("John Smith", BarcodeTypes.Code128);
signOptions.setVerticalAlignment(VerticalAlignment.Top);
signOptions.setHorizontalAlignment(HorizontalAlignment.Center);
signOptions.setWidth(100);
signOptions.setHeight(40);
signOptions.setMargin(new java.awt.Rectangle(20, 20, 0, 0));
signOptions.setForeColor(Color.RED);

SignatureFont signatureFont = new SignatureFont();
signatureFont.setSize(12);
signatureFont.setFamilyName("Comic Sans MS");
signOptions.setFont(signatureFont);

Pro ipucu: Kodlanan dize 20 karakteri aşarsa, tarama hatalarını önlemek için barkod genişliğini artırın.

4. İmzayı Uygula

İmzalama işlemini yürütün ve çıktı dosyasını oluşturun:

signature.sign(outputFilePath, signOptions);

5. Gerçek Dünya Örneği

Bir fatura‑onay sisteminde onaylayıcının çalışan kimliğini ve bir zaman damgasını gömebilirsiniz:

String invoiceId = "INV-2025-0042";
String approver = "john.smith@company.com";
String timestamp = LocalDateTime.now().toString();

// Combine into barcode data
String barcodeData = invoiceId + "|" + approver + "|" + timestamp;

BarcodeSignOptions signOptions = new BarcodeSignOptions(barcodeData, BarcodeTypes.QR);
signOptions.setVerticalAlignment(VerticalAlignment.Bottom);
signOptions.setHorizontalAlignment(HorizontalAlignment.Right);

signature.sign(outputFilePath, signOptions);

Ortaya çıkan PDF, gerekli tüm onay meta verilerini kodlayan taranabilir bir barkod içerir.

Java belgesinde bir barkod imzasını nasıl doğrularım?

Signature.verify metodu, sağlanan seçeneklere göre belgeyi eşleşen barkod imzaları için kontrol eder ve beklenen barkodun mevcut olup olmadığını gösteren bir boolean döndürür. Doğrulama, bir belgenin doğru tarafça işlendiğini onaylamanız gereken otomatik iş akışları için faydalıdır.

Doğrulama Adımları

1. İmzalı Belgeyi Yükle

Signature signature = new Signature("YOUR_OUTPUT_DIRECTORY/signed_sample.docx");

2. Doğrulama Kriterlerini Belirle

BarcodeVerifyOptions verifyOptions = new BarcodeVerifyOptions();
verifyOptions.setAllPages(false); // Only check the first page
verifyOptions.setPageNumber(1);
verifyOptions.setEncodeType(BarcodeTypes.Code128);
verifyOptions.setText("John Smith");

3. Doğrulamayı Çalıştır

boolean isValid = signature.verify(verifyOptions) != null;

if (isValid) {
    System.out.println("Document signature verified successfully!");
} else {
    System.out.println("Warning: Signature verification failed!");
}

Ortak desen: Belirli bir tipte herhangi bir barkodun varlığını basitçe onaylamak için setText filtresini atlayın:

BarcodeVerifyOptions flexibleOptions = new BarcodeVerifyOptions();
flexibleOptions.setAllPages(true);
flexibleOptions.setEncodeType(BarcodeTypes.Code128);
// No setText() call = accept any text with this barcode type

boolean hasAnySignature = signature.verify(flexibleOptions) != null;

Veya içeriğe bakmadan sadece barkod formatını doğrulayın:

BarcodeVerifyOptions formatOnly = new BarcodeVerifyOptions();
formatOnly.setEncodeType(BarcodeTypes.QR);
// Confirms a QR code exists, regardless of content

Uyarı: Doğrulama büyük/küçük harfe ve boşluklara duyarlıdır; imzalamadan önce verileri her zaman kırpın ve normalize edin.

Bir belgede barkod imzalarını nasıl ararım?

Signature.search metodu, sağlanan BarcodeSearchOptions ile eşleşen barkod imzalarını tarar ve her barkodun konumu, sayfa numarası ve kodlanmış değeri gibi bilgileri içeren bir koleksiyon döndürür. Bu özellik, her dosyayı manuel olarak açmadan toplu meta veri çıkarımını sağlar.

Arama İş Akışı

1. Aramayı Başlat

Signature signature = new Signature("YOUR_OUTPUT_DIRECTORY/signed_sample.docx");

2. Arama Parametrelerini Yapılandır

BarcodeSearchOptions searchOptions = new BarcodeSearchOptions();
searchOptions.setAllPages(true); // Search the entire document

Performansı artırmak için isteğe bağlı olarak aramayı daraltın:

BarcodeSearchOptions narrowSearch = new BarcodeSearchOptions();
narrowSearch.setAllPages(false);
narrowSearch.setPageNumber(1); // Only search page 1
narrowSearch.setEncodeType(BarcodeTypes.Code128); // Only find Code128 barcodes

3. Aramayı Gerçekleştir

java.util.List<BarcodeSignature> signatures = signature.search(BarcodeSignature.class, searchOptions);

System.out.println("Found " + signatures.size() + " barcode signature(s)");

for (BarcodeSignature bcSignature : signatures) {
    System.out.println("Barcode Type: " + bcSignature.getEncodeType().getTypeName());
    System.out.println("Text: " + bcSignature.getText());
    System.out.println("Position: (" + bcSignature.getLeft() + ", " + bcSignature.getTop() + ")");
    System.out.println("Size: " + bcSignature.getWidth() + "x" + bcSignature.getHeight());
    System.out.println("---");
}

4. Veri Çıkarma Örneği

Bir fatura toplu işlemindeki her barkottan onay verisini çekin:

List<BarcodeSignature> foundSignatures = signature.search(BarcodeSignature.class, searchOptions);

for (BarcodeSignature sig : foundSignatures) {
    String barcodeData = sig.getText();
    
    // Parse your custom format (remember our invoice example?)
    String[] parts = barcodeData.split("\\|");
    if (parts.length == 3) {
        String invoiceId = parts[0];
        String approver = parts[1];
        String timestamp = parts[2];
        
        System.out.println("Invoice " + invoiceId + " approved by " + approver + " at " + timestamp);
    }
}

Performans ipucu: 100 sayfadan uzun belgelerde, aramayı yalnızca barkodların bulunduğu sayfalara sınırlayın; bu, çalışma süresini %70 kadar azaltabilir.

Mevcut bir barkod imzasını nasıl güncellerim?

Signature.update metodu, mevcut bir barkod imzasının görsel özelliklerini (konum, boyut, renk gibi) değiştirir ve orijinal kodlanmış veriyi korur. Bu, belge imzalandıktan sonra düzen değişiklikleri gerektiğinde kullanışlıdır.

Güncelleme Prosedürü

1. Güncellenecek İmzaları Bul

Signature signature = new Signature("YOUR_OUTPUT_DIRECTORY/signed_sample.docx");

BarcodeSearchOptions searchOptions = new BarcodeSearchOptions();
searchOptions.setAllPages(true);

List<BarcodeSignature> signatures = signature.search(BarcodeSignature.class, searchOptions);

2. İstenen Özellikleri Değiştir

List<BarcodeSignature> signaturesToUpdate = new ArrayList<>();

if (!signatures.isEmpty()) {
    BarcodeSignature bcSignature = signatures.get(0); // Update the first found signature
    
    // Move it 100px right and 100px down
    bcSignature.setLeft(bcSignature.getLeft() + 100);
    bcSignature.setTop(bcSignature.getTop() + 100);
    
    // Make it bigger
    bcSignature.setWidth(200);
    bcSignature.setHeight(50);
    
    signaturesToUpdate.add(bcSignature);
}

Birden fazla özelliği aynı anda değiştirebilirsiniz:

bcSignature.setLeft(50);
bcSignature.setTop(50);
bcSignature.setWidth(150);
bcSignature.setHeight(45);
// Note: You can't change the encoded text or barcode type with update
// For that, you'd need to delete and re-sign

3. Değişiklikleri Kaydet

ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
signature.update(outputStream, signaturesToUpdate);

// If you want to save to a file instead:
// signature.update("path/to/updated_document.docx", signaturesToUpdate);

4. Gerçek Dünya Senaryosu

Yeni eklenen şirket logosuyla çakışmayı önlemek için tüm imzaların konumunu yeniden ayarlayın:

List<BarcodeSignature> allSignatures = signature.search(BarcodeSignature.class, searchOptions);
List<BarcodeSignature> toUpdate = new ArrayList<>();

for (BarcodeSignature sig : allSignatures) {
    // Move all signatures down by 50px to clear space for new logo
    if (sig.getTop() < 100) {
        sig.setTop(sig.getTop() + 50);
        toUpdate.add(sig);
    }
}

if (!toUpdate.isEmpty()) {
    signature.update(outputStream, toUpdate);
    System.out.println("Repositioned " + toUpdate.size() + " signature(s)");
}

Sınırlama: Kodlanmış metni değiştirmek, imzanın silinip yeni bir imza eklenmesini gerektirir.

Bir belgeden barkod imzalarını nasıl silerim?

Signature.delete metodu, seçilen barkod imzalarını belgeden kalıcı olarak kaldırır, görsel öğeyi ve kodlanmış veriyi siler. Bu işlemi test imzalarını temizlerken veya barkod artık ilgili olmadığında kullanın.

Silme Adımları

1. İmzaları Bul

Signature signature = new Signature("YOUR_OUTPUT_DIRECTORY/signed_sample.docx");

BarcodeSearchOptions searchOptions = new BarcodeSearchOptions();
searchOptions.setAllPages(true);

List<BarcodeSignature> signatures = signature.search(BarcodeSignature.class, searchOptions);

2. Seçili İmzaları Sil

List<BarcodeSignature> signaturesToDelete = new ArrayList<>();

// Delete all Code128 signatures (for example)
for (BarcodeSignature sig : signatures) {
    if (sig.getEncodeType().equals(BarcodeTypes.Code128)) {
        signaturesToDelete.add(sig);
    }
}

if (!signaturesToDelete.isEmpty()) {
    boolean result = signature.delete(signaturesToDelete);
    
    if (result) {
        System.out.println("Successfully deleted " + signaturesToDelete.size() + " signature(s)");
    } else {
        System.err.println("Failed to delete signatures");
    }
}

3. Koşullu Silme Örneği

Yalnızca belirli bir zaman damgasından daha eski barkodları kaldırın (zaman damgasının kodlanmış metnin bir parçası olduğunu varsayarak):

LocalDateTime cutoffDate = LocalDateTime.now().minusDays(30);
List<BarcodeSignature> outdatedSignatures = new ArrayList<>();

for (BarcodeSignature sig : signatures) {
    try {
        String text = sig.getText();
        // Assuming format like "data|timestamp"
        String[] parts = text.split("\\|");
        if (parts.length > 1) {
            LocalDateTime sigDate = LocalDateTime.parse(parts[1]);
            if (sigDate.isBefore(cutoffDate)) {
                outdatedSignatures.add(sig);
            }
        }
    } catch (Exception e) {
        // Skip signatures that don't match our format
        continue;
    }
}

if (!outdatedSignatures.isEmpty()) {
    signature.delete(outdatedSignatures);
    System.out.println("Removed " + outdatedSignatures.size() + " outdated signature(s)");
}

Uyarı: Silme işlemi geri alınamaz; test sırasında her zaman üretim dosyalarının bir kopyası üzerinde çalışın.

4. Toplu Silme Deseni

Yayına önceden test imzalarını temizleyin:

// Remove all signatures containing "TEST" in their text
List<BarcodeSignature> testSignatures = signatures.stream()
    .filter(sig -> sig.getText().toUpperCase().contains("TEST"))
    .collect(Collectors.toList());

if (!testSignatures.isEmpty()) {
    signature.delete(testSignatures);
    System.out.println("Cleaned up " + testSignatures.size() + " test signature(s)");
}

Barkod Türleri: Pratik Bir Rehber

Doğru barkodu seçmek, tarama güvenilirliği, veri kapasitesi ve yazıcı uyumluluğunu etkiler.

Code128 (En Yaygın Seçim)

  • Ne zaman kullanılmalı: Alfanümerik veri, yüksek yoğunluk, basılı belgeler.
  • Artıları: Kompakt, standart tarayıcılarla çalışır, küçük boyutlarda net basar.
  • Eksileri: ASCII ile sınırlı, 2‑D kodlara göre daha az hata toleranslı.
BarcodeSignOptions code128 = new BarcodeSignOptions("INV-2025-042", BarcodeTypes.Code128);

QR Kodu (Mobil İçin En İyi)

  • Ne zaman kullanılmalı: Mobil tarama, büyük veri yükleri (URL’ler, JSON vb.), hasar görebilecek belgeler.
  • Artıları: 4 000 karaktere kadar, yerleşik hata düzeltme, akıllı telefon dostu.
  • Eksileri: Daha büyük görsel alan, küçük boyutlar için daha yüksek çözünürlük gerekir.
String jsonData = "{\"invoice\":\"INV-042\",\"amount\":1500.00,\"approver\":\"john@company.com\"}";
BarcodeSignOptions qrCode = new BarcodeSignOptions(jsonData, BarcodeTypes.QR);

Code39 (Eski Güvenilir)

  • Ne zaman kullanılmalı: Eski tarayıcı ortamları, insan‑okunur metin ihtiyacı.
  • Artıları: Geniş eski destek, basit format, kontrol toplamı gerekmez.
  • Eksileri: Düşük veri yoğunluğu, sınırlı karakter seti, daha fazla yer kaplar.

Data Matrix (Kompakt Güç Merkezi)

  • Ne zaman kullanılmalı: Son derece sınırlı alan, çok küçük öğelerin işaretlenmesi, yüksek yoğunlukta veri.
  • Artıları: Çok kompakt, güçlü hata düzeltme, eğimli yüzeylerde çalışır.
  • Eksileri: Yüksek kaliteli baskı gerekir, daha az yaygın tarayıcı desteği.

Hızlı Karşılaştırma

Barkod TürüVeri KapasitesiEn İyi KullanımTipik Boyut
Code128~100 karakterGenel amaçlı etiketlemeKüçük
QR Kodu~4 000 karakterMobil tarama, zengin veriOrta
Code39~43 karakterEski donanımBüyük
Data Matrix~3 000 karakterÇok küçük alanlar, endüstriyel etiketlerÇok küçük

Öneri: Basit kimlikler için Code128 ile başlayın. URL’ler veya daha büyük veri yükleri eklemeniz gerektiğinde QR’ye geçin. Code39’u yalnızca eski entegrasyonlar için kullanın.

Yaygın Sorunlar ve Çözümler

Sorun: “Doğrulama Sırasında Barkod Bulunamadı”

Belirtiler: Barkod görünür olmasına rağmen doğrulama false döner.

Tipik nedenler

  1. Büyük/küçük harf eşleşmemesi (örneğin “John Smith” vs. “john smith”).
  2. Kodlanmış metinde ekstra boşluk.
  3. Doğrulama seçeneklerinde yanlış barkod tipi belirtilmesi.
  4. Yanlış sayfa numarasının aranması.

Çözüm: İmzalamadan ve doğrulamadan önce metni normalize edin ve setEncodeType‘ın orijinal tipe eşleştiğinden emin olun.

// Always normalize your data
String signatureText = originalText.trim().toLowerCase();

// When signing:
BarcodeSignOptions signOptions = new BarcodeSignOptions(signatureText, BarcodeTypes.Code128);

// When verifying:
BarcodeVerifyOptions verifyOptions = new BarcodeVerifyOptions();
verifyOptions.setText(signatureText); // Use the same normalized text
verifyOptions.setEncodeType(BarcodeTypes.Code128);

Sorun: “Barkod Bulanık veya Okunamaz Görünüyor”

Belirtiler: Yazdırılan barkodlar taranamaz.

Nedenler

  • Barkod boyutları kodlanan veri için çok küçük.
  • Düşük çözünürlüklü yazıcı ayarları.
  • Barkod rengi ile arka plan arasındaki kontrast yetersiz.

Çözüm: Barkod genişliğini/ yüksekliğini artırın, yüksek kontrast renkler (beyaz üzerine siyah) kullanın ve yazıcı DPI ayarını en az 300 dpi yapın.

// Increase size for longer strings
int dataLength = barcodeText.length();
int minWidth = Math.max(100, dataLength * 10); // 10px per character minimum

BarcodeSignOptions signOptions = new BarcodeSignOptions(barcodeText, BarcodeTypes.Code128);
signOptions.setWidth(minWidth);
signOptions.setHeight(60); // Taller = easier to scan

// Use high-contrast colors
signOptions.setForeColor(Color.BLACK); // Black on white is most reliable
signOptions.setBackColor(Color.WHITE);

Sorun: “Büyük Belgelerde OutOfMemoryError”

Belirtiler: Yüzlerce sayfalı PDF’leri işlerken uygulama çöküyor.

Neden: Kütüphane tüm belgeyi belleğe yüklüyor.

Çözüm: Akış modunu etkinleştirin ve sayfaları artımlı olarak işleyin.

// Process pages in batches instead of all at once
BarcodeSearchOptions searchOptions = new BarcodeSearchOptions();
searchOptions.setAllPages(false);

List<BarcodeSignature> allSignatures = new ArrayList<>();

for (int page = 1; page <= totalPages; page++) {
    searchOptions.setPageNumber(page);
    List<BarcodeSignature> pageSignatures = signature.search(BarcodeSignature.class, searchOptions);
    allSignatures.addAll(pageSignatures);
    
    // Process and clear as you go
    if (page % 10 == 0) {
        System.gc(); // Suggest garbage collection every 10 pages
    }
}

Sorun: “İmza Konumu Belge Türleri Arasında Tutarsız”

Belirtiler: PDF’lerde imzalama ile Word belgelerinde imzalama arasında barkodlar farklı konumlarda görünüyor.

Neden: PDF, sol‑alt kökeni kullanırken, Word sol‑üst kökeni kullanır.

Çözüm: Belge tipini tespit edin ve uygun koordinat dönüşümünü uygulayın.

// Use relative positioning instead of absolute
signOptions.setVerticalAlignment(VerticalAlignment.Bottom);
signOptions.setHorizontalAlignment(HorizontalAlignment.Right);

// Then use margins for fine-tuning
Padding margin = new Padding();
margin.setRight(50); // 50px from right edge
margin.setBottom(50); // 50px from bottom
signOptions.setMargin(margin);

// This works consistently across PDF, DOCX, XLSX, etc.

Sorun: “Güncellenen İmzalar Biçimlendirmeyi Kaybediyor”

Belirtiler: update çağrısından sonra barkodun rengi veya yazı tipi beklenmedik şekilde değişiyor.

Neden: Güncelleme sırasında tüm görsel özellikler korunmaz.

Çözüm: Güncelleme çağrısından sonra görsel ayarları yeniden uygulayın.

// When updating, explicitly set all visual properties
bcSignature.setLeft(newLeft);
bcSignature.setTop(newTop);
bcSignature.setWidth(originalWidth); // Don't forget these!
bcSignature.setHeight(originalHeight);
// Note: Color and font can't be updated - you'd need to delete and re-sign

Üretim İçin En İyi Uygulamalar

Performans Optimizasyonu

  1. Signature Örneklerini Yeniden Kullan – Belge başına tek bir Signature nesnesi oluşturun ve birden fazla işlemde yeniden kullanın.
// Bad - Creates new instance each time
public void processDocument(String path) {
    Signature sig1 = new Signature(path);
    sig1.search(/* ... */);
    
    Signature sig2 = new Signature(path); // Unnecessary reload
    sig2.verify(/* ... */);
}

// Good - Reuse the same instance
public void processDocument(String path) {
    try (Signature signature = new Signature(path)) {
        signature.search(/* ... */);
        signature.verify(/* ... */);
        signature.update(/* ... */);
    }
}
  1. Yalnızca Belirli Sayfaları Ara – Barkodların beklendiği sayfa aralığını sınırlayın.
// Slow for 100+ page documents
BarcodeSearchOptions slowSearch = new BarcodeSearchOptions();
slowSearch.setAllPages(true);

// Fast - only check where signatures actually are
BarcodeSearchOptions fastSearch = new BarcodeSearchOptions();
fastSearch.setAllPages(false);
fastSearch.setPageNumber(1); // Only check cover page
  1. En Basit Barkod Tipini Seç – Daha basit barkodlar daha hızlı üretilir; ekstra kapasiteye gerçekten ihtiyacınız olduğunda QR veya Data Matrix kullanın.
// Overkill for simple IDs
BarcodeSignOptions slow = new BarcodeSignOptions("12345", BarcodeTypes.QR);

// Faster and more appropriate
BarcodeSignOptions fast = new BarcodeSignOptions("12345", BarcodeTypes.Code128);

Güvenlik Hususları

  1. Kişisel Hassas Verileri Asla Kodlama – Barkodlar kolay okunur; SSN gibi kişisel tanımlayıcı bilgileri (PII) kodlamaktan kaçının.
// Bad - exposes sensitive data
String barcodeData = "SSN:123-45-6789|Password:hunter2";

// Good - use reference IDs
String barcodeData = "USER-REF-7721X"; // Look up sensitive data server-side
  1. Sunucu Tarafında Doğrula – Yalnızca istemci‑tarafı doğrulamaya güvenmeyin; her zaman güvenilir bir arka uçta yeniden doğrulayın.
// Client scans barcode and extracts "APPROVED-BY-ADMIN"
// Always verify server-side:
public boolean verifyApproval(String documentId, String scannedData) {
    // Load document from secure storage
    Signature signature = new Signature(getSecureDocument(documentId));
    
    BarcodeVerifyOptions verifyOptions = new BarcodeVerifyOptions();
    verifyOptions.setText(scannedData);
    
    boolean isValid = signature.verify(verifyOptions) != null;
    
    // Also check against your database
    boolean isInDatabase = checkApprovalDatabase(documentId, scannedData);
    
    return isValid && isInDatabase;
}
  1. Zaman Damgaları Ekle – Tekrar saldırılarını önlemek için barkod yüküne bir zaman damgası ekleyin.
import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;

String timestamp = LocalDateTime.now().truncatedTo(ChronoUnit.SECONDS).toString();
String barcodeData = "APPROVAL|" + userId + "|" + timestamp;

// When verifying, check the timestamp isn't too old
public boolean isSignatureRecent(String barcodeData, int maxAgeHours) {
    String[] parts = barcodeData.split("\\|");
    if (parts.length < 3) return false;
    
    LocalDateTime signatureTime = LocalDateTime.parse(parts[2]);
    LocalDateTime now = LocalDateTime.now();
    
    long hoursSince = ChronoUnit.HOURS.between(signatureTime, now);
    return hoursSince <= maxAgeHours;
}

Hata‑İşleme Desenleri

  • Her Zaman Try‑With‑Resources Kullan Signature nesnelerinin serbest bırakıldığından emin olmak için.
try (Signature signature = new Signature(documentPath)) {
    // Your operations here
    signature.sign(outputPath, signOptions);
} catch (Exception e) {
    logger.error("Failed to sign document: " + documentPath, e);
    throw new DocumentSigningException("Could not process document", e);
}
  • İmzalamadan Önce Dosya Erişimini Doğrula.
public void signDocument(String inputPath, String outputPath) {
    File inputFile = new File(inputPath);
    
    if (!inputFile.exists()) {
        throw new IllegalArgumentException("Input file not found: " + inputPath);
    }
    
    if (!inputFile.canRead()) {
        throw new SecurityException("Cannot read input file: " + inputPath);
    }
    
    File outputDir = new File(outputPath).getParentFile();
    if (outputDir != null && !outputDir.exists()) {
        outputDir.mkdirs();
    }
    
    try (Signature signature = new Signature(inputPath)) {
        signature.sign(outputPath, signOptions);
    }
}
  • Erişimi Senkronize Et birden fazla iş parçacığı aynı dosya üzerinde çalışabilir.
import java.util.concurrent.locks.ReentrantLock;
import java.util.concurrent.ConcurrentHashMap;

public class SignatureManager {
    private final ConcurrentHashMap<String, ReentrantLock> documentLocks = new ConcurrentHashMap<>();
    
    public void signDocument(String documentPath, BarcodeSignOptions options) {
        ReentrantLock lock = documentLocks.computeIfAbsent(documentPath, k -> new ReentrantLock());
        
        lock.lock();
        try (Signature signature = new Signature(documentPath)) {
            signature.sign(documentPath + ".signed", options);
        } finally {
            lock.unlock();
        }
    }
}

Uygulamanızı Test Etme

Birim Test Şablonu

import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.io.TempDir;
import static org.junit.jupiter.api.Assertions.*;

public class BarcodeSignatureTest {
    
    @TempDir
    Path tempDir;
    
    @Test
    public void testSignAndVerify() throws Exception {
        // Setup
        String testDoc = "test-document.pdf";
        String outputDoc = tempDir.resolve("signed-test.pdf").toString();
        String testData = "TEST-USER-12345";
        
        // Sign
        try (Signature signature = new Signature(testDoc)) {
            BarcodeSignOptions signOptions = new BarcodeSignOptions(testData, BarcodeTypes.Code128);
            signature.sign(outputDoc, signOptions);
        }
        
        // Verify
        try (Signature signature = new Signature(outputDoc)) {
            BarcodeVerifyOptions verifyOptions = new BarcodeVerifyOptions();
            verifyOptions.setText(testData);
            verifyOptions.setEncodeType(BarcodeTypes.Code128);
            
            boolean isValid = signature.verify(verifyOptions) != null;
            assertTrue(isValid, "Signature should be valid");
        }
    }
    
    @Test
    public void testSearchFindsSignature() throws Exception {
        String signedDoc = "signed-document.pdf";
        
        try (Signature signature = new Signature(signedDoc)) {
            BarcodeSearchOptions searchOptions = new BarcodeSearchOptions();
            searchOptions.setAllPages(true);
            
            List<BarcodeSignature> signatures = signature.search(BarcodeSignature.class, searchOptions);
            
            assertFalse(signatures.isEmpty(), "Should find at least one signature");
            assertEquals("TEST-USER-12345", signatures.get(0).getText());
        }
    }
}

Entegrasyon Kontrol Listesi

  • ✅ Desteklenen tüm formatları test edin (PDF, DOCX, XLSX, PPTX, PNG).
  • ✅ Barkodların yazdır‑tara döngüsünden sonra ayakta kalmasını doğrulayın.
  • ✅ Maksimum uzunluktaki veri dizeleriyle stres testi yapın.
  • ✅ A4, Letter ve özel sayfa boyutlarında konumlamayı doğrulayın.
  • ✅ Birden fazla belge üzerinde eşzamanlı imzalama çalıştırın.
  • ✅ 500 sayfadan büyük belgeler için bellek kullanımını izleyin.
  • ✅ Barkod tarayıcıların çıktıyı güvenilir şekilde okuduğundan emin olun.

Günlükleme ve İzleme

Her işlem etrafına anlamlı günlükler ekleyin:

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class DocumentSigningService {
    private static final Logger logger = LoggerFactory.getLogger(DocumentSigningService.class);
    
    public void signDocument(String docPath, String barcodeData) {
        logger.info("Starting signature process for document: {}", docPath);
        logger.debug("Barcode data length: {} characters", barcodeData.length());
        
        try (Signature signature = new Signature(docPath)) {
            BarcodeSignOptions options = new BarcodeSignOptions(barcodeData, BarcodeTypes.Code128);
            
            long startTime = System.currentTimeMillis();
            signature.sign(docPath + ".signed", options);
            long duration = System.currentTimeMillis() - startTime;
            
            logger.info("Successfully signed document in {}ms", duration);
        } catch (Exception e) {
            logger.error("Failed to sign document: {}", docPath, e);
            throw new RuntimeException("Signature operation failed", e);
        }
    }
}

İşleme süresi, bellek tüketimi ve hata oranları gibi ana metrikleri izleyin:

// Track success/failure rates
metricsService.incrementCounter("signature.sign.success");
metricsService.incrementCounter("signature.verify.failure");

// Track performance
metricsService.recordTimer("signature.sign.duration", duration);

// Track document sizes
metricsService.recordHistogram("signature.document.pages", pageCount);

Gerçek Dünya Kullanımından Pro İpuçları

Toplu İşleme Stratejisi Yüzlerce dosyayla çalışırken, dosyaları toplu işleyin ve ilerlemeyi raporlayın:

public void signBatch(List<String> documents, String barcodePrefix) {
    int total = documents.size();
    int completed = 0;
    int failed = 0;
    
    for (String docPath : documents) {
        try {
            String barcodeData = barcodePrefix + "-" + UUID.randomUUID().toString();
            signDocument(docPath, barcodeData);
            completed++;
            
            if (completed % 10 == 0) {
                logger.info("Progress: {}/{} documents signed", completed, total);
            }
        } catch (Exception e) {
            failed++;
            logger.warn("Failed to sign: {}", docPath, e);
        }
    }
    
    logger.info("Batch complete: {} succeeded, {} failed", completed, failed);
}

Yapılandırmayı Dışa Aktar Barkod ayarlarını (tip, boyut, renk) yeniden derlemeden kolayca ayarlamak için bir properties dosyasında saklayın:

public class BarcodeConfig {
    private int defaultWidth = 100;
    private int defaultHeight = 40;
    private String defaultBarcodeType = "Code128";
    private String defaultColor = "BLACK";
    
    // Load from properties file or environment variables
    public BarcodeConfig() {
        this.defaultWidth = Integer.parseInt(
            System.getProperty("barcode.width", "100")
        );
        // ... load other properties
    }
    
    public BarcodeSignOptions createDefaultOptions(String text) {
        BarcodeSignOptions options = new BarcodeSignOptions(text, getBarcodeType());
        options.setWidth(defaultWidth);
        options.setHeight(defaultHeight);
        options.setForeColor(getColor());
        return options;
    }
}

Barkod Yükünü Standartlaştır Ayrılmış bir format (EMPID|TIMESTAMP|DOCID) kullanarak ayrıştırmayı basit ve tutarlı hale getirin:

public class BarcodeDataBuilder {
    private String userId;
    private String action;
    private LocalDateTime timestamp;
    private String documentId;
    
    public BarcodeDataBuilder setUserId(String userId) {
        this.userId = userId;
        return this;
    }
    
    public BarcodeDataBuilder setAction(String action) {
        this.action = action;
        return this;
    }
    
    public BarcodeDataBuilder setDocumentId(String documentId) {
        this.documentId = documentId;
        return this;
    }
    
    public String build() {
        this.timestamp = LocalDateTime.now();
        
        // Format: VERSION|USER|ACTION|DOC_ID|TIMESTAMP|CHECKSUM
        String data = String.join("|",
            "v1",
            userId,
            action,
            documentId,
            timestamp.toString()
        );
        
        // Add simple checksum
        int checksum = data.hashCode();
        return data + "|" + checksum;
    }
    
    public static ParsedBarcodeData parse(String barcodeData) {
        String[] parts = barcodeData.split("\\|");
        if (parts.length != 6 || !parts[0].equals("v1")) {
            throw new IllegalArgumentException("Invalid barcode format");
        }
        
        return new ParsedBarcodeData(parts[1], parts[2], parts[3], 
                                     LocalDateTime.parse(parts[4]));
    }
}

// Usage:
String barcodeData = new BarcodeDataBuilder()
    .setUserId("john.smith")
    .setAction("APPROVED")
    .setDocumentId("INV-2025-042")
    .build();

Belge Tipini Otomatik Algıla Hedef PDF, Word veya görüntü olup olmadığına göre barkod boyutlarını ayarlayın:

public BarcodeSignOptions getOptimalOptions(String documentPath, String text) {
    String extension = documentPath.substring(documentPath.lastIndexOf(".") + 1).toLowerCase();
    
    BarcodeSignOptions options = new BarcodeSignOptions(text, BarcodeTypes.Code128);
    
    switch (extension) {
        case "pdf":
            // PDFs can handle larger, detailed barcodes
            options.setWidth(150);
            options.setHeight(50);
            break;
        case "docx":
        case "doc":
            // Word docs need compact signatures that don't disrupt flow
            options.setWidth(100);
            options.setHeight(35);
            options.setVerticalAlignment(VerticalAlignment.Bottom);
            break;
        case "xlsx":
        case "xls":
            // Excel needs signatures that don't obscure data
            options.setWidth(80);
            options.setHeight(30);
            options.setHorizontalAlignment(HorizontalAlignment.Right);
            break;
        default:
            // Safe defaults
            options.setWidth(100);
            options.setHeight(40);
    }
    
    return options;
}

Ek Kaynaklar

Sıkça Sorulan Sorular

S: GroupDocs.Signature’ı Java 17 ile kullanabilir miyim?
C: Evet – kütüphane JDK 8, 11 ve 17 ile tam uyumludur.

S: Barkod yazdır‑tara döngüsünden sonra ayakta kalır mı?
C: Yeterli boyut ve kontrastla Code128 veya QR kullanırsanız, barkod yazdırıp taradıktan sonra da taranabilir kalır.

S: Tek bir belge kaç barkod içerebilir?
C: Katı bir limit yok; ancak optimum performans için toplam sayıyı belge başına 200’ün altında tutun.

S: Geliştirme derlemeleri için lisans gerekli mi?
C: Geçici lisans değerlendirme filigranlarını kaldırır; tam lisans herhangi bir üretim dağıtımı için zorunludur.

S: Şifre korumalı PDF’leri imzalayabilir miyim?
C: Evet – Signature nesnesi oluştururken şifreyi sağlayın; API dosyayı dahili olarak açar.


Last Updated: 2026-07-15
Tested With: GroupDocs.Signature 23.9 for Java
Author: GroupDocs