From f558b7838033a08947303bc9542cb4a5e23fe9d1 Mon Sep 17 00:00:00 2001 From: Eric Fischer Date: Fri, 7 Apr 2017 13:21:38 -0700 Subject: [PATCH] Include tileset metadata when writing either to directory or mbtiles --- CHANGELOG.md | 4 ++ main.cpp | 4 +- mbtiles.cpp | 75 ++++++++++++++++++++++----- mbtiles.hpp | 2 +- tests/raw-tiles/compare/metadata.json | 12 +++++ tile-join.cpp | 2 +- version.hpp | 2 +- 7 files changed, 83 insertions(+), 18 deletions(-) create mode 100644 tests/raw-tiles/compare/metadata.json diff --git a/CHANGELOG.md b/CHANGELOG.md index 2a1d3f9..3d8bcc8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## 1.16.15 + +* Add --output-to-directory and --no-tile-compression options + ## 1.16.14 * Add --description option for mbtiles metadata diff --git a/main.cpp b/main.cpp index 9e4926d..78c6128 100644 --- a/main.cpp +++ b/main.cpp @@ -1845,9 +1845,7 @@ int read_input(std::vector &sources, char *fname, int maxzoom, int minzo ai->second.maxzoom = maxzoom; } - if (outdb != NULL) { - mbtiles_write_metadata(outdb, fname, minzoom, maxzoom, minlat, minlon, maxlat, maxlon, midlat, midlon, forcetable, attribution, merged_lm, true, description); - } + mbtiles_write_metadata(outdb, outdir, fname, minzoom, maxzoom, minlat, minlon, maxlat, maxlon, midlat, midlon, forcetable, attribution, merged_lm, true, description); return ret; } diff --git a/mbtiles.cpp b/mbtiles.cpp index 0a364da..ab9aeb3 100644 --- a/mbtiles.cpp +++ b/mbtiles.cpp @@ -131,11 +131,23 @@ bool type_and_string::operator<(const type_and_string &o) const { return false; } -void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int maxzoom, double minlat, double minlon, double maxlat, double maxlon, double midlat, double midlon, int forcetable, const char *attribution, std::map const &layermap, bool vector, const char *description) { +void mbtiles_write_metadata(sqlite3 *outdb, const char *outdir, const char *fname, int minzoom, int maxzoom, double minlat, double minlon, double maxlat, double maxlon, double midlat, double midlon, int forcetable, const char *attribution, std::map const &layermap, bool vector, const char *description) { char *sql, *err; + sqlite3 *db = outdb; + if (outdb == NULL) { + if (sqlite3_open("", &db) != SQLITE_OK) { + fprintf(stderr, "Temporary db: %s\n", sqlite3_errmsg(db)); + exit(EXIT_FAILURE); + } + if (sqlite3_exec(db, "CREATE TABLE metadata (name text, value text);", NULL, NULL, &err) != SQLITE_OK) { + fprintf(stderr, "Create metadata table: %s\n", err); + exit(EXIT_FAILURE); + } + } + sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('name', %Q);", fname); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set name in metadata: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -144,7 +156,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('description', %Q);", description != NULL ? description : fname); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set description in metadata: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -153,7 +165,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('version', %d);", 2); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set version : %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -162,7 +174,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('minzoom', %d);", minzoom); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set minzoom: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -171,7 +183,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('maxzoom', %d);", maxzoom); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set maxzoom: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -180,7 +192,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('center', '%f,%f,%d');", midlon, midlat, maxzoom); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set center: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -189,7 +201,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('bounds', '%f,%f,%f,%f');", minlon, minlat, maxlon, maxlat); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set bounds: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -198,7 +210,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int sqlite3_free(sql); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('type', %Q);", "overlay"); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set type: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -208,7 +220,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int if (attribution != NULL) { sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('attribution', %Q);", attribution); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set type: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -218,7 +230,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int } sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('format', %Q);", vector ? "pbf" : "png"); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set format: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -276,7 +288,7 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int aprintf(&buf, " ] }"); sql = sqlite3_mprintf("INSERT INTO metadata (name, value) VALUES ('json', %Q);", buf.c_str()); - if (sqlite3_exec(outdb, sql, NULL, NULL, &err) != SQLITE_OK) { + if (sqlite3_exec(db, sql, NULL, NULL, &err) != SQLITE_OK) { fprintf(stderr, "set json: %s\n", err); if (!forcetable) { exit(EXIT_FAILURE); @@ -284,6 +296,45 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int } sqlite3_free(sql); } + + if (outdir != NULL) { + std::string metadata = std::string(outdir) + "/metadata.json"; + FILE *fp = fopen(metadata.c_str(), "w"); + if (fp == NULL) { + perror(metadata.c_str()); + exit(EXIT_FAILURE); + } + + fprintf(fp, "{\n"); + + sqlite3_stmt *stmt; + bool first = true; + if (sqlite3_prepare_v2(db, "SELECT name, value from metadata;", -1, &stmt, NULL) == SQLITE_OK) { + while (sqlite3_step(stmt) == SQLITE_ROW) { + std::string key, value; + + quote(&key, (const char *) sqlite3_column_text(stmt, 0)); + quote(&value, (const char *) sqlite3_column_text(stmt, 1)); + + if (!first) { + fprintf(fp, ",\n"); + } + fprintf(fp, " \"%s\": \"%s\"", key.c_str(), value.c_str()); + first = false; + } + sqlite3_finalize(stmt); + } + + fprintf(fp, "\n}\n"); + fclose(fp); + } + + if (outdb == NULL) { + if (sqlite3_close(db) != SQLITE_OK) { + fprintf(stderr, "Could not close temp database: %s\n", sqlite3_errmsg(db)); + exit(EXIT_FAILURE); + } + } } void mbtiles_close(sqlite3 *outdb, char **argv) { diff --git a/mbtiles.hpp b/mbtiles.hpp index 4fb18b1..dbe93cd 100644 --- a/mbtiles.hpp +++ b/mbtiles.hpp @@ -20,7 +20,7 @@ sqlite3 *mbtiles_open(char *dbname, char **argv, int forcetable); void mbtiles_write_tile(sqlite3 *outdb, int z, int tx, int ty, const char *data, int size); -void mbtiles_write_metadata(sqlite3 *outdb, const char *fname, int minzoom, int maxzoom, double minlat, double minlon, double maxlat, double maxlon, double midlat, double midlon, int forcetable, const char *attribution, std::map const &layermap, bool vector, const char *description); +void mbtiles_write_metadata(sqlite3 *outdb, const char *outdir, const char *fname, int minzoom, int maxzoom, double minlat, double minlon, double maxlat, double maxlon, double midlat, double midlon, int forcetable, const char *attribution, std::map const &layermap, bool vector, const char *description); void mbtiles_close(sqlite3 *outdb, char **argv); diff --git a/tests/raw-tiles/compare/metadata.json b/tests/raw-tiles/compare/metadata.json new file mode 100644 index 0000000..c83c17c --- /dev/null +++ b/tests/raw-tiles/compare/metadata.json @@ -0,0 +1,12 @@ +{ + "name": "tests/raw-tiles/raw-tiles", + "description": "tests/raw-tiles/raw-tiles", + "version": "2", + "minzoom": "0", + "maxzoom": "14", + "center": "-122.662354,45.514045,14", + "bounds": "-122.682427,45.512332,-122.654961,45.569975", + "type": "overlay", + "format": "pbf", + "json": "{\"vector_layers\": [ { \"id\": \"hackspotsgeojson\", \"description\": \"\", \"minzoom\": 0, \"maxzoom\": 14, \"fields\": {\"Address\": \"String\", \"Name\": \"String\", \"Notes\": \"String\"} } ] }" +} diff --git a/tile-join.cpp b/tile-join.cpp index 4920f2d..6ca1617 100644 --- a/tile-join.cpp +++ b/tile-join.cpp @@ -750,7 +750,7 @@ int main(int argc, char **argv) { decode(readers, csv, layermap, outdb, &st, header, mapping, exclude, ifmatched, attribution, description); - mbtiles_write_metadata(outdb, outfile, st.minzoom, st.maxzoom, st.minlat, st.minlon, st.maxlat, st.maxlon, st.midlat, st.midlon, 0, attribution.size() != 0 ? attribution.c_str() : NULL, layermap, true, description.c_str()); + mbtiles_write_metadata(outdb, NULL, outfile, st.minzoom, st.maxzoom, st.minlat, st.minlon, st.maxlat, st.maxlon, st.midlat, st.midlon, 0, attribution.size() != 0 ? attribution.c_str() : NULL, layermap, true, description.c_str()); mbtiles_close(outdb, argv); return 0; diff --git a/version.hpp b/version.hpp index 3b4aad7..b44031b 100644 --- a/version.hpp +++ b/version.hpp @@ -1 +1 @@ -#define VERSION "tippecanoe v1.16.13\n" +#define VERSION "tippecanoe v1.16.14\n"