Support date properties in facet search - move parseDateField
This commit is contained in:
parent
ba88dfafcd
commit
763341eacf
3 changed files with 62 additions and 12 deletions
|
@ -695,7 +695,7 @@ const ControlsMixin = {
|
|||
keys.forEach((key) => {
|
||||
let value = feature.properties[key]
|
||||
if (facetKeys[key]["type"] === "date") {
|
||||
value = feature.parseDateField(value)
|
||||
value = L.Util.parseDateField(value)
|
||||
if (!!value && (!facetCriteria[key]["min"] || facetCriteria[key]["min"] > value)) {
|
||||
facetCriteria[key]["min"] = value
|
||||
}
|
||||
|
|
|
@ -67,6 +67,66 @@ L.Util.setNullableBooleanFromQueryString = function (options, name) {
|
|||
}
|
||||
}
|
||||
|
||||
// the Date() constructor can handle various inputs to create a date
|
||||
// - value: epoch (unix timestamp) in milliseconds
|
||||
// - dateString: ISO 8601 formatted (YYYY-MM-DDTHH:mm:ss.sssZ)
|
||||
// - dateObject: JS date object
|
||||
// - multiple parameters for different date fields (year, month, ...)
|
||||
//
|
||||
// a mix of those options shall be supported without the user having
|
||||
// to specify the exact format, since umap is based on json the type
|
||||
// of the feature property value can only be
|
||||
// - string, number or boolean
|
||||
// - object or array
|
||||
// - null
|
||||
//
|
||||
// therefore, the following inputs shall be covered
|
||||
// - epoch (unix timestamp) in milliseconds as number
|
||||
// - epoch (unix timestamp) in seconds as number
|
||||
// - epoch (unix timestamp) in milliseconds as string
|
||||
// - epoch (unix timestamp) in seconds as string
|
||||
// - date in ISO 8601 format as string
|
||||
//
|
||||
// this function tries to guess the format of the feature property value
|
||||
// and adjust it a little before passing it to Date() constructor
|
||||
//
|
||||
L.Util.parseDateField = function (value) {
|
||||
if (value != null && parseFloat(value).toString() === value.toString()) {
|
||||
// if the string representation of the feature property value is
|
||||
// the same with and without being parsed as a float, the value is
|
||||
// a number (either of type number or string)
|
||||
//
|
||||
// numbers are assumed to be epochs (unix timestamps) but so far
|
||||
// it is unclear whether it is in seconds, milliseconds or nanoseconds
|
||||
//
|
||||
// without user input it can never be determined with certainty, but
|
||||
// by making some assumptions and sacrificing some small date ranges,
|
||||
// it is possible to work around that
|
||||
//
|
||||
value = parseFloat(value);
|
||||
if (Math.abs(value) < 10000000000) {
|
||||
// if the absolute value of that number is smaller than 10000000000,
|
||||
// it is assumed to be in seconds and must be multiplied by 1000
|
||||
//
|
||||
value = value * 1000;
|
||||
} else if (Math.abs(value) > 10000000000000) {
|
||||
// if the absolute value of that number is bigger than 10000000000000,
|
||||
// it is assumed to be in nanoseconds and must be divided by 1000
|
||||
//
|
||||
value = value / 1000;
|
||||
}
|
||||
// in all other cases the number is assumed to be in milliseconds
|
||||
}
|
||||
// in all other cases the value is passed to the Date() constructor
|
||||
// without modification and the constructor will try to make something out of it
|
||||
//
|
||||
// this can either result in something proper (e.g. string containing dateString),
|
||||
// something wrong (e.g. boolean) or an invalid date (e.g. object, array, null,
|
||||
// string not containing dateString)
|
||||
//
|
||||
return new Date(value);
|
||||
}
|
||||
|
||||
L.DomUtil.add = (tagName, className, container, content) => {
|
||||
const el = L.DomUtil.create(tagName, className, container)
|
||||
if (content) {
|
||||
|
|
|
@ -492,16 +492,6 @@ U.FeatureMixin = {
|
|||
return false
|
||||
},
|
||||
|
||||
parseDateField: function (value) {
|
||||
if (parseFloat(value).toString() === value.toString()) {
|
||||
value = parseFloat(value);
|
||||
if (value < 10000000000) {
|
||||
value = value * 1000;
|
||||
}
|
||||
}
|
||||
return new Date(value);
|
||||
},
|
||||
|
||||
matchFacets: function () {
|
||||
const facets = this.map.facets
|
||||
for (const [property, criteria] of Object.entries(facets)) {
|
||||
|
@ -510,7 +500,7 @@ U.FeatureMixin = {
|
|||
if (type === "date") {
|
||||
const min = new Date(criteria["min"])
|
||||
const max = new Date(criteria["max"])
|
||||
value = this.parseDateField(value)
|
||||
value = L.Util.parseDateField(value)
|
||||
if (!!min && (!value || min > value)) return false
|
||||
if (!!max && (!value || max < value)) return false
|
||||
} else {
|
||||
|
|
Loading…
Reference in a new issue