protected void packBundle(ZipOutputStream output, Bundle bundle) throws IOException {
   BundleFile bundleFile = bundle.getBundleFile();
   Filter filter = filters.get(bundle.getBundleID());
   List<String> pathes = bundleFile.getEntryPaths("/");
   for (String path : pathes) {
     packBundle(output, bundle, path, filter);
   }
 }
  protected void packBundle(ZipOutputStream output, Bundle bundle, String path, Filter filter)
      throws IOException {
    if (filter != null && !filter.accept(path)) {
      log(Level.FINE, "exclude {0}/{1}", new Object[] {bundle.getBundleID(), path});
      return;
    }
    BundleFile bundleFile = bundle.getBundleFile();
    if (bundleFile.isDirectory(path)) {
      List<String> entries = bundleFile.getEntryPaths(path);
      for (String entry : entries) {
        packBundle(output, bundle, entry, filter);
      }
      return;
    }

    // pack the JAR/ZIP
    BundleEntry bundleEntry = bundleFile.getEntry(path);
    if (path.endsWith(".jar") || path.endsWith(".zip")) {
      File tempZipFile = createTempFile(bundleEntry);
      try {
        ZipFile zipFile = new ZipFile(tempZipFile);
        try {
          packZip(output, bundleEntry, zipFile, filter);
        } finally {
          zipFile.close();
        }
      } finally {
        tempZipFile.delete();
      }
      return;
    }

    // pack the normal entry
    if (existingEntries.contains(path)) {
      log(Level.WARNING, "duplicate {0}/{1}", new Object[] {bundle.getBundleID(), path});
      return;
    }
    existingEntries.add(path);

    InputStream input = bundleEntry.getInputStream();
    try {
      ZipEntry zipEntry = new ZipEntry(bundleEntry.getName());
      zipEntry.setTime(bundleEntry.getTime());
      zipEntry.setSize(bundleEntry.getSize());
      output.putNextEntry(zipEntry);
      try {
        copyStream(input, output);
      } finally {
        output.closeEntry();
      }
    } finally {
      input.close();
    }
  }
 public void packFiles(ZipOutputStream zipOutput) throws IOException {
   // pack them together
   List<Bundle> bundles = framework.getAllBundles();
   for (Bundle bundle : bundles) {
     if (!bundle.isFragment()) {
       List<Bundle> fragments = bundle.getFragments();
       if (fragments != null) {
         for (Bundle fragment : fragments) {
           packBundle(zipOutput, fragment);
         }
       }
     }
     packBundle(zipOutput, bundle);
   }
 }
  public void packDescription(ZipOutputStream zipOutput)
      throws IOException, ParserConfigurationException, TransformerException {
    ZipEntry entry = new ZipEntry("plugin.xml");
    zipOutput.putNextEntry(entry);
    try {
      Document document = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
      Element documentRoot = document.createElement("plugin");
      document.appendChild(documentRoot);

      List<Bundle> bundles = framework.getAllBundles();
      for (Bundle bundle : bundles) {
        if (!bundle.isFragment()) {
          List<Bundle> fragments = bundle.getFragments();
          if (fragments != null) {
            for (Bundle fragment : fragments) {
              Document description = fragment.getDescription();
              if (description != null) {
                Node comment = document.createComment("import from " + fragment.getBundleID());
                document.getDocumentElement().appendChild(comment);
                appendDescription(document, description);
              }
            }
          }
        }
        Document description = bundle.getDescription();
        if (description != null) {
          Node comment = document.createComment("import from " + bundle.getBundleID());
          document.getDocumentElement().appendChild(comment);
          appendDescription(document, description);
        }
      }
      // Prepare the DOM document for writing
      Source source = new DOMSource(document);
      // Prepare the output file
      Result result = new StreamResult(zipOutput);
      // Write the DOM document to the file
      Transformer xformer = TransformerFactory.newInstance().newTransformer();
      xformer.transform(source, result);
    } finally {
      zipOutput.closeEntry();
    }
  }