feat(default-exts): Implement read fallback extension
This commit is contained in:
@@ -0,0 +1,14 @@
|
||||
package de.siphalor.tweed5.defaultextensions.readfallback.api;
|
||||
|
||||
import de.siphalor.tweed5.core.api.extension.TweedExtension;
|
||||
import de.siphalor.tweed5.defaultextensions.readfallback.impl.ReadFallbackExtensionImpl;
|
||||
|
||||
public interface ReadFallbackExtension extends TweedExtension {
|
||||
Class<? extends ReadFallbackExtension> DEFAULT = ReadFallbackExtensionImpl.class;
|
||||
String EXTENSION_ID = "read-fallback";
|
||||
|
||||
@Override
|
||||
default String getId() {
|
||||
return EXTENSION_ID;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
package de.siphalor.tweed5.defaultextensions.readfallback.impl;
|
||||
|
||||
import de.siphalor.tweed5.core.api.container.ConfigContainer;
|
||||
import de.siphalor.tweed5.core.api.entry.ConfigEntry;
|
||||
import de.siphalor.tweed5.core.api.middleware.Middleware;
|
||||
import de.siphalor.tweed5.defaultextensions.readfallback.api.ReadFallbackExtension;
|
||||
import de.siphalor.tweed5.data.extension.api.TweedEntryReadException;
|
||||
import de.siphalor.tweed5.data.extension.api.TweedEntryReader;
|
||||
import de.siphalor.tweed5.data.extension.api.extension.ReadWriteExtensionSetupContext;
|
||||
import de.siphalor.tweed5.data.extension.api.extension.ReadWriteRelatedExtension;
|
||||
import de.siphalor.tweed5.defaultextensions.presets.api.PresetsExtension;
|
||||
import lombok.extern.apachecommons.CommonsLog;
|
||||
import org.jspecify.annotations.NonNull;
|
||||
import org.jspecify.annotations.Nullable;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Set;
|
||||
|
||||
@CommonsLog
|
||||
public class ReadFallbackExtensionImpl implements ReadFallbackExtension, ReadWriteRelatedExtension {
|
||||
private final ConfigContainer<?> configContainer;
|
||||
private @Nullable PresetsExtension presetsExtension;
|
||||
|
||||
public ReadFallbackExtensionImpl(ConfigContainer<?> configContainer) {
|
||||
this.configContainer = configContainer;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void extensionsFinalized() {
|
||||
presetsExtension = configContainer.extension(PresetsExtension.class)
|
||||
.orElseThrow(() -> new IllegalStateException(getClass().getSimpleName()
|
||||
+ " requires " + ReadFallbackExtension.class.getSimpleName()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setupReadWriteExtension(ReadWriteExtensionSetupContext context) {
|
||||
assert presetsExtension != null;
|
||||
|
||||
context.registerReaderMiddleware(new Middleware<TweedEntryReader<?, ?>>() {
|
||||
@Override
|
||||
public String id() {
|
||||
return EXTENSION_ID;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<String> mustComeBefore() {
|
||||
return Collections.singleton(DEFAULT_START);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<String> mustComeAfter() {
|
||||
return Collections.emptySet();
|
||||
}
|
||||
|
||||
@Override
|
||||
public TweedEntryReader<?, ?> process(TweedEntryReader<?, ?> inner) {
|
||||
//noinspection unchecked
|
||||
TweedEntryReader<Object, ConfigEntry<Object>> castedInner =
|
||||
(TweedEntryReader<Object, @NonNull ConfigEntry<Object>>) inner;
|
||||
return (TweedEntryReader<Object, @NonNull ConfigEntry<Object>>) (reader, entry, context1) -> {
|
||||
try {
|
||||
return castedInner.read(reader, entry, context1);
|
||||
} catch (TweedEntryReadException e) {
|
||||
log.error("Failed to read entry: " + e.getMessage(), e);
|
||||
return presetsExtension.presetValue(entry, PresetsExtension.DEFAULT_PRESET_NAME);
|
||||
}
|
||||
};
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
package de.siphalor.tweed5.defaultextensions.readfallback.impl;
|
||||
|
||||
import de.siphalor.tweed5.core.api.entry.ConfigEntry;
|
||||
import de.siphalor.tweed5.core.impl.DefaultConfigContainer;
|
||||
import de.siphalor.tweed5.core.impl.entry.SimpleConfigEntryImpl;
|
||||
import de.siphalor.tweed5.data.extension.api.ReadWriteExtension;
|
||||
import de.siphalor.tweed5.data.extension.api.TweedEntryReadException;
|
||||
import de.siphalor.tweed5.data.extension.api.TweedReadContext;
|
||||
import de.siphalor.tweed5.data.extension.api.TweedWriteContext;
|
||||
import de.siphalor.tweed5.data.extension.api.readwrite.TweedEntryReaderWriter;
|
||||
import de.siphalor.tweed5.data.hjson.HjsonLexer;
|
||||
import de.siphalor.tweed5.data.hjson.HjsonReader;
|
||||
import de.siphalor.tweed5.dataapi.api.*;
|
||||
import de.siphalor.tweed5.defaultextensions.presets.api.PresetsExtension;
|
||||
import de.siphalor.tweed5.defaultextensions.readfallback.api.ReadFallbackExtension;
|
||||
import org.jspecify.annotations.NullMarked;
|
||||
import org.jspecify.annotations.Nullable;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import java.io.StringReader;
|
||||
|
||||
import static de.siphalor.tweed5.data.extension.api.ReadWriteExtension.entryReaderWriter;
|
||||
import static de.siphalor.tweed5.data.extension.api.ReadWriteExtension.read;
|
||||
import static de.siphalor.tweed5.defaultextensions.presets.api.PresetsExtension.presetValue;
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
@NullMarked
|
||||
class ReadFallbackExtensionImplTest {
|
||||
@Test
|
||||
void test() {
|
||||
DefaultConfigContainer<Integer> configContainer = new DefaultConfigContainer<>();
|
||||
configContainer.registerExtension(ReadWriteExtension.class);
|
||||
configContainer.registerExtension(PresetsExtension.class);
|
||||
configContainer.registerExtension(ReadFallbackExtension.DEFAULT);
|
||||
configContainer.finishExtensionSetup();
|
||||
|
||||
ConfigEntry<Integer> entry = new SimpleConfigEntryImpl<>(configContainer, Integer.class)
|
||||
.apply(presetValue(PresetsExtension.DEFAULT_PRESET_NAME, -1))
|
||||
.apply(entryReaderWriter(new TweedEntryReaderWriter<>() {
|
||||
@Override
|
||||
public Integer read(
|
||||
TweedDataReader reader,
|
||||
ConfigEntry<Integer> entry,
|
||||
TweedReadContext context
|
||||
) throws TweedEntryReadException {
|
||||
int value;
|
||||
try {
|
||||
value = reader.readToken().readAsInt();
|
||||
} catch (TweedDataReadException e) {
|
||||
throw new IllegalStateException("Should not be called", e);
|
||||
}
|
||||
if (value % 2 == 0) {
|
||||
return value;
|
||||
} else {
|
||||
throw new TweedEntryReadException("Value is not even", context);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(
|
||||
TweedDataVisitor writer,
|
||||
@Nullable Integer value,
|
||||
ConfigEntry<Integer> entry,
|
||||
TweedWriteContext context
|
||||
) throws TweedDataWriteException {
|
||||
throw new IllegalStateException("Should not be called");
|
||||
}
|
||||
}));
|
||||
|
||||
configContainer.attachTree(entry);
|
||||
configContainer.initialize();
|
||||
|
||||
assertThat(entry.call(read(new HjsonReader(new HjsonLexer(new StringReader("12")))))).isEqualTo(12);
|
||||
assertThat(entry.call(read(new HjsonReader(new HjsonLexer(new StringReader("13")))))).isEqualTo(-1);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user