[Git][java-team/libsejda-commons-java][upstream] New upstream version 1.1.6
Markus Koschany
gitlab at salsa.debian.org
Sat Jan 30 23:39:15 GMT 2021
Markus Koschany pushed to branch upstream at Debian Java Maintainers / libsejda-commons-java
Commits:
3d141f3c by Markus Koschany at 2021-01-31T00:32:56+01:00
New upstream version 1.1.6
- - - - -
3 changed files:
- pom.xml
- src/main/java/org/sejda/commons/util/NumericalSortFilenameComparator.java
- src/test/java/org/sejda/commons/util/NumericalSortFilenameComparatorTest.java
Changes:
=====================================
pom.xml
=====================================
@@ -5,7 +5,7 @@
<artifactId>sejda-commons</artifactId>
<packaging>jar</packaging>
<name>sejda-commons</name>
- <version>1.1.4</version>
+ <version>1.1.6</version>
<description>A collection of utilities and common classes.</description>
<url>http://www.sejda.org</url>
@@ -37,7 +37,7 @@
<connection>scm:git:git at github.com:torakiki/sejda-commons.git</connection>
<developerConnection>scm:git:git at github.com:torakiki/sejda-commons.git</developerConnection>
<url>scm:git:git at github.com:torakiki/sejda-commons.git</url>
- <tag>v1.1.4</tag>
+ <tag>v1.1.6</tag>
</scm>
<developers>
=====================================
src/main/java/org/sejda/commons/util/NumericalSortFilenameComparator.java
=====================================
@@ -1,5 +1,5 @@
/*
- * Copyright 2020 Sober Lemur S.a.s. di Vacondio Andrea and Sejda BV
+ * Copyright 2018 Sober Lemur S.a.s. di Vacondio Andrea and Sejda BV
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -15,51 +15,104 @@
*/
package org.sejda.commons.util;
+import static java.util.Comparator.comparing;
+import static java.util.Comparator.nullsLast;
import static java.util.Objects.nonNull;
+import static java.util.Optional.ofNullable;
+import static org.sejda.commons.util.StringUtils.isEmpty;
+import static org.sejda.commons.util.StringUtils.isNotEmpty;
import java.io.File;
import java.math.BigInteger;
import java.util.Comparator;
-import java.util.Optional;
import java.util.function.Function;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
/**
- * Comparator for filenames that performs a numerical sort if the file names start with digits, returns 0 in any other case.
+ * Comparator for filenames that performs a numerical sort if the file names start or end with digits. It allows to specify a fallback comparator to use in case the numerical sort
+ * fails. The goal is to behave as close as possible to file managers sorting results.
*
* @author Andrea Vacondio
*
*/
public class NumericalSortFilenameComparator implements Comparator<File> {
- public static Logger LOG = LoggerFactory.getLogger(NumericalSortFilenameComparator.class);
- private Pattern pattern = Pattern.compile("^(\\d*)(.*)$");
+ private static Pattern PATTERN = Pattern.compile("^(\\d*)(\\D*)(\\d*)$");
+
+ private static Function<String, BigInteger> DIGITS_EXTRACTOR = (g) -> {
+ return ofNullable(g).filter(StringUtils::isNotEmpty).map(BigInteger::new).orElse(null);
+ };
+
+ private static Comparator<String> BIG_INT_COMPARATOR = (a, b) -> {
+ BigInteger bigA = DIGITS_EXTRACTOR.apply(a);
+ BigInteger bigB = DIGITS_EXTRACTOR.apply(b);
+ if (nonNull(bigA) && nonNull(bigB)) {
+ return bigA.compareTo(bigB);
+ }
+ return 0;
+ };
- private Function<File, BigInteger> leadingDigits = (f) -> {
- if (nonNull(f)) {
- Matcher matcher = pattern.matcher(f.getName().toLowerCase());
- if (matcher.matches()) {
- return Optional.of(matcher.group(1)).filter(StringUtils::isNotEmpty).map(BigInteger::new).orElse(null);
+ private static Comparator<String> STRING_COMPARATOR = (a, b) -> {
+ if (isNotEmpty(a) && isNotEmpty(b)) {
+ return a.compareToIgnoreCase(b);
+ }
+ return 0;
+ };
+
+ private static String basename(File file) {
+ if (nonNull(file)) {
+ String filename = file.getName();
+ int index = filename.lastIndexOf('.');
+ if (index > 0) {
+ return filename.substring(0, index);
+ }
+ if (StringUtils.isNotEmpty(filename)) {
+ return filename;
}
}
return null;
- };
+ }
+
+ private static Comparator<Matcher> MATCHER_COMPARATOR = comparing((Matcher m) -> m.group(1), BIG_INT_COMPARATOR)
+ .thenComparing(comparing(m -> m.group(2), STRING_COMPARATOR))
+ .thenComparing(comparing(m -> m.group(3), BIG_INT_COMPARATOR));
+
+ private Comparator<File> fallback;
+
+ /**
+ * @param fallback
+ * the comparator to use when numerical sorting fails. Default is file name case insensitive compare
+ */
+ public NumericalSortFilenameComparator(Comparator<File> fallback) {
+ this.fallback = ofNullable(fallback).orElse(nullsLast(comparing(File::getName, String.CASE_INSENSITIVE_ORDER)));
+ }
+
+ /**
+ * Comparator performing numerical sort with fallback to file name case insensitive compare in case numerical sort fails
+ */
+ public NumericalSortFilenameComparator() {
+ this(null);
+ }
@Override
public int compare(File a, File b) {
- try {
- BigInteger bigA = leadingDigits.apply(a);
- BigInteger bigB = leadingDigits.apply(b);
- if (nonNull(bigA) && nonNull(bigB)) {
- return bigA.compareTo(bigB);
- }
- } catch (NumberFormatException | IllegalStateException e) {
- LOG.warn("Unexpected conversion issue", e);
+ Matcher m1 = ofNullable(a).map(NumericalSortFilenameComparator::basename).map(PATTERN::matcher)
+ .filter(Matcher::matches).orElse(null);
+ Matcher m2 = ofNullable(b).map(NumericalSortFilenameComparator::basename).map(PATTERN::matcher)
+ .filter(Matcher::matches).orElse(null);
+
+ if (nonNull(m1) && nonNull(m2) && (isEmpty(m1.group(1)) ^ isEmpty(m2.group(1)))) {
+ // one start with digits the other doesn't, we can just go with the fallback
+ return fallback.compare(a, b);
}
- return 0;
+
+ int retVal = nullsLast(MATCHER_COMPARATOR).compare(m1, m2);
+ if (retVal == 0) {
+ // from the numerical sort of point of view they are equivalent (ex. 001banana.pdf and 1banana.pdf)
+ return fallback.compare(a, b);
+ }
+ return retVal;
}
+
}
=====================================
src/test/java/org/sejda/commons/util/NumericalSortFilenameComparatorTest.java
=====================================
@@ -1,5 +1,5 @@
/*
- * Copyright 2020 Sober Lemur S.a.s. di Vacondio Andrea and Sejda BV
+ * Copyright 2018 Sober Lemur S.a.s. di Vacondio Andrea and Sejda BV
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -15,34 +15,64 @@
*/
package org.sejda.commons.util;
-import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertTrue;
import java.io.File;
import org.junit.jupiter.api.Test;
+/**
+ * @author Andrea Vacondio
+ *
+ */
public class NumericalSortFilenameComparatorTest {
-
@Test
public void nulls() {
- assertEquals(0, new NumericalSortFilenameComparator().compare(null, new File("bla")));
- assertEquals(0, new NumericalSortFilenameComparator().compare(null, null));
- assertEquals(0, new NumericalSortFilenameComparator().compare(new File("bla"), null));
+ NumericalSortFilenameComparator victim = new NumericalSortFilenameComparator();
+ assertTrue(victim.compare(null, new File("bla")) > 0);
+ assertTrue(victim.compare(null, null) == 0);
+ assertTrue(victim.compare(new File("bla"), null) < 0);
}
@Test
public void nonDigit() {
- assertEquals(0, new NumericalSortFilenameComparator().compare(new File("123.pdf"), new File("bla.pdf")));
- assertEquals(0, new NumericalSortFilenameComparator().compare(new File("bla"), new File("123.pdf")));
+ NumericalSortFilenameComparator victim = new NumericalSortFilenameComparator();
+ assertTrue(victim.compare(new File("123.pdf"), new File("bla.pdf")) < 0);
+ assertTrue(victim.compare(new File("bla.pdf"), new File("123.pdf")) > 0);
+ assertTrue(victim.compare(new File("bla.pdf"), new File("abc.pdf")) > 0);
+ assertTrue(victim.compare(new File("bla.pdf"), new File("bla.pdf")) == 0);
+ assertTrue(victim.compare(new File("bla.pdf"), new File("bla123.pdf")) < 0);
+ assertTrue(victim.compare(new File("123bla.pdf"), new File("123.pdf")) > 0);
+ }
+
+ @Test
+ public void leadingDigits() {
+ NumericalSortFilenameComparator victim = new NumericalSortFilenameComparator();
+ assertTrue(victim.compare(new File("123.pdf"), new File("1bla.pdf")) > 0);
+ assertTrue(victim.compare(new File("123bla.pdf"), new File("1bla.pdf")) > 0);
+ assertTrue(victim.compare(new File("1.pdf"), new File("001bla.pdf")) > 0);
+ assertTrue(victim.compare(new File("1bla.pdf"), new File("001bla.pdf")) > 0);
+ assertTrue(victim.compare(new File("005bla.pdf"), new File("500.pdf")) < 0);
+ }
+
+ @Test
+ public void trailingDigits() {
+ NumericalSortFilenameComparator victim = new NumericalSortFilenameComparator();
+ assertTrue(victim.compare(new File("123.pdf"), new File("bla1.pdf")) < 0);
+ assertTrue(victim.compare(new File("bla 10.pdf"), new File("bla 1.pdf")) > 0);
+ assertTrue(victim.compare(new File("1.pdf"), new File("bla001.pdf")) < 0);
+ assertTrue(victim.compare(new File("bla1.pdf"), new File("bla001.pdf")) > 0);
+ assertTrue(victim.compare(new File("bla005.pdf"), new File("500.pdf")) > 0);
}
@Test
- public void digits() {
- assertEquals(1, new NumericalSortFilenameComparator().compare(new File("123.pdf"), new File("1bla.pdf")));
- assertEquals(1, new NumericalSortFilenameComparator().compare(new File("123bla.pdf"), new File("1bla.pdf")));
- assertEquals(0, new NumericalSortFilenameComparator().compare(new File("1.pdf"), new File("001bla.pdf")));
- assertEquals(0, new NumericalSortFilenameComparator().compare(new File("1bla.pdf"), new File("001bla.pdf")));
- assertEquals(-1, new NumericalSortFilenameComparator().compare(new File("005bla.pdf"), new File("500.pdf")));
- assertEquals(-1, new NumericalSortFilenameComparator().compare(new File("005bla.pdf"), new File("500bla.pdf")));
+ public void mixed() {
+ NumericalSortFilenameComparator victim = new NumericalSortFilenameComparator();
+ assertTrue(victim.compare(new File("bla 1.pdf"), new File("vol 10.pdf")) < 0);
+ assertTrue(victim.compare(new File("20 bla 1.pdf"), new File("03 vol 10.pdf")) > 0);
+ assertTrue(victim.compare(new File("20 bla 1.pdf"), new File("20 bla 5.pdf")) < 0);
+ assertTrue(victim.compare(new File("banana.pdf"), new File("avocado.pdf")) > 0);
+ assertTrue(victim.compare(new File("chuck.pdf"), new File("chuck.abc")) > 0);
+ assertTrue(victim.compare(new File("1234file.pdf"), new File("chuck.abc")) < 0);
}
}
View it on GitLab: https://salsa.debian.org/java-team/libsejda-commons-java/-/commit/3d141f3c597810c067cedd2b1d37daf6f9030bdb
--
View it on GitLab: https://salsa.debian.org/java-team/libsejda-commons-java/-/commit/3d141f3c597810c067cedd2b1d37daf6f9030bdb
You're receiving this email because of your account on salsa.debian.org.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://alioth-lists.debian.net/pipermail/pkg-java-commits/attachments/20210130/a8b32caf/attachment.html>
More information about the pkg-java-commits
mailing list