Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bugfix patch #544

Merged
merged 19 commits into from
Apr 29, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
f7ccc24
build: corrected release date interpretation
novoj Apr 22, 2024
97acd42
fix: NullPointerException in tracing
novoj Apr 23, 2024
4195c5b
fix(#532): NPE when GQL query is sent without a name and tracing is e…
lukashornych Apr 24, 2024
4998132
Merge pull request #533 from FgForrest/532-npe-when-tracing-is-enable…
lukashornych Apr 24, 2024
9eb443e
fix(#534): log exception with log message so that consumers can bette…
lukashornych Apr 24, 2024
c23d7d0
Revert "fix(#534): log exception with log message so that consumers c…
lukashornych Apr 24, 2024
36874d7
ix(#534): log exception with log message so that consumers can better…
lukashornych Apr 24, 2024
abfbc15
Merge pull request #535 from FgForrest/534-log-exception-to-message-i…
lukashornych Apr 24, 2024
7345b90
fix (#536): Invalid OffsetDateTime comparison taking offset differenc…
novoj Apr 26, 2024
db00134
Merge pull request #539 from FgForrest/536-invalid-offsetdatetime-con…
novoj Apr 26, 2024
dd9a66a
fix(#537): Incorrect facet statistics difference when userFilter is used
novoj Apr 26, 2024
13ebcf0
Merge pull request #541 from FgForrest/537-incorrect-facet-statistics…
novoj Apr 26, 2024
323bb99
refactor(#542): Limit allocations when no changes in indexes occur
novoj Apr 26, 2024
095cd22
Merge pull request #543 from FgForrest/542-limit-allocations-when-no-…
novoj Apr 26, 2024
7c39dd4
fix: fixed invalid logging file definition
novoj Apr 29, 2024
abf0c31
chore: added `toString` method implementations for better readability
novoj Apr 29, 2024
6a90374
chore: added more debug information for bug hunting
novoj Apr 29, 2024
e28e2dd
build: updated SNAPSHOT to next version
novoj Apr 29, 2024
c832415
chore: better toString formatting
novoj Apr 29, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .github/workflows/docker-latest.yml
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ jobs:
echo "fullVersion=$(cat version.txt)" >> $GITHUB_ENV
echo "version=$(cat version.txt | cut -d'.' -f1,2)"
echo "version=$(cat version.txt | cut -d'.' -f1,2)" >> $GITHUB_ENV
echo "releaseDate=$(date +%Y-%m-%d)" >> $GITHUB_ENV

- name: Build and push Docker image
env:
Expand All @@ -77,3 +78,4 @@ jobs:
build-args: |
EVITA_JAR_NAME=${{ env.EVITA_JAR_NAME }}
VERSION=${{ env.fullVersion }}
RELEASE_DATE=${{ env.releaseDate }}
2 changes: 1 addition & 1 deletion .idea/runConfigurations/All_functional_tests.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion docker/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,14 @@ FROM index.docker.io/azul/zulu-openjdk-alpine:17-latest
## not supposed to be overriden in container
ARG EVITA_JAR_NAME
ARG VERSION=not_set
ARG RELEASE_DATE=not_set
ENV EVITA_HOME="/evita"
ENV EVITA_JAR_NAME="$EVITA_JAR_NAME"

# Labels with dynamic information based on environment variables and current date
LABEL vendor="FG Forrest, a.s." \
io.evitadb.version="${VERSION}" \
io.evitadb.release-date="$(date +%Y-%m-%d)"
io.evitadb.release-date="${RELEASE_DATE}"

USER root

Expand Down
2 changes: 1 addition & 1 deletion evita_api/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@
<parent>
<groupId>io.evitadb</groupId>
<artifactId>evita_root</artifactId>
<version>2024.4-SNAPSHOT</version>
<version>2024.5-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -176,4 +176,8 @@ public Entity mutate(@Nonnull EntitySchemaContract entitySchema, @Nullable Entit
.toList();
}

@Override
public String toString() {
return "entity `" + entityType + "` removal: " + entityPrimaryKey;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
import java.util.Iterator;
import java.util.Objects;
import java.util.Optional;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import static java.util.Optional.empty;
Expand Down Expand Up @@ -185,6 +186,12 @@ public Entity mutate(@Nonnull EntitySchemaContract entitySchema, @Nullable Entit
return localMutations;
}

@Override
public String toString() {
return "entity `" + entityType + "` upsert (" + entityType + "): " + entityPrimaryKey +
" and mutations: [" + localMutations.stream().map(Object::toString).collect(Collectors.joining(", ")) + "]";
}

@Override
public int hashCode() {
int result = entityPrimaryKey != null ? entityPrimaryKey.hashCode() : 0;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
import io.evitadb.api.requestResponse.data.AttributesContract.AttributeValue;
import io.evitadb.api.requestResponse.schema.EntitySchemaContract;
import io.evitadb.utils.ArrayUtils;
import io.evitadb.utils.StringUtils;

import javax.annotation.Nonnull;
import javax.annotation.Nullable;
Expand Down Expand Up @@ -106,7 +107,7 @@ public int hashCode() {

@Override
public String toString() {
return "upsert attribute `" + attributeKey + "` with value: " + value;
return "upsert attribute `" + attributeKey + "` with value: " + StringUtils.toString(value);
}

}
2 changes: 1 addition & 1 deletion evita_common/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
<parent>
<groupId>io.evitadb</groupId>
<artifactId>evita_root</artifactId>
<version>2024.4-SNAPSHOT</version>
<version>2024.5-SNAPSHOT</version>
</parent>
<dependencies>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
import java.io.Serializable;
import java.text.Collator;
import java.util.Comparator;
import java.util.Locale;

/**
* This comparator compares two string with respect to a national characters.
Expand All @@ -41,9 +42,13 @@ public class LocalizedStringComparator implements Comparator<String>, Serializab
@Serial private static final long serialVersionUID = 8102561596057708303L;
@Nonnull private final Collator collator;

public LocalizedStringComparator(@Nonnull Locale locale) {
this.collator = Collator.getInstance(locale);
}

@Override
public int compare(String o1, String o2) {
return collator.compare(o1, o2);
}

}
}
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ private ByteNumberRange(@Nullable Byte from, @Nullable Byte to) {
assertNotFloatingPointType(to, "to");
}

@Nonnull
@Override
public Range<Byte> cloneWithDifferentBounds(@Nullable Byte from, @Nullable Byte to) {
return new ByteNumberRange(from, to);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ private IntegerNumberRange(@Nullable Integer from, @Nullable Integer to) {
assertNotFloatingPointType(to, "to");
}

@Nonnull
@Override
public Range<Integer> cloneWithDifferentBounds(@Nullable Integer from, @Nullable Integer to) {
return new IntegerNumberRange(from, to);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ private LongNumberRange(@Nullable Long from, @Nullable Long to) {
assertNotFloatingPointType(to, "to");
}

@Nonnull
@Override
public Range<Long> cloneWithDifferentBounds(@Nullable Long from, @Nullable Long to) {
return new LongNumberRange(from, to);
Expand Down
14 changes: 10 additions & 4 deletions evita_common/src/main/java/io/evitadb/dataType/Range.java
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@
import io.evitadb.utils.ArrayUtils;
import io.evitadb.utils.Assert;

import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import java.lang.reflect.Array;
import java.util.ArrayList;
import java.util.Arrays;
Expand Down Expand Up @@ -58,8 +60,9 @@ public sealed interface Range<T> permits DateTimeRange, NumberRange {
*
* Because other ranges overlap one another.
*/
@Nonnull
@SuppressWarnings("unchecked")
static <S, T extends Range<S>> T[] consolidateRange(T[] ranges) {
static <S, T extends Range<S>> T[] consolidateRange(@Nonnull T[] ranges) {
if (ArrayUtils.isEmpty(ranges)) {
return ranges;
}
Expand Down Expand Up @@ -100,30 +103,33 @@ static <S, T extends Range<S>> T[] consolidateRange(T[] ranges) {
/**
* Returns original from value used when range was created without any loss of precision.
*/
@Nullable
T getPreciseFrom();

/**
* Returns original to value used when range was created without any loss of precision.
*/
@Nullable
T getPreciseTo();

/**
* Returns TRUE when value to check is withing the current range (inclusive).
*/
boolean isWithin(T valueToCheck);
boolean isWithin(@Nonnull T valueToCheck);

/**
* Creates new range of the same type with changed from and to boundaries.
* This method is used from {@link #consolidateRange(Range[])}
*/
Range<T> cloneWithDifferentBounds(T from, T to);
@Nonnull
Range<T> cloneWithDifferentBounds(@Nonnull T from, @Nonnull T to);

/**
* Returns true if two ranges overlap one another (using inclusive boundaries).
*
* @throws IllegalArgumentException when ranges are not of the same type
*/
default boolean overlaps(Range<T> otherRange) {
default boolean overlaps(@Nonnull Range<T> otherRange) {
Assert.isTrue(
this.getClass().equals(otherRange.getClass()),
"Ranges `" + this.getClass().getName() + "` and `" + otherRange.getClass().getName() + "` are not comparable!"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ private ShortNumberRange(@Nullable Short from, @Nullable Short to) {
assertNotFloatingPointType(to, "to");
}

@Nonnull
@Override
public Range<Short> cloneWithDifferentBounds(@Nullable Short from, @Nullable Short to) {
return new ShortNumberRange(from, to);
Expand Down
54 changes: 54 additions & 0 deletions evita_common/src/main/java/io/evitadb/utils/ArrayUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -869,6 +869,15 @@ public static void sortArray(@Nonnull Comparator<Integer> comparator, @Nonnull i
wrapper.sort(comparator);
}

/**
* Sorts array by the Comparator passed in first argument. Contents of the array are changed.
*/
public static <T> void sortArray(@Nonnull Comparator<T> comparator, @Nonnull T[] array) {
// now sort positions according to recordId value - this will change ordered positions to unordered ones
final ArrayWrapper<T> wrapper = new ArrayWrapper<>(array);
wrapper.sort(comparator);
}

/**
* This method will merge all passed arrays into one. All values from all arrays will be combined one after another.
* Result array is not sorted.
Expand Down Expand Up @@ -1164,4 +1173,49 @@ public int size() {

}

/**
* Internal helper class that is used to sort array A by comparator that uses array B. This cannot be easily done
* by other way than mimicking list to get advantage of {@link java.util.AbstractList#sort(Comparator)} function
* that accepts external comparator.
*/
@RequiredArgsConstructor
private static class ArrayWrapper<T> extends AbstractList<T> {
@Getter private final T[] elements;

@Override
public T get(int index) {
return elements[index];
}

@Override
public T set(int index, T element) {
T v = elements[index];
elements[index] = element;
return v;
}

@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
if (!super.equals(o)) return false;
//noinspection unchecked
ArrayWrapper<T> otherElements = (ArrayWrapper<T>) o;
return Arrays.equals(elements, otherElements.elements);
}

@Override
public int hashCode() {
int result = super.hashCode();
result = 31 * result + Arrays.hashCode(elements);
return result;
}

@Override
public int size() {
return elements.length;
}

}

}
29 changes: 29 additions & 0 deletions evita_common/src/main/java/io/evitadb/utils/StringUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,8 @@
import java.util.regex.Pattern;
import java.util.stream.Collectors;

import static java.lang.reflect.Array.*;

/**
* String utils contains shared utility methods for working with Strings.
* We know some of these functions are available in Apache Commons, but we try to keep our transitive dependencies as low as
Expand Down Expand Up @@ -561,6 +563,33 @@ public static String formatDuration(@Nonnull Duration duration) {
return sb.toString().trim();
}

/**
* Renders value as String taking into account NULL values and arrays.
*
* @param value value to render
* @return rendered value
*/
@Nonnull
public static String toString(@Nullable Object value) {
if (value == null) {
return "NULL";
} else if (value.getClass().isArray()) {
final StringBuilder sb = new StringBuilder(256);
sb.append('[');
for (int i = 0; i < getLength(value); i++) {
if (i > 0) {
sb.append(", ");
}
sb.append(toString(get(value, i)));

}
sb.append(']');
return sb.toString();
} else {
return value.toString();
}
}

/**
* <p>
* Replace all occurrences of Strings within another String.
Expand Down
2 changes: 1 addition & 1 deletion evita_db/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@
<parent>
<groupId>io.evitadb</groupId>
<artifactId>evita_root</artifactId>
<version>2024.4-SNAPSHOT</version>
<version>2024.5-SNAPSHOT</version>
</parent>

<dependencies>
Expand Down
2 changes: 1 addition & 1 deletion evita_engine/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@
<parent>
<groupId>io.evitadb</groupId>
<artifactId>evita_root</artifactId>
<version>2024.4-SNAPSHOT</version>
<version>2024.5-SNAPSHOT</version>
</parent>

<dependencies>
Expand Down
2 changes: 1 addition & 1 deletion evita_engine/src/main/java/io/evitadb/core/Evita.java
Original file line number Diff line number Diff line change
Expand Up @@ -261,7 +261,7 @@ public Evita(@Nonnull EvitaConfiguration configuration) {
updatedCatalog -> this.catalogs.put(catalogName, updatedCatalog)
);
} catch (Throwable ex) {
log.error("Catalog {} is corrupted!", catalogName);
log.error("Catalog {} is corrupted!", catalogName, ex);
this.catalogs.put(catalogName, new CorruptedCatalog(catalogName, directory, ex));
} finally {
startUpLatch.countDown();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -339,7 +339,7 @@ public SpanAttribute[] getSpanAttributes() {
new SpanAttribute("require", query.getRequire() == null ? "<NONE>" : query.getRequire().toString()),
new SpanAttribute("scannedRecords", this.filter.getEstimatedCardinality()),
new SpanAttribute("totalRecordCount", this.totalRecordCount),
new SpanAttribute("returnedRecordCount", this.primaryKeys.length)
new SpanAttribute("returnedRecordCount", this.primaryKeys == null ? 0 : this.primaryKeys.length)
};
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@

import io.evitadb.core.query.algebra.Formula;
import io.evitadb.core.query.algebra.facet.FacetGroupFormula;
import io.evitadb.core.query.algebra.facet.UserFilterFormula;
import io.evitadb.core.query.algebra.utils.FormulaFactory;
import io.evitadb.core.query.extraResult.translator.utils.AbstractFormulaStructureOptimizeVisitor;

import javax.annotation.Nonnull;
Expand Down Expand Up @@ -53,18 +55,28 @@
* @author Jan Novotný (novotny@fg.cz), FG Forrest a.s. (c) 2021
*/
public class FilterFormulaFacetOptimizeVisitor extends AbstractFormulaStructureOptimizeVisitor {
private boolean userFormulaFound;

private FilterFormulaFacetOptimizeVisitor() {
super(FacetGroupFormula.class::isInstance);
}

@Override
public void visit(@Nonnull Formula formula) {
if (formula instanceof UserFilterFormula) {
this.userFormulaFound = true;
}
super.visit(formula);
}

/**
* Preferred way of invoking this visitor. Accepts formula (tree) and produces optimized form of the formula where
* the base filter is pre-aggregated in separate container which result can be memoized.
*/
public static Formula optimize(@Nonnull Formula inputFormula) {
final FilterFormulaFacetOptimizeVisitor visitor = new FilterFormulaFacetOptimizeVisitor();
inputFormula.accept(visitor);
return visitor.getResult();
return visitor.userFormulaFound ?
visitor.getResult() : FormulaFactory.and(inputFormula, new UserFilterFormula());
}
}
Loading
Loading