Skip to content

Commit 1eaa8c3

Browse files
committed
[bugfix] Fix handling of entry-filter, entry-data, and entry-path functions in compression:unzip and compression:untar functions
1 parent 82ced9d commit 1eaa8c3

File tree

10 files changed

+644
-277
lines changed

10 files changed

+644
-277
lines changed

extensions/modules/compression/pom.xml

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -162,8 +162,14 @@
162162
<include>pom.xml</include>
163163
<include>src/test/resources-filtered/conf.xml</include>
164164
<include>src/test/resources/log4j2.xml</include>
165+
<include>src/test/xquery/modules/compression/unzip-tests.xql</include>
165166
<include>src/main/java/org/exist/xquery/modules/compression/AbstractCompressFunction.java</include>
167+
<include>src/main/java/org/exist/xquery/modules/compression/AbstractExtractFunction.java</include>
168+
<include>src/main/java/org/exist/xquery/modules/compression/CompressionModule.java</include>
166169
<include>src/main/java/org/exist/xquery/modules/compression/EntryFunctions.java</include>
170+
<include>src/main/java/org/exist/xquery/modules/compression/UnTarFunction.java</include>
171+
<include>src/main/java/org/exist/xquery/modules/compression/UnZipFunction.java</include>
172+
167173
</includes>
168174
</licenseSet>
169175

@@ -176,9 +182,15 @@
176182
<exclude>pom.xml</exclude>
177183
<exclude>src/test/resources-filtered/conf.xml</exclude>
178184
<exclude>src/test/resources/log4j2.xml</exclude>
185+
<exclude>src/test/xquery/modules/compression/unzip-tests.xql</exclude>
186+
<exclude>src/test/xquery/modules/compression/zip-tests.xql</exclude>
179187
<exclude>src/test/xquery/modules/compression/zip-unzip-tests.xqm</exclude>
180188
<exclude>src/main/java/org/exist/xquery/modules/compression/AbstractCompressFunction.java</exclude>
189+
<exclude>src/main/java/org/exist/xquery/modules/compression/AbstractExtractFunction.java</exclude>
190+
<exclude>src/main/java/org/exist/xquery/modules/compression/CompressionModule.java</exclude>
181191
<exclude>src/main/java/org/exist/xquery/modules/compression/EntryFunctions.java</exclude>
192+
<exclude>src/main/java/org/exist/xquery/modules/compression/UnTarFunction.java</exclude>
193+
<exclude>src/main/java/org/exist/xquery/modules/compression/UnZipFunction.java</exclude>
182194
</excludes>
183195
</licenseSet>
184196

extensions/modules/compression/src/main/java/org/exist/xquery/modules/compression/AbstractCompressFunction.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -88,10 +88,10 @@
8888

8989
/**
9090
* Compresses a sequence of resources and/or collections
91-
*
92-
* @author <a href="mailto:adam@exist-db.org">Adam Retter</a>
91+
*
92+
* @author <a href="mailto:adam@evolvedbinary.com">Adam Retter</a>
9393
* @author <a href="mailto:[email protected]">Leif-Jöran Olsson</a>
94-
* @version 1.0
94+
* @version 2.0
9595
*/
9696
public abstract class AbstractCompressFunction extends BasicFunction
9797
{
@@ -227,7 +227,7 @@ private void compressFromUri(final OutputStream os, final URI uri, final boolean
227227
collection.close();
228228

229229
if (doc == null) {
230-
throw new XPathException(this, "Invalid URI: " + uri.toString());
230+
throw new XPathException(this, "No document available at URI: " + uri.toString());
231231
}
232232

233233
compressResource(os, doc.getDocument(), useHierarchy, stripOffset, method, resourceName, sbWriter, chksum);

extensions/modules/compression/src/main/java/org/exist/xquery/modules/compression/AbstractExtractFunction.java

Lines changed: 232 additions & 150 deletions
Large diffs are not rendered by default.

extensions/modules/compression/src/main/java/org/exist/xquery/modules/compression/CompressionModule.java

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,28 @@
11
/*
2+
* Elemental
3+
* Copyright (C) 2024, Evolved Binary Ltd
4+
*
5+
6+
* https://www.evolvedbinary.com | https://www.elemental.xyz
7+
*
8+
* This library is free software; you can redistribute it and/or
9+
* modify it under the terms of the GNU Lesser General Public
10+
* License as published by the Free Software Foundation; version 2.1.
11+
*
12+
* This library is distributed in the hope that it will be useful,
13+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15+
* Lesser General Public License for more details.
16+
*
17+
* You should have received a copy of the GNU Lesser General Public
18+
* License along with this library; if not, write to the Free Software
19+
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20+
*
21+
* NOTE: Parts of this file contain code from 'The eXist-db Authors'.
22+
* The original license header is included below.
23+
*
24+
* =====================================================================
25+
*
226
* eXist-db Open Source Native XML Database
327
* Copyright (C) 2001 The eXist-db Authors
428
*
@@ -33,7 +57,7 @@
3357
/**
3458
* XQuery Extension module for compression and de-compression functions
3559
*
36-
* @author <a href="mailto:adam@exist-db.org">Adam Retter</a>
60+
* @author <a href="mailto:adam@evolvedbinary.com">Adam Retter</a>
3761
* @author ljo
3862
*/
3963
public class CompressionModule extends AbstractInternalModule {
@@ -53,7 +77,8 @@ public class CompressionModule extends AbstractInternalModule {
5377
functionDefs(UnZipFunction.class,
5478
UnZipFunction.FS_UNZIP[0],
5579
UnZipFunction.FS_UNZIP[1],
56-
UnZipFunction.FS_UNZIP[2]
80+
UnZipFunction.FS_UNZIP[2],
81+
UnZipFunction.FS_UNZIP[3]
5782
),
5883
functionDefs(GZipFunction.class,
5984
GZipFunction.signatures[0]
@@ -77,7 +102,8 @@ public class CompressionModule extends AbstractInternalModule {
77102
functionDefs(UnTarFunction.class,
78103
UnTarFunction.FS_UNTAR[0],
79104
UnTarFunction.FS_UNTAR[1],
80-
UnTarFunction.FS_UNTAR[2]
105+
UnTarFunction.FS_UNTAR[2],
106+
UnTarFunction.FS_UNTAR[3]
81107
),
82108
functionDefs(EntryFunctions.class,
83109
EntryFunctions.FS_NO_FILTER[0],

extensions/modules/compression/src/main/java/org/exist/xquery/modules/compression/EntryFunctions.java

Lines changed: 42 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -50,8 +50,12 @@
5050
import org.exist.EXistException;
5151
import org.exist.collections.Collection;
5252
import org.exist.collections.triggers.TriggerException;
53+
import org.exist.dom.persistent.DocumentImpl;
54+
import org.exist.dom.persistent.NodeImpl;
55+
import org.exist.dom.persistent.NodeProxy;
5356
import org.exist.security.PermissionDeniedException;
5457
import org.exist.storage.lock.Lock;
58+
import org.exist.storage.serializers.Serializer;
5559
import org.exist.storage.txn.TransactionException;
5660
import org.exist.storage.txn.Txn;
5761
import org.exist.util.BinaryValueInputSource;
@@ -61,11 +65,12 @@
6165
import org.exist.xmldb.XmldbURI;
6266
import org.exist.xquery.*;
6367
import org.exist.xquery.value.*;
68+
import org.w3c.dom.Document;
69+
import org.w3c.dom.Node;
6470
import org.xml.sax.SAXException;
6571

66-
import java.io.BufferedOutputStream;
67-
import java.io.IOException;
68-
import java.io.OutputStream;
72+
import javax.annotation.Nullable;
73+
import java.io.*;
6974
import java.net.URI;
7075
import java.nio.file.Files;
7176
import java.nio.file.Path;
@@ -253,8 +258,31 @@ protected void eval(final String path, final DataType dataType, final Optional<I
253258
if(data.isPresent()) {
254259
// store the resource
255260
try (final OutputStream os = new BufferedOutputStream(Files.newOutputStream(destPath, StandardOpenOption.WRITE, StandardOpenOption.CREATE, StandardOpenOption.TRUNCATE_EXISTING))) {
256-
((BinaryValue)data.get()).streamBinaryTo(os);
257-
} catch (final IOException e) {
261+
if (data.get() instanceof BinaryValue) {
262+
// binary
263+
((BinaryValue)data.get()).streamBinaryTo(os);
264+
} else {
265+
// XML
266+
final Serializer serializer = context.getBroker().borrowSerializer();
267+
try {
268+
serializer.setUser(context.getSubject());
269+
serializer.setProperty("omit-xml-declaration", "no");
270+
271+
final NodeValue nodeValue;
272+
if (data.get() instanceof NodeValue || data.get() instanceof NodeProxy) {
273+
nodeValue = (NodeValue) data.get();
274+
} else {
275+
final NodeImpl n = (NodeImpl) data.get();
276+
nodeValue = new NodeProxy(n instanceof DocumentImpl ? (DocumentImpl)n : (DocumentImpl)n.getOwnerDocument(), n.getNodeId());
277+
}
278+
try (final Writer writer = new OutputStreamWriter(os)) {
279+
serializer.serialize(nodeValue, writer);
280+
}
281+
} finally {
282+
context.getBroker().returnSerializer(serializer);
283+
}
284+
}
285+
} catch (final IOException | SAXException e) {
258286
throw new XPathException(this, "Cannot serialize file. A problem occurred while serializing the binary data: " + e.getMessage(), e);
259287
}
260288
}
@@ -307,9 +335,16 @@ protected void eval(final String path, final DataType dataType, final Optional<I
307335
try (final Txn transaction = context.getBroker().getBrokerPool().getTransactionManager().beginTransaction()) {
308336

309337
try (final Collection collection = context.getBroker().openCollection(destPath.removeLastSegment(), Lock.LockMode.WRITE_LOCK)) {
310-
final BinaryValue binaryValue = (BinaryValue) data.get();
311338
final MimeType mimeType = MimeTable.getInstance().getContentTypeFor(destPath.lastSegment());
312-
context.getBroker().storeDocument(transaction, destPath.lastSegment(), new BinaryValueInputSource(binaryValue), mimeType, collection);
339+
340+
if (data.get() instanceof BinaryValue) {
341+
// binary
342+
final BinaryValue binaryValue = (BinaryValue) data.get();
343+
context.getBroker().storeDocument(transaction, destPath.lastSegment(), new BinaryValueInputSource(binaryValue), mimeType, collection);
344+
} else {
345+
// XML
346+
context.getBroker().storeDocument(transaction, destPath.lastSegment(), (Node)data.get(), mimeType, collection);
347+
}
313348
}
314349
transaction.commit();
315350
} catch (final IOException | PermissionDeniedException | EXistException | LockException | SAXException e) {

0 commit comments

Comments
 (0)