merge TileArchives and TileArchiveConfig into TileArchive

use-pmtiles-tile-archive
Mike Barry 2023-03-18 14:08:59 -04:00
rodzic da419834a4
commit 17bdd190f1
5 zmienionych plików z 99 dodań i 111 usunięć

Wyświetl plik

@ -1,9 +1,8 @@
package com.onthegomap.planetiler;
import com.onthegomap.planetiler.archive.TileArchiveConfig;
import com.onthegomap.planetiler.archive.TileArchive;
import com.onthegomap.planetiler.archive.TileArchiveMetadata;
import com.onthegomap.planetiler.archive.TileArchiveWriter;
import com.onthegomap.planetiler.archive.TileArchives;
import com.onthegomap.planetiler.archive.WriteableTileArchive;
import com.onthegomap.planetiler.collection.FeatureGroup;
import com.onthegomap.planetiler.collection.LongLongMap;
@ -86,7 +85,7 @@ public class Planetiler {
private final PlanetilerConfig config;
private FeatureGroup featureGroup;
private OsmInputFile osmInputFile;
private TileArchiveConfig output;
private TileArchive output;
private boolean overwrite = false;
private boolean ran = false;
// most common OSM languages
@ -548,7 +547,7 @@ public class Planetiler {
@Deprecated(forRemoval = true)
public Planetiler setOutput(String argument, Path fallback) {
this.output =
TileArchiveConfig
TileArchive
.from(arguments.getString("output|" + argument, "output tile archive path", fallback.toString()));
return this;
}
@ -561,10 +560,10 @@ public class Planetiler {
*
* @param defaultOutputUri The default output URI string to write to.
* @return this runner instance for chaining
* @see TileArchiveConfig For details on URI string formats and options.
* @see TileArchive For details on URI string formats and options.
*/
public Planetiler setOutput(String defaultOutputUri) {
this.output = TileArchiveConfig.from(arguments.getString("output", "output tile archive URI", defaultOutputUri));
this.output = TileArchive.from(arguments.getString("output", "output tile archive URI", defaultOutputUri));
return this;
}
@ -592,7 +591,7 @@ public class Planetiler {
*
* @param defaultOutputUri The default output URI string to write to.
* @return this runner instance for chaining
* @see TileArchiveConfig For details on URI string formats and options.
* @see TileArchive For details on URI string formats and options.
*/
public Planetiler overwriteOutput(String defaultOutputUri) {
this.overwrite = true;
@ -698,7 +697,7 @@ public class Planetiler {
// must construct this after bounds providers are added in order to infer bounds from the input source if not provided
tileArchiveMetadata = new TileArchiveMetadata(profile, config);
try (WriteableTileArchive archive = TileArchives.newWriter(output, config)) {
try (WriteableTileArchive archive = output.newWriter(config)) {
featureGroup =
FeatureGroup.newDiskBackedFeatureGroup(archive.tileOrder(), featureDbPath, profile, config, stats);
stats.monitorFile("nodes", nodeDbPath);

Wyświetl plik

@ -3,7 +3,12 @@ package com.onthegomap.planetiler.archive;
import static com.onthegomap.planetiler.util.LanguageUtils.nullIfEmpty;
import com.onthegomap.planetiler.config.Arguments;
import com.onthegomap.planetiler.config.PlanetilerConfig;
import com.onthegomap.planetiler.mbtiles.Mbtiles;
import com.onthegomap.planetiler.pmtiles.ReadablePmtiles;
import com.onthegomap.planetiler.pmtiles.WriteablePmtiles;
import com.onthegomap.planetiler.util.FileUtils;
import java.io.IOException;
import java.net.URI;
import java.net.URLDecoder;
import java.nio.charset.StandardCharsets;
@ -32,19 +37,19 @@ import java.util.Map;
* @param uri Full URI including scheme, location, and options
* @param options Parsed query parameters from the definition string
*/
public record TileArchiveConfig(
public record TileArchive(
Format format,
Scheme scheme,
URI uri,
Map<String, String> options
) {
private static TileArchiveConfig.Scheme getScheme(URI uri) {
private static TileArchive.Scheme getScheme(URI uri) {
String scheme = uri.getScheme();
if (scheme == null) {
return Scheme.FILE;
}
for (var value : TileArchiveConfig.Scheme.values()) {
for (var value : TileArchive.Scheme.values()) {
if (value.id().equals(scheme)) {
return value;
}
@ -75,15 +80,15 @@ public record TileArchiveConfig(
return result;
}
private static TileArchiveConfig.Format getFormat(URI uri) {
private static TileArchive.Format getFormat(URI uri) {
String format = parseQuery(uri).get("format");
if (format == null) {
format = getExtension(uri);
}
if (format == null) {
return TileArchiveConfig.Format.MBTILES;
return TileArchive.Format.MBTILES;
}
for (var value : TileArchiveConfig.Format.values()) {
for (var value : TileArchive.Format.values()) {
if (value.id().equals(format)) {
return value;
}
@ -94,7 +99,7 @@ public record TileArchiveConfig(
/**
* Parses a string definition of a tileset from a URI-like string.
*/
public static TileArchiveConfig from(String string) {
public static TileArchive from(String string) {
// unix paths parse fine as URIs, but need to explicitly parse windows paths with backslashes
if (string.contains("\\")) {
String[] parts = string.split("\\?", 2);
@ -109,7 +114,7 @@ public record TileArchiveConfig(
/**
* Parses a string definition of a tileset from a URI.
*/
public static TileArchiveConfig from(URI uri) {
public static TileArchive from(URI uri) {
if (uri.getScheme() == null) {
String base = Path.of(uri.getPath()).toAbsolutePath().toUri().normalize().toString();
if (uri.getRawQuery() != null) {
@ -117,7 +122,7 @@ public record TileArchiveConfig(
}
uri = URI.create(base);
}
return new TileArchiveConfig(
return new TileArchive(
getFormat(uri),
getScheme(uri),
uri,
@ -125,6 +130,72 @@ public record TileArchiveConfig(
);
}
/**
* Returns a new {@link WriteableTileArchive} from the string definition in {@code archive} that will be parsed with
* {@link TileArchive}.
*
* @throws IOException if an error occurs creating the resource.
*/
public static WriteableTileArchive newWriter(String archive, PlanetilerConfig config) throws IOException {
return from(archive).newWriter(config);
}
/**
* Returns a new {@link ReadableTileArchive} from the string definition in {@code archive} that will be parsed with
* {@link TileArchive}.
*
* @throws IOException if an error occurs opening the resource.
*/
public static ReadableTileArchive newReader(String archive, PlanetilerConfig config) throws IOException {
return from(archive).newReader(config);
}
/** Alias for {@link #newReader(String, PlanetilerConfig)}. */
public static ReadableTileArchive newReader(Path path, PlanetilerConfig config) throws IOException {
return newReader(path.toString(), config);
}
/** Alias for {@link #newWriter(String, PlanetilerConfig)}. */
public static WriteableTileArchive newWriter(Path path, PlanetilerConfig config) throws IOException {
return newWriter(path.toString(), config);
}
/**
* Returns a new {@link WriteableTileArchive} from this definition.
*
* @throws IOException if an error occurs creating the resource.
*/
public WriteableTileArchive newWriter(PlanetilerConfig config)
throws IOException {
Arguments settings = applyFallbacks(config.arguments());
return switch (format) {
case MBTILES ->
// pass-through legacy arguments for fallback
Mbtiles.newWriteToFileDatabase(getLocalPath(), settings.orElse(config.arguments()
.subset(Mbtiles.LEGACY_VACUUM_ANALYZE, Mbtiles.LEGACY_COMPACT_DB, Mbtiles.LEGACY_SKIP_INDEX_CREATION)));
case PMTILES -> WriteablePmtiles.newWriteToFile(getLocalPath());
};
}
private Arguments applyFallbacks(Arguments arguments) {
// to resolve "option" look to "?option=value" query param or "--mbtiles-option=value" command-line arg
return Arguments.of(options).orElse(arguments.withPrefix(format.id));
}
/**
* Returns a new {@link ReadableTileArchive} from this definition.
*
* @throws IOException if an error occurs opening the resource.
*/
public ReadableTileArchive newReader(PlanetilerConfig config)
throws IOException {
var options = applyFallbacks(config.arguments());
return switch (format) {
case MBTILES -> Mbtiles.newReadOnlyDatabase(getLocalPath(), options);
case PMTILES -> ReadablePmtiles.newReadFromFile(getLocalPath());
};
}
/**
* Returns the local path on disk that this archive reads/writes to, or {@code null} if it is not on disk (ie. an HTTP
* repository).
@ -157,13 +228,6 @@ public record TileArchiveConfig(
return getLocalPath() == null ? 0 : FileUtils.size(getLocalPath());
}
/**
* Returns an {@link Arguments} instance that returns the value for options directly from the query parameters in the
* URI, or from {@code arguments} prefixed by {@code "format_"}.
*/
public Arguments applyFallbacks(Arguments arguments) {
return Arguments.of(options).orElse(arguments.withPrefix(format.id));
}
public enum Format {
MBTILES("mbtiles"),

Wyświetl plik

@ -1,75 +0,0 @@
package com.onthegomap.planetiler.archive;
import com.onthegomap.planetiler.config.PlanetilerConfig;
import com.onthegomap.planetiler.mbtiles.Mbtiles;
import com.onthegomap.planetiler.pmtiles.ReadablePmtiles;
import com.onthegomap.planetiler.pmtiles.WriteablePmtiles;
import java.io.IOException;
import java.nio.file.Path;
/** Utilities for creating {@link ReadableTileArchive} and {@link WriteableTileArchive} instances. */
public class TileArchives {
private TileArchives() {}
/**
* Returns a new {@link WriteableTileArchive} from the string definition in {@code archive} that will be parsed with
* {@link TileArchiveConfig}.
*
* @throws IOException if an error occurs creating the resource.
*/
public static WriteableTileArchive newWriter(String archive, PlanetilerConfig config) throws IOException {
return newWriter(TileArchiveConfig.from(archive), config);
}
/**
* Returns a new {@link ReadableTileArchive} from the string definition in {@code archive} that will be parsed with
* {@link TileArchiveConfig}.
*
* @throws IOException if an error occurs opening the resource.
*/
public static ReadableTileArchive newReader(String archive, PlanetilerConfig config) throws IOException {
return newReader(TileArchiveConfig.from(archive), config);
}
/**
* Returns a new {@link WriteableTileArchive} from the string definition in {@code archive}.
*
* @throws IOException if an error occurs creating the resource.
*/
public static WriteableTileArchive newWriter(TileArchiveConfig archive, PlanetilerConfig config)
throws IOException {
var options = archive.applyFallbacks(config.arguments());
return switch (archive.format()) {
case MBTILES ->
// pass-through legacy arguments for fallback
Mbtiles.newWriteToFileDatabase(archive.getLocalPath(), options.orElse(config.arguments()
.subset(Mbtiles.LEGACY_VACUUM_ANALYZE, Mbtiles.LEGACY_COMPACT_DB, Mbtiles.LEGACY_SKIP_INDEX_CREATION)));
case PMTILES -> WriteablePmtiles.newWriteToFile(archive.getLocalPath());
};
}
/**
* Returns a new {@link ReadableTileArchive} from the string definition in {@code archive}.
*
* @throws IOException if an error occurs opening the resource.
*/
public static ReadableTileArchive newReader(TileArchiveConfig archive, PlanetilerConfig config)
throws IOException {
var options = archive.applyFallbacks(config.arguments());
return switch (archive.format()) {
case MBTILES -> Mbtiles.newReadOnlyDatabase(archive.getLocalPath(), options);
case PMTILES -> ReadablePmtiles.newReadFromFile(archive.getLocalPath());
};
}
/** Alias for {@link #newReader(String, PlanetilerConfig)}. */
public static ReadableTileArchive newReader(Path path, PlanetilerConfig config) throws IOException {
return newReader(path.toString(), config);
}
/** Alias for {@link #newWriter(String, PlanetilerConfig)}. */
public static WriteableTileArchive newWriter(Path path, PlanetilerConfig config) throws IOException {
return newWriter(path.toString(), config);
}
}

Wyświetl plik

@ -10,27 +10,27 @@ class TileArchiveConfigTest {
@Test
void testMbtiles() {
var config = TileArchiveConfig.from("output.mbtiles");
assertEquals(TileArchiveConfig.Format.MBTILES, config.format());
assertEquals(TileArchiveConfig.Scheme.FILE, config.scheme());
var config = TileArchive.from("output.mbtiles");
assertEquals(TileArchive.Format.MBTILES, config.format());
assertEquals(TileArchive.Scheme.FILE, config.scheme());
assertEquals(Map.of(), config.options());
assertEquals(Path.of("output.mbtiles").toAbsolutePath(), config.getLocalPath());
}
@Test
void testMbtilesWithOptions() {
var config = TileArchiveConfig.from("output.mbtiles?compact=true");
assertEquals(TileArchiveConfig.Format.MBTILES, config.format());
assertEquals(TileArchiveConfig.Scheme.FILE, config.scheme());
var config = TileArchive.from("output.mbtiles?compact=true");
assertEquals(TileArchive.Format.MBTILES, config.format());
assertEquals(TileArchive.Scheme.FILE, config.scheme());
assertEquals(Map.of("compact", "true"), config.options());
assertEquals(Path.of("output.mbtiles").toAbsolutePath(), config.getLocalPath());
}
@Test
void testPmtiles() {
assertEquals(TileArchiveConfig.Format.PMTILES, TileArchiveConfig.from("output.pmtiles").format());
assertEquals(TileArchiveConfig.Format.PMTILES, TileArchiveConfig.from("output.mbtiles?format=pmtiles").format());
assertEquals(TileArchiveConfig.Format.PMTILES,
TileArchiveConfig.from("file:///output.mbtiles?format=pmtiles").format());
assertEquals(TileArchive.Format.PMTILES, TileArchive.from("output.pmtiles").format());
assertEquals(TileArchive.Format.PMTILES, TileArchive.from("output.mbtiles?format=pmtiles").format());
assertEquals(TileArchive.Format.PMTILES,
TileArchive.from("file:///output.mbtiles?format=pmtiles").format());
}
}

Wyświetl plik

@ -2,9 +2,9 @@ package com.onthegomap.planetiler.examples;
import com.onthegomap.planetiler.Planetiler;
import com.onthegomap.planetiler.Profile;
import com.onthegomap.planetiler.archive.TileArchive;
import com.onthegomap.planetiler.archive.TileArchiveMetadata;
import com.onthegomap.planetiler.archive.TileArchiveWriter;
import com.onthegomap.planetiler.archive.TileArchives;
import com.onthegomap.planetiler.archive.WriteableTileArchive;
import com.onthegomap.planetiler.collection.FeatureGroup;
import com.onthegomap.planetiler.collection.LongLongMap;
@ -113,7 +113,7 @@ public class ToiletsOverlayLowLevelApi {
// then process rendered features, grouped by tile, encoding them into binary vector tile format
// and writing to the output mbtiles file.
try (WriteableTileArchive db = TileArchives.newWriter(output, config)) {
try (WriteableTileArchive db = TileArchive.newWriter(output, config)) {
TileArchiveWriter.writeOutput(featureGroup, db, () -> FileUtils.fileSize(output), tileArchiveMetadata, config,
stats);
} catch (IOException e) {