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

Localize all or nothing #129

Merged
merged 41 commits into from
Oct 27, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
41 commits
Select commit Hold shift + click to select a range
9555ca9
add note in contributing.md
lily-chai Oct 17, 2022
05dc619
[revert me] comment out make_global_settings
lily-chai Oct 17, 2022
c23a5f9
make LocalizeBatonType members consistent
lily-chai Oct 17, 2022
2d789e3
validate new LocalizeBatonType members in localize function
lily-chai Oct 17, 2022
06725fa
add return_localized_tile to LocalizeBatonType
lily-chai Oct 17, 2022
617d4d5
retain only those features with compatible worldview and adjust their…
lily-chai Oct 19, 2022
e61a624
be more explicity with class
lily-chai Oct 19, 2022
2e89c7e
easier to read
lily-chai Oct 19, 2022
61e591e
consistent bracket format
lily-chai Oct 19, 2022
c70ddb8
add string startswith helper function
lily-chai Oct 19, 2022
597d561
not all layers have both {class_prefix}{class_property}
lily-chai Oct 19, 2022
fe595bd
non-localized tile need to keep features in every worldview
lily-chai Oct 19, 2022
8eb553e
keep only relevant names
lily-chai Oct 19, 2022
fe48ec0
do not interchange name and language
lily-chai Oct 19, 2022
0f28295
fix typos and syntax errors
lily-chai Oct 19, 2022
2b1f149
fix class test
lily-chai Oct 19, 2022
dd809d2
fix worldview test
lily-chai Oct 20, 2022
8d62e75
add worldview_default; enfore non-empty array of languages and worldv…
lily-chai Oct 21, 2022
a5b94bb
test default worldview
lily-chai Oct 21, 2022
ff88492
test invalid params.worldviews values
lily-chai Oct 21, 2022
3bd5f32
lint
lily-chai Oct 21, 2022
84f5baa
split up vtcomposite-param-validation.test.js by function
lily-chai Oct 21, 2022
c8750a2
fix localize param validation tests
lily-chai Oct 21, 2022
938ef20
fix default worldview code, add partial string match test
lily-chai Oct 21, 2022
7825b6b
fix language test
lily-chai Oct 24, 2022
287fc20
add checks for legacy params
lily-chai Oct 24, 2022
32665e7
Revert "[revert me] comment out make_global_settings"
lily-chai Oct 24, 2022
ae37679
update readme
lily-chai Oct 24, 2022
30eac5f
fix format
lily-chai Oct 24, 2022
fd5479e
tidy up
lily-chai Oct 25, 2022
3aa513e
preserve ability to create clones of a feature
lily-chai Oct 25, 2022
06255f4
increment version, update changelog
lily-chai Oct 25, 2022
4931c25
1.2.0-dev0 [publish binary]
lily-chai Oct 25, 2022
cf0cee6
fix comment
lily-chai Oct 26, 2022
328092e
fix README.md
lily-chai Oct 26, 2022
3711e05
address feedback
lily-chai Oct 26, 2022
f7236b3
remove stray &&
lily-chai Oct 26, 2022
47f5e10
update changelog
lily-chai Oct 27, 2022
759e709
elaborate comment
lily-chai Oct 27, 2022
00b9398
one hidden_prefix for all; drop anything with hidden_prefix
lily-chai Oct 27, 2022
bd7647f
2.0.0 [publish binary]
lily-chai Oct 27, 2022
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
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
# 2.0.0

- Updates the `localize` function to return features with either all properties localized or features with no properties localized; nothing in between [#129](https://github.com/mapbox/vtcomposite/pull/129).

# 1.1.0

- Updates the `localize` function to translate `_mbx_class` to `class` when `_mbx_worldview` is provided along with matching worldview filtering
Expand Down
4 changes: 3 additions & 1 deletion CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ npm install -g documentation
npm run docs
```

* Note for MacOS: if you're having issue building on MacOS, try commenting out [`make_global_settings` in binding.gyp](https://github.com/mapbox/vtcomposite/blob/main/binding.gyp#L5-L9) (for more info see [this](https://github.com/mapbox/node-cpp-skel/pull/169#issuecomment-1068127191)).
lily-chai marked this conversation as resolved.
Show resolved Hide resolved

# Benchmarks

Benchmarks can be run with the bench/bench.js script to test vtcomposite against common real-world fixtures (provided by mvt-fixtures) and to test vtcomposite against its predecessor compositing library node-mapnik. When making changes in a pull request, please provide the benchmarks from the master branch and the HEAD of your current branch. You can control the `concurrency`, `iterations`, and `package` of the benchmarks with the following command:
Expand Down Expand Up @@ -96,4 +98,4 @@ These commands are set from within [the Makefile](./Makefile).

# Releasing

In short, you'll need to push a commit with the log line containing `[publish binary]` to build the binary, followed by an `npm publish`. See [node-cpp-skel](https://github.com/mapbox/node-cpp-skel/blob/d2848ed5bcc5a798ff39a2ac139b70844043ff11/docs/publishing-binaries.md) for all the details.
In short, you'll need to push a commit with the log line containing `[publish binary]` to build the binary, followed by an `npm publish`. See [node-cpp-skel](https://github.com/mapbox/node-cpp-skel/blob/d2848ed5bcc5a798ff39a2ac139b70844043ff11/docs/publishing-binaries.md) for all the details.
94 changes: 70 additions & 24 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,40 +73,86 @@ A filtering function for modifying a tile's features and properties to support l
#### Parameters

- `params` **Object**
- `params.buffer` **Buffer** a vector tile buffer, gzip compressed or not
- `params.compress` **Boolean** a boolean value indicating whether or not to return a compressed buffer. Default is to return an uncompressed buffer. (optional, default `false`)
- `params.language` **String** the IETF BCP 47 language code used to search for matching translations available in a feature's properties. All language-related properties must match the following format: `{language_prefix}{language_property}_{language}`. Default properties are `_mbx_name_{language}`. Example `_mbx_name_jp` property includes the Japanese translation for the value in `name`.
- If a feature has a matching translation, the feature redefines the `{language_property}` to the value of the discovered translation.
- If a feature has a matching translation, the original value from `{language_property}` is retained in a newly created value `{language_property}_local`.
- If a translation is from a property _without_ a `{language_prefix}`, the property is retained in the final tile.
- If a translation is from a property _with_ a `{language_prefix}`, the property is dropped in the final tile. This allows users to add as many languages as desired to the vector tile and eventually drop them before using the tile.
- If a feature does not have a matching translation, no fields are modified.
- In any case, all fields with a property that matches `{language_prefix}` are dropped from the final tile, even if they do not pertain to language translations.
- `params.language_property` **String** the primary property in features that identifies the feature in a language. Default `name`. This values is used to search for additional translations that match the following format `{language_property}_{language}`
- `params.language_prefix` **String** prefix for any additional translation properties. The value is used to search for additional translations that match the following format: `{language_prefix}{language_property}_{language}`.
- `params.worldview` **Array<String>** array of ISO 3166-1 alpha-2 country codes used to filter out features of different worldviews. Worldview data must be included in the vector tile. See `params.worldview_property` for more details on encoding data.
- If a feature matches one of the requested worldviews, the feature is kept. It will have a property `worldview` equal to the matching worldview value and the `params.worldview_property` property will be dropped. If the original feature contained a `worldview` property, it is overwritten.
- If a feature has a worldview value of `all` it is considered a match and `worldview: all` is added to the feature's properties and the `params.worldview_property` property is dropped. If the original feature contains a `worldview` property, it is ovewritten.
- If a feature does not match the request worldview the entire feature is dropped.
- If a feature does not have a `params.worldview_property` property it is retained.
- `params.worldview_property` **String** the name of the property that specifies in which worldview a feature belongs. The vector tile encoded property must contain a comma-separated string of ISO 3166-1 alpha-2 country codes that define which worldviews the feature represents (example: `US,RU,IN`). Default value: `_mbx_worldview`.
- If a feature contains multiple values that match multiple given values in the `params.worldview` array, it will be split into multiple features in the final vector tile, one for each matching worldview.
- `params.class_property` **String** the name of the property that specifies the class of a feature (examples: `sea`, `canal`, `village`). Default value: `_mbx_class`.
- `callback` **Function** callback function that returns `err` and `buffer` parameters
- `params.buffer` **Buffer** a vector tile buffer, gzip compressed or not.
- `params.compress` **Boolean** a boolean value indicating whether or not to return a compressed buffer.
- Default value: `false` (i.e. return an uncompressed buffer).
- `params.hidden_prefix` **String** prefix for any additional properties that will be used to override non-prefixed properties.
- Default value: `_mbx_`.
- Any property that starts with this prefix are considered hidden properties and thus will be dropped.
- `params.languages` **Array<String>** array of IETF BCP 47 language codes used to search for matching translations available in a feature's properties.
- Optional parameter.
- All language-related properties must match the following format: `{hidden_prefix}{language_property}_{language}`.
- Default properties are `_mbx_name_{language}`; for example, the `_mbx_name_jp` property contains the Japanese translation for the value in `name`.
- `params.language_property` **String** the primary property in features that identifies the feature in a language.
- Default value: `name`.
- This values is used to search for additional translations that match the following format `{language_property}_{language}`.
- `params.worldviews` **Array<String>** array of ISO 3166-1 alpha-2 country codes used to filter out features of different worldviews.
- Optional parameter.
- For now, only the first item in the array will be processed; the rest are discarded (*TODO in the future*: expand support for more than one worldviews).
- `params.worldview_property` **String** the name of the property that specifies in which worldview a feature belongs.
- Default value: `worldview`.
- The vector tile encoded property must contain a single ISO 3166-1 alpha-2 country code or a comma-separated string of country codes that define which worldviews the feature represents (for example: `JP`, `IN,RU,US`).
- `params.worldview_default` **String** default worldview to assume when `params.worldviews` is not provided.
- Default value: `US`.
- `params.class_property` **String** the name of the property that specifies the class category of a feature.
- Default value: `class`.
- `callback` **Function** callback function that returns `err` and `buffer` parameters

The existence of the parameters `params.languages` and `params.worldviews` determines the type of features that will be returned:

- Non-localized feature: when `params.languages` and `params.worldviews` both do not exist.
- No new language property.
- The property `{language_property}` retains its original value.
- Properties like `{language_property}_{language}` are kept.
- Properties like `{hidden_prefix}{language_property}_{language}` are dropped.
- All features with `{worldview_property}` are kept.
- All features with `{hidden_prefix}{worldview_property}` are dropped except for those that have the value `all`.
- Property `{class_property}` retains its original value.
- Property `{hidden_prefix}{class_property}` is dropped.

- Localized feature: when either `params.languages` or `params.worldviews` exists.
- A new `{language_property}_local` property is created to keep the original value of `{language_property}`
- The value of `{language_property}` is replaced with the first translation found by looping through `params.languages`.
- First searches for `{language_property}_{language}` and then `{hidden_prefix}{language_property}_{language}` before moving on to the next language in `params.languages`.
- Properties like `{language_property}_{language}` are dropped.
- Properties like `{hidden_prefix}{language_property}_{language}` are dropped.
- All features with `{worldview_property}` are dropped except for those that have the value `all`.
- Features with `{hidden_prefix}{worldview_property}` are kept if their `{hidden_prefix}{worldview_property}` value is
- `all`, or
- a comma-separated list that contains the first item of `parmas.worldviews`, in which a property `{worldview_property}` is created from that one single worldview country code and the property `{hidden_prefix}{worldview_property}` is dropped.
- If `{hidden_prefix}{class_property}` exists,
- Property `{class_property}` is replaced with the value in `{hidden_prefix}{class_property}`.
- Property `{hidden_prefix}{class_property}` is dropped.

#### Example

Example 1: a tile of non-localized features

```js
const { localize } = require('@mapbox/vtcomposite');

const params = {
// REQUIRED
buffer: require('fs').readFileSync('./path/to/tile.mvt'),
};

localize(params, function(err, result) {
if (err) throw err;
console.log(result); // tile buffer
});
```

Example 2: a tile of localized features in Japan worldview

```js
const { localize } = require('@mapbox/vtcomposite');

const params = {
// REQUIRED
buffer: require('fs').readFileSync('./path/to/tile.mvt'),
// OPTIONAL (defaults)
language: null,
worldview: [],
worldview_property: '_mbx_worldview',
class_property: '_mbx_class',
languages: ['ja']
worldviews: ['JP'],
compress: true
};

Expand Down
2 changes: 1 addition & 1 deletion package-lock.json

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

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@mapbox/vtcomposite",
"version": "1.1.0",
"version": "2.0.0",
"description": "Compositing operations on Vector Tiles (c++ bindings using N-API)",
"url": "http://github.com/mapbox/vtcomposite",
"main": "./lib/index.js",
Expand Down
8 changes: 7 additions & 1 deletion src/module_utils.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,12 @@ inline std::vector<std::string> split(std::string const& input)
return values;
}

// checks if a string starts with a given substring
inline bool startswith(std::string const& astring, std::string const& substring)
{
return substring.length() <= astring.length() && std::equal(substring.begin(), substring.end(), astring.begin());
}

// finds the intersection of two vectors of strings
// and assigns the intersection to a new vector passed by reference
// results are returned in alphabetically ascending order
Expand All @@ -44,4 +50,4 @@ void inline intersection(
v2.begin(), v2.end(),
std::back_inserter(result));
}
} // namespace utils
} // namespace utils
Loading