CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/maven-biz-a-qute-bnd--biz-a-qute-bndlib

bndlib: A Swiss Army Knife for OSGi providing comprehensive bundle manipulation and analysis capabilities

Pending
Overview
Eval results
Files

jar-resource-management.mddocs/

JAR and Resource Management

Low-level JAR file manipulation and resource handling for OSGi bundles, providing fine-grained control over bundle contents.

Capabilities

Jar

Represents a JAR file with OSGi-specific operations for reading, writing, and manipulating bundle contents.

/**
 * Represents a JAR file with OSGi-specific operations
 */
public class Jar implements Closeable {
    /** Create empty JAR */
    public Jar(String name);
    
    /** Create JAR from file */
    public Jar(File file) throws IOException;
    
    /** Create JAR from input stream */
    public Jar(String name, InputStream in) throws IOException;
    
    /** Add resource to JAR */
    public void putResource(String path, Resource resource);
    
    /** Get resource from JAR */
    public Resource getResource(String path);
    
    /** Remove resource from JAR */
    public void remove(String path);
    
    /** Write JAR to file */
    public void write(File file) throws Exception;
    
    /** Write JAR to output stream */
    public void write(OutputStream out) throws IOException;
    
    /** Get JAR manifest */
    public Manifest getManifest() throws Exception;
    
    /** Set JAR manifest */
    public void setManifest(Manifest manifest);
    
    /** Get bundle symbolic name from manifest */
    public String getBsn();
    
    /** Get bundle version from manifest */
    public String getVersion();
    
    /** Get all resource paths */
    public Set<String> getResources();
    
    /** Get resources matching pattern */
    public Map<String, Resource> getResources(String pattern);
    
    /** Get directories in JAR */
    public Set<String> getDirectories();
    
    /** Get JAR name */
    public String getName();
    
    /** Set JAR name */
    public void setName(String name);
    
    /** Get last modified time */
    public long lastModified();
    
    /** Close and clean up resources */
    public void close();
}

Usage Examples:

import aQute.bnd.osgi.Jar;
import aQute.bnd.osgi.Resource;
import java.util.jar.Manifest;

// Create and populate JAR
Jar jar = new Jar("mybundle");

// Set manifest
Manifest manifest = new Manifest();
manifest.getMainAttributes().putValue("Bundle-SymbolicName", "com.example.mybundle");
manifest.getMainAttributes().putValue("Bundle-Version", "1.0.0");
jar.setManifest(manifest);

// Add resources
jar.putResource("com/example/MyClass.class", 
    new FileResource(new File("target/classes/com/example/MyClass.class")));
jar.putResource("META-INF/MANIFEST.MF", 
    new ManifestResource(manifest));

// Write to file  
jar.write(new File("mybundle.jar"));
jar.close();

// Read existing JAR
Jar existingJar = new Jar(new File("existing.jar"));
System.out.println("Bundle: " + existingJar.getBsn() + " v" + existingJar.getVersion());

// List all resources
for (String path : existingJar.getResources()) {
    System.out.println("Resource: " + path);
}

existingJar.close();

Resource

Interface representing a resource within a JAR file, providing access to content and metadata.

/**
 * Represents a resource in a JAR file
 */
public interface Resource extends Closeable {
    /** Open input stream to read resource content */
    public InputStream openInputStream() throws IOException;
    
    /** Write resource content to output stream */
    public void write(OutputStream out) throws Exception;
    
    /** Get last modified time */
    public long lastModified();
    
    /** Set extra data associated with resource */
    public void setExtra(String extra);
    
    /** Get extra data */
    public String getExtra();
    
    /** Get resource size */
    public long size() throws Exception;
    
    /** Close resource and clean up */
    public void close();
}

Common Resource Implementations

Standard resource implementations for different content types.

/**
 * Resource backed by a file
 */
public class FileResource implements Resource {
    public FileResource(File file);
    public File getFile();
}

/**
 * Resource with string content
 */
public class EmbeddedResource implements Resource {
    public EmbeddedResource(byte[] data, long lastModified);
    public EmbeddedResource(String data, long lastModified);
    public byte[] getData();
}

/**
 * Resource backed by URL
 */
public class URLResource implements Resource {
    public URLResource(URL url);
    public URL getURL();
}

/**
 * Resource representing a JAR manifest
 */
public class ManifestResource implements Resource {
    public ManifestResource(Manifest manifest);
    public Manifest getManifest();
}

/**
 * Resource from ZIP entry
 */
public class ZipResource implements Resource {
    public ZipResource(ZipFile zip, ZipEntry entry);
    public ZipEntry getEntry();
}

Resource Usage Examples:

import aQute.bnd.osgi.*;

// Working with different resource types
Jar jar = new Jar("example");

// File resource
jar.putResource("config/app.properties", 
    new FileResource(new File("src/main/resources/app.properties")));

// String resource
String xmlContent = "<?xml version=\"1.0\"?><config></config>";
jar.putResource("META-INF/config.xml", 
    new EmbeddedResource(xmlContent, System.currentTimeMillis()));

// URL resource (from classpath)
URL resourceUrl = getClass().getResource("/template.txt");
jar.putResource("templates/default.txt", 
    new URLResource(resourceUrl));

// Read resource content
Resource configResource = jar.getResource("config/app.properties");
if (configResource != null) {
    try (InputStream in = configResource.openInputStream()) {
        Properties props = new Properties();
        props.load(in);
        System.out.println("Loaded " + props.size() + " properties");
    }
}

jar.close();

JAR Manipulation Utilities

Advanced JAR manipulation and analysis utilities.

/**
 * Utilities for JAR analysis and manipulation
 */
public class JarUtils {
    /** Copy JAR with filtering */
    public static void copy(Jar source, Jar dest, String pattern);
    
    /** Merge multiple JARs */
    public static Jar merge(Jar... jars) throws IOException;
    
    /** Extract JAR to directory */
    public static void extract(Jar jar, File targetDir) throws IOException;
    
    /** Create JAR from directory */
    public static Jar create(File sourceDir) throws IOException;
    
    /** Compare JAR contents */
    public static boolean equals(Jar jar1, Jar jar2);
    
    /** Get JAR checksum */
    public static String checksum(Jar jar) throws Exception;
}

Bundle Information

Classes for extracting and working with OSGi bundle metadata.

/**
 * Bundle information extracted from manifest
 */
public class BundleInfo {
    public String getSymbolicName();
    public Version getVersion();
    public String getName();
    public String getDescription();
    public String getVendor();
    public List<String> getExportedPackages();
    public List<String> getImportedPackages();
    public List<String> getRequiredBundles();
    public boolean isFragment();
    public String getFragmentHost();
}

/**
 * Utility for extracting bundle information
 */
public class BundleInfoReader {
    /** Read bundle info from JAR */
    public static BundleInfo read(Jar jar) throws Exception;
    
    /** Read bundle info from file */
    public static BundleInfo read(File bundleFile) throws Exception;
    
    /** Read bundle info from manifest */
    public static BundleInfo read(Manifest manifest);
}

Complete JAR Processing Example:

import aQute.bnd.osgi.*;
import java.util.jar.Manifest;

// Complete JAR processing workflow
try {
    // Create new bundle JAR
    Jar bundle = new Jar("com.example.mybundle");
    
    // Create manifest
    Manifest manifest = new Manifest();
    manifest.getMainAttributes().putValue("Manifest-Version", "1.0");
    manifest.getMainAttributes().putValue("Bundle-ManifestVersion", "2");
    manifest.getMainAttributes().putValue("Bundle-SymbolicName", "com.example.mybundle");
    manifest.getMainAttributes().putValue("Bundle-Version", "1.0.0");
    manifest.getMainAttributes().putValue("Bundle-Name", "My Example Bundle");
    manifest.getMainAttributes().putValue("Export-Package", "com.example.api;version=\"1.0\"");
    manifest.getMainAttributes().putValue("Import-Package", "org.osgi.framework;version=\"[1.8,2)\"");
    
    bundle.setManifest(manifest);
    
    // Add class files
    File classesDir = new File("target/classes");
    if (classesDir.exists()) {
        addDirectory(bundle, classesDir, "");
    }
    
    // Add resources
    bundle.putResource("META-INF/spring/bundle-context.xml",
        new FileResource(new File("src/main/resources/bundle-context.xml")));
    
    // Write bundle
    File outputFile = new File("target/mybundle-1.0.0.jar");
    bundle.write(outputFile);
    
    System.out.println("Created bundle: " + outputFile);
    System.out.println("Bundle-SymbolicName: " + bundle.getBsn());
    System.out.println("Bundle-Version: " + bundle.getVersion());
    System.out.println("Resources: " + bundle.getResources().size());
    
    bundle.close();
    
} catch (Exception e) {
    System.err.println("Failed to create bundle: " + e.getMessage());
    e.printStackTrace();
}

// Helper method to add directory recursively
private static void addDirectory(Jar jar, File dir, String path) throws IOException {
    for (File file : dir.listFiles()) {
        String filePath = path.isEmpty() ? file.getName() : path + "/" + file.getName();
        if (file.isDirectory()) {
            addDirectory(jar, file, filePath);  
        } else {
            jar.putResource(filePath, new FileResource(file));
        }
    }
}

Install with Tessl CLI

npx tessl i tessl/maven-biz-a-qute-bnd--biz-a-qute-bndlib

docs

api-comparison-diffing.md

core-osgi-processing.md

header-processing.md

index.md

jar-resource-management.md

plugin-architecture.md

repository-system.md

version-management.md

workspace-project-management.md

tile.json