Commit Graph

31 Commits

Author SHA1 Message Date
Yuri Astrakhan
144e10ff20
Upgrade sqlx to v0.7 (#743)
This is mostly a noop, just updating to the new way of storing cached
queries and a few other changes per
https://github.com/launchbadge/sqlx/blob/main/CHANGELOG.md#070---2023-06-30

Note that this uses some of the code from #729 (thanks @upsicleclown !)

A minor unrelated change - a reformat of `martin/release.toml`
2023-07-04 08:05:23 -04:00
Pirmin Kalberer
aabcb0aa0a
Add sqlx-rustls support (#720)
I'd like to add optional rustls support for SQLx. This PR implements the
required features, but tests using `--all-features` fail, because
runtime selection features are not additive. I didn't find a solution
apart from avoiding `--all-features`.

---------

Co-authored-by: Yuri Astrakhan <YuriAstrakhan@gmail.com>
2023-07-03 21:29:44 +00:00
Yuri Astrakhan
a5c5505713
Add dynamic sprites support (#715)
Dynamically create image sprites for MapLibre rendering, given a
directory with images.

### TODO
* [x] Work with @flother to merge these PRs
  * [x] https://github.com/flother/spreet/pull/59  (must have)
  * [x] https://github.com/flother/spreet/pull/57
  * [x] https://github.com/flother/spreet/pull/56
* [ ] https://github.com/flother/spreet/pull/62 (not required but nice
to have, can upgrade later without any code changes)
* [x] Add docs to the book
* [x] Add CLI param, e.g. `--sprite <dir_path>`
* [x] Don't output `.sprites` in auto-genned config when not in use

### API
Per [MapLibre sprites
API](https://maplibre.org/maplibre-style-spec/sprite/), we need to
support the following:
* `/sprite/<sprite_id>.json` metadata about the sprite file - all coming
from a single directory
* `/sprite/<sprite_id>.png` all images combined into a single PNG
* `/sprite/<sprite_id>@2x.json` same but for high DPI devices
* `/sprite/<sprite_id>@2x.png`

Multiple sprite_id values can be combined into one sprite with the same
pattern as for tile joining:
`/sprite/<sprite_id1>,<sprite_id2>,...,<sprite_idN>[.json|.png|@2x.json|@2x.png]`.
No ID renaming is done, so identical names will override one another.

### Configuration
[Config file](https://maplibre.org/martin/config-file.html) and possibly
CLI should have a simple option to serve sprites. The configuration may
look similar to how mbtiles and pmtiles are configured:

```yaml
# Publish sprite images
sprites:
  paths:
    # scan this whole dir, matching all image files, and publishing it as "my_images" sprite source
    - /path/to/my_images
  sources:
    # named source matching source name to a directory
    my_sprites: /path/to/some_dir
```

Implement #705
2023-06-16 08:19:47 -04:00
Yuri Astrakhan
7e20602079
Minor refactor and cleanup (#716)
* moved `IdResolver` to a separate file
* added `just fmt2` build target to format code using nightly mode
* moved all Actix `Data<AppState>` into individual state objects, e.g.
`Data<Sources>` (allows other source types, separate from `Sources`
type)
* move all Source-related code to a new `Sources` struct (a simple
wrapper over a HashMap)
2023-06-15 18:36:41 -04:00
Yuri Astrakhan
1418a8b44c Cargo update and a minor lint 2023-06-12 23:20:52 -04:00
Yuri Astrakhan
6d02416720
Improve PG performance by 28% (!!!) (#703)
A very long overdue PostgreSQL querying performance optimization that
should have used cached queries, but ... somehow didn't.

Also, this PR adds two new `just` tasks: `run-release` and `bench-http`

I used [oha](https://github.com/hatoo/oha) for its visual appeal. All
tests were using keep-alive, which I think is relatively accurate
because clients make many tile requests on the same connection. As a
target, I used the same non-empty small tile to reduce the PostgreSQL
indexing load.

❯ just run-release
❯ just bench-http

`bench-http` runs this command:
```
oha -z 120s http://localhost:3000/function_zxy_query/18/235085/122323
```

<pre>
|       before the change          |         after the change         |
|----------------------------------|----------------------------------|
|   Summary:                       | Summary:                         |
|     Success rate:    1.0000      |   Success rate:    1.0000        |
|     Total:    120.0004 secs      |   Total:    120.0002 secs        |
|     Slowest:    0.1339 secs      |   Slowest:    0.3505 secs        |
|     Fastest:    0.0015 secs      |   Fastest:    0.0012 secs        |
|     Average:    0.0076 secs      |   Average:    0.0055 secs        |
|     Requests/sec:    6583.6946   |   Requests/sec:    9073.5398     |
|                                  |                                  |
|     Total data:    113.02 MiB    |   Total data:    155.76 MiB      |
|     Size/request:    150 B       |   Size/request:    150 B         |
|     Size/sec:    964.41 KiB      |   Size/sec:    1.30 MiB          |
|                                  |                                  |
|   Response time histogram:       | Response time histogram:         |
|     0.002 [1]                    |   0.001 [1]                      |
|     0.015 [785706] ■■■■■■■■■■■■■ |   0.036 [1088825] ■■■■■■■■■■■■■  |
|     0.028 [4225]                 |   0.071 [0]                      |
|     0.041 [111]                  |   0.106 [0]                      |
|     0.054 [2]                    |   0.141 [0]                      |
|     0.068 [0]                    |   0.176 [0]                      |
|     0.081 [0]                    |   0.211 [0]                      |
|     0.094 [0]                    |   0.246 [0]                      |
|     0.107 [0]                    |   0.281 [0]                      |
|     0.121 [0]                    |   0.316 [0]                      |
|     0.134 [1]                    |   0.350 [1]                      |
|                                  |                                  |
|   Latency distribution:          | Latency distribution:            |
|     10% in 0.0057 secs           |   10% in 0.0039 secs             |
|     25% in 0.0064 secs           |   25% in 0.0045 secs             |
|     50% in 0.0073 secs           |   50% in 0.0053 secs             |
|     75% in 0.0084 secs           |   75% in 0.0063 secs             |
|     90% in 0.0098 secs           |   90% in 0.0074 secs             |
|     95% in 0.0107 secs           |   95% in 0.0082 secs             |
|     99% in 0.0135 secs           |   99% in 0.0102 secs             |
</pre>

Fixes #678
2023-06-04 15:02:00 -04:00
Yuri Astrakhan
adab3bca95 Fix mdbook compile target 2023-06-04 14:11:44 -04:00
Yuri Astrakhan
2cdd373044
Refactor mbtiles lib, mbtiles tool tests & CI (#702)
* Broke up martin-mbtiles into multiple files
* Made all mbtiles functions take a `SqliteExecutor` -- this way they
can be used with any SQLX connection structs - either a pool connection
or an individual non-pooled connection.
* Simplified mbtiles bin a bit - I realized there is really no need to
pretty print the output for the single value retrieval. Easier to just
dump it to console as is.
* Bump martin-mbtiles to v0.2.0
* Minor fixes in tools docs, cargo.toml, and justfile
* MBTiles tool Integration tests and release publishing

Major thanks to the
[stackoverflow](https://stackoverflow.com/questions/76394665/how-to-pass-sqlx-connection-a-mut-trait-as-a-fn-parameter-in-rust/76395111)
quick reply by @cafce25 on how to use generic sql executor!
2023-06-04 00:54:50 +02:00
rstanciu
78e67c3ad2
Add mbtiles meta-get utility (#701)
* Add functionality to retrieve a metadata value in an mbtiles file by
key; simple implementation for one of the items in #667
* Also, disable TTY in docker-up `just` target
2023-06-03 00:40:22 +00:00
Yuri Astrakhan
81bb9582ed
Cleaning up mdbook (#697)
A lot of book content cleanup, making it a bit shorter and "logical"
(whatever that even means)

To try, run `just mdbook`
2023-06-02 01:16:41 -04:00
Yuri Astrakhan
278f46f772 Add just prepare-sqlite to simplify sqlite dev 2023-06-01 13:07:13 -04:00
baishikele
56dde81cfe
Create mdbook documentation (#681)
Copy readme into multiple book files

Co-authored-by: Yuri Astrakhan <YuriAstrakhan@gmail.com>
2023-05-29 02:06:35 +00:00
Yuri Astrakhan
0209b662bf Format justfile using just --fmt 2023-05-23 23:47:55 -04:00
Yuri Astrakhan
39c19c0369 Print connection str from justfile
* update readme with the missing justfile CLI commands
* add `print-conn-str` command to show the full DB connection string
2023-05-16 14:12:24 -04:00
Yuri Astrakhan
71a427e143 Fix pedantic CI runs 2023-04-08 02:37:53 -04:00
Stepan Kuzmin
79c8ccb452
Migrate to GitHub Docker registry (#602)
Publishes Martin Docker Image to GitHub Docker Registry as
[`ghcr.io/maplibre/martin`](https://ghcr.io/maplibre/martin)

Closes https://github.com/maplibre/martin/issues/601

---------

Co-authored-by: Yuri Astrakhan <YuriAstrakhan@gmail.com>
2023-03-16 16:01:33 -04:00
cthiange
612a8d38c4
Issue 540 - missing index warnings (#569)
Warn users when a PG table geometry column has no index - thus accessing it would be slow.  This is only done for tables. Issues with the views are not printed.

## Implementation

This adds two fields to `TableInfo`:
* `geom_idx: Option<bool>` to tell if a geo column has a spatial index
* `is_view: Option<bool>` to distinguish views from other relations

Missing spatial index warnings are logged for non-view relations. Views
will never have indexed columns and, if referencing a table with a
missing index, it will be logged already.

Couldn't figure out how to make `just test` accept the new warning (from
missing index), so I have them logged as INFO for now :)

fixes #540

---------

Co-authored-by: Christophe Thiange <cthiange@gmail.com>
Co-authored-by: Yuri Astrakhan <YuriAstrakhan@gmail.com>
2023-02-07 01:05:47 -05:00
Yuri Astrakhan
fbb282dcb7
Improve SSL support (#567)
This is a partial fix for #496

* BREAKING: Now Martin behaves the same way as `psql` -- by default, if
SSL is available on the server, it will be used, even though it will not
verify that the server has a valid SSL certificate
* Martin now understands `PGSSLCERT`, `PGSSLKEY`, and `PGSSLROOTCERT`
env vars (and corresponding config keys) - same as psql.
* Martin can now process `?sslmode=verify-ca` and `verify-full` (just
like psql). The verify modes require root and/or client cert & key.
* remove `danger_accept_invalid_certs` -- turns out that behavior is
expected by default unless ssl mode is set to verify - which upstream
lib [does not
support](https://github.com/sfackler/rust-postgres/issues/768) - PR
[submitted](https://github.com/sfackler/rust-postgres/pull/988).
* added connection_timeout_ms option for postgres and set it to 5
seconds by default. This way it will fail out earlier.
* added error reporting to bb8 - but it is currently [broken
upstream](https://github.com/djc/bb8/issues/151) - not sure we can fix
it easily, so may need to switch to deadpool later.
* added docker-based TLS test (horray!) - wasn't trivial at all, despite
ending up fairly simple.
2023-02-06 14:32:28 -05:00
Yuri Astrakhan
e58773f7b0
Refactorings, content-type/enc, cli parsing, tests, minor fixes (#548)
* introduce a new Connections object to track all positional strings
passed as the CLI arguments
* each tile provider can now indicate if it can take a positional CLI
arg, and if the value can be shared between multiple providers, i.e. if
its a directory that could contain files for multiple providers
* make xyz use better types - u8 for zoom, u32 for x&y. Postgres casts
those to INT2 and INT8
* minor bug in pre-push git hook to abort in case of a testingerror
* added GIF detection/type
* combine MVT and compression concepts into one enum more explicitly. It
is not ideal (technically they are separate concerns), but it keeps it a
bit simpler for now for multiple providers.
* set content encoding and content type on HTTP responses if known, and
also include them in the `/catalog` response (json)
* raise an error if the user attempts to merge non-concatenatable tiles
from multiple sources. We may want to implement it in the future, e.g.
combine multiple semi-transparent PNGs. Or even combine GIF & PNG & JPEG
* do not set content-type on empty responses (http 204)
* add tilejson outputs to testing
2023-01-08 16:31:58 +02:00
Yuri Astrakhan
64ad07ce36
Fix legacy DB, add CI tests (#547)
* fixed SQL to work on older PG versions
* re-enable CI to test expected `test.sh` output against the one stored
in the `tests/expected`
* add postgres in docker tests on linux - one for the oldest supported
DB, and another using the more recent version
* minor justfile cleanup
* ensure config files are sorted alphabetically
2023-01-01 05:03:21 +00:00
Yuri Astrakhan
555a1fccdd
Improve Coverage tooling (#535)
* added manual coverage justfile command
* a lot of small refactorings of config and argument parsing
* feature: support jsonb query param for functions
* cleaned up public/private access
* make all tests populate with a predefined values to avoid issues with
random data
2022-12-27 06:56:27 +00:00
Yuri Astrakhan
2b240b3a34
Implement multi-sourced postgres (#511)
* Support `postgres` config key to be either a list or an object
* Use `PathBuf` instead of `String` where dealing with files
* Merge `SrvConfigBuilder` into `SrvConfig`
* Parse keep_alive as u64
* More config tests
2022-12-22 06:35:29 +00:00
Yuri Astrakhan
cb99b835e9
Enable clippy pedantic, fix lints (#525)
Pedantic lints often offer some good insight into the code. It is
usually easier to sprinkle a few "allow"-s around, than to miss some
important life hack offered by clippy.

Also, make use a different martin port when running integration tests
locally (make sure `git push` works even if martin is running).
2022-12-18 21:24:06 -05:00
Yuri Astrakhan
2ee517d135
Support z,x,y and record-returning funcs, table rework (#380)
Can now handle several additional Postgres functions to get a tile, plus
tons of small fixes

### Multiple result variants
* `getmvt(z,x,y) -> [bytea,md5]`  (single row with two columns)
* `getmvt(z,x,y) -> [bytea]` (single row with a single column)
* `getmvt(z,x,y) -> bytea` (value)

### Multiple input parameter variants
* `getmvt(z, x, y)` or `getmvt(zoom, x, y)` (all 3 vars must be
integers)
* `getmvt(z, x, y, url_query)`, where instead of `url_query` it could be
any other name, but must be of type JSON

### Breaking
* srid is now the same type as PG -- `i32`
* renamed config vals `table_sources` and `function_sources` into
`tables` and `functions`

### Features and fixes
* if postgis is v3.1+, uses margin parameter to extend the search box by
the size of the buffer. I think we should make 3.1 minimal required.
* fixes feature ID issue from #466
* fixes mixed case names for schemas, tables and columns, functions and
parameter names per #389
 

### Notes
* More dynamic SQL generation in code instead of using external SQL
files. Those should only be used when they are not parametrized.
* The new function/table discovery mechanism: query for all functions in
the database, and match up those functions with the ones configured (if
any), plus adds all the rest of the un-declared ones if discovery mode
is on.
* During table and function discovery, the code generates a map of
`(PgSqlInfo, FunctionInfo)` (or table) tupples containing SQL needed to
get the tile.
* Auto-discovery mode is currently hidden - the discovery is on only
when no tables or functions are configured. TBD - how to configure it in
the future
* The new system allows for an easy way to auto-discover for the
specific schemas only, solving #47
* predictable order of table/function instantiation
* bounding boxes computed in parallel for all tables (when not
configured)
* proper identifier escaping
* test cleanup

fixes #378
fixes #466
fixes #65
fixes #389
2022-12-10 16:20:42 +02:00
Yuri Astrakhan
ff7c31e16f
Improve pre-push hook and debug page (#509)
* write custom git pre-push via justfile
* fix tests/debug.html incorrectly loading test page
* minor cleanup of the obsolete just targets
2022-12-10 09:40:01 +02:00
Yuri Astrakhan
cfc31fae1b
Update minimal legacy db (#500)
* bump docker compose to use latest supported db and postgis
* update justfile to allow simple legacy testing
* update readme

Followup: implement CI testing -- see #502
2022-12-04 14:34:44 +09:00
Yuri Astrakhan
c1b65796f6
Require PostGIS 3 and use ST_TileEnvelope (#497)
* All tests and internal code now uses ST_TileEnvelope function
* Remove `tile_bbox`
* Rename test function sources for clarity - this will be needed in a
subsequent PR to add other function tests
2022-11-30 18:57:27 +02:00
Yuri Astrakhan
0a5e449ca9
fix CI tests to include all targets and docs (#483) 2022-11-19 15:52:58 +00:00
Yuri Astrakhan
6b114cc7f1
Docker improvements and CI tests (#472)
* Change docker image to use `entrypoint` -- so that Martin can be used
as a command:

```bash
docker run maplibre/martin <parameters>
```

* The docker image is now tested the same way as in the CI tests
* Added a few changes to the justfile

Fixes #436
2022-11-02 19:00:05 +01:00
Yuri Astrakhan
b8ac719be8
Rework and consolidate CI (#467)
Rework CI to run tests locally using the VM-installed Postgres on all
target platforms.

### CI jobs
* Build release versions on Linux/Win/Mac and save build results as
output artifacts
* In a separate VMs (Linux/Win/Mac)
* use
[nyurik/action-setup-postgis](https://github.com/nyurik/action-setup-postgis)
to install postgis and run tests using the built artifacts
  * run `cargo test` on Linux only
* copy built artifacts from the build step, and run tests using the
release martin binary
  * package and publish if this is a release

### Other changes
* Port some minor changes from the rewrite to porting easier
* minor cleanups
* remove all "expected" data files - too unstable to be usable
2022-10-31 16:28:21 -04:00
Yuri Astrakhan
a0a411f088
Consolidate DB init and tests (#463)
* Add justfile to simplify running all the tests
* Save all PBF outputs to the text files
* Consolidate all tests to reuse the same code
* Consolidate database initialization
* updated readme with the new instructions

Note that while this PR creates "expected" files, the CI cannot validate
the generated results because the output is not stable. Eventually we
may try to output just the non-geometry values to have reasonable tests
comparing against the expected results.
2022-10-28 14:52:39 -04:00