Add robustness when run via console, formatting

This commit is contained in:
pietervdvn 2021-10-20 00:09:40 +02:00
parent 83af5adaea
commit 89d4a6bcce
11 changed files with 118 additions and 67 deletions

View file

@ -23,11 +23,11 @@ export default class AvailableBaseLayers {
private static implementation: AvailableBaseLayersObj
static AvailableLayersAt(location: UIEventSource<Loc>): UIEventSource<BaseLayer[]> {
return AvailableBaseLayers.implementation.AvailableLayersAt(location);
return AvailableBaseLayers.implementation?.AvailableLayersAt(location) ?? new UIEventSource<BaseLayer[]>([]);
}
static SelectBestLayerAccordingTo(location: UIEventSource<Loc>, preferedCategory: UIEventSource<string | string[]>): UIEventSource<BaseLayer> {
return AvailableBaseLayers.implementation.SelectBestLayerAccordingTo(location, preferedCategory);
return AvailableBaseLayers.implementation?.SelectBestLayerAccordingTo(location, preferedCategory) ?? new UIEventSource<BaseLayer>(undefined);
}

View file

@ -2,6 +2,7 @@ import {UIEventSource} from "../UIEventSource";
import BaseLayer from "../../Models/BaseLayer";
import AvailableBaseLayers from "./AvailableBaseLayers";
import Loc from "../../Models/Loc";
import {Utils} from "../../Utils";
/**
* Sets the current background layer to a layer that is actually available
@ -12,6 +13,11 @@ export default class BackgroundLayerResetter {
location: UIEventSource<Loc>,
availableLayers: UIEventSource<BaseLayer[]>,
defaultLayerId: string = undefined) {
if(Utils.runningFromConsole){
return
}
defaultLayerId = defaultLayerId ?? AvailableBaseLayers.osmCarto.id;
// Change the baselayer back to OSM if we go out of the current range of the layer

View file

@ -1,6 +1,7 @@
import {Changes} from "../Osm/Changes";
import Constants from "../../Models/Constants";
import {UIEventSource} from "../UIEventSource";
import {Utils} from "../../Utils";
export default class PendingChangesUploader {
@ -30,6 +31,10 @@ export default class PendingChangesUploader {
}
});
if(Utils.runningFromConsole){
return;
}
document.addEventListener('mouseout', e => {
// @ts-ignore
if (!e.toElement && !e.relatedTarget) {

View file

@ -9,6 +9,13 @@ import {OsmConnection} from "../Osm/OsmConnection";
export default class SelectedElementTagsUpdater {
private static readonly metatags = new Set(["timestamp",
"version",
"changeset",
"user",
"uid",
"id"] )
constructor(state: {
selectedElement: UIEventSource<any>,
allElements: ElementStorage,
@ -18,15 +25,15 @@ export default class SelectedElementTagsUpdater {
state.osmConnection.isLoggedIn.addCallbackAndRun(isLoggedIn => {
if(isLoggedIn){
if (isLoggedIn) {
SelectedElementTagsUpdater.installCallback(state)
return true;
}
})
}
private static installCallback(state: {
public static installCallback(state: {
selectedElement: UIEventSource<any>,
allElements: ElementStorage,
changes: Changes,
@ -36,80 +43,99 @@ export default class SelectedElementTagsUpdater {
state.selectedElement.addCallbackAndRunD(s => {
let id = s.properties?.id
const backendUrl = state.osmConnection._oauth_config.url
if(id.startsWith(backendUrl)){
if (id.startsWith(backendUrl)) {
id = id.substring(backendUrl.length)
}
if(!(id.startsWith("way") || id.startsWith("node") || id.startsWith("relation"))){
if (!(id.startsWith("way") || id.startsWith("node") || id.startsWith("relation"))) {
// This object is _not_ from OSM, so we skip it!
return;
}
if(id.indexOf("-") >= 0){
if (id.indexOf("-") >= 0) {
// This is a new object
return;
}
OsmObject.DownloadPropertiesOf(id).then(tags => {
SelectedElementTagsUpdater.applyUpdate(state, tags, id)
}).catch(e => {
console.error("Could not update tags of ", id, "due to", e)
OsmObject.DownloadPropertiesOf(id).then(latestTags => {
SelectedElementTagsUpdater.applyUpdate(state, latestTags, id)
})
});
}
private static applyUpdate(state: {
selectedElement: UIEventSource<any>,
allElements: ElementStorage,
changes: Changes,
osmConnection: OsmConnection
}, latestTags: any, id: string
public static applyUpdate(state: {
selectedElement: UIEventSource<any>,
allElements: ElementStorage,
changes: Changes,
osmConnection: OsmConnection
}, latestTags: any, id: string
) {
const pendingChanges = state.changes.pendingChanges.data
.filter(change => change.type +"/"+ change.id === id)
.filter(change => change.tags !== undefined);
for (const pendingChange of pendingChanges) {
const tagChanges = pendingChange.tags;
for (const tagChange of tagChanges) {
const key = tagChange.k
const v = tagChange.v
if (v === undefined || v === "") {
delete latestTags[key]
} else {
latestTags[key] = v
try {
const pendingChanges = state.changes.pendingChanges.data
.filter(change => change.type + "/" + change.id === id)
.filter(change => change.tags !== undefined);
for (const pendingChange of pendingChanges) {
const tagChanges = pendingChange.tags;
for (const tagChange of tagChanges) {
const key = tagChange.k
const v = tagChange.v
if (v === undefined || v === "") {
delete latestTags[key]
} else {
latestTags[key] = v
}
}
}
}
// With the changes applied, we merge them onto the upstream object
let somethingChanged = false;
const currentTagsSource = state.allElements.getEventSourceById(id);
const currentTags = currentTagsSource.data
for (const key in latestTags) {
let osmValue = latestTags[key]
if(typeof osmValue === "number"){
osmValue = ""+osmValue
}
const localValue = currentTags[key]
if (localValue !== osmValue) {
console.log("Local value for ", key ,":", localValue, "upstream", osmValue)
somethingChanged = true;
currentTags[key] = osmValue
}
}
if (somethingChanged) {
console.log("Detected upstream changes to the object when opening it, updating...")
currentTagsSource.ping()
}else{
console.debug("Fetched latest tags for ", id, "but detected no changes")
}
// With the changes applied, we merge them onto the upstream object
let somethingChanged = false;
const currentTagsSource = state.allElements.getEventSourceById(id);
const currentTags = currentTagsSource.data
for (const key in latestTags) {
let osmValue = latestTags[key]
if (typeof osmValue === "number") {
osmValue = "" + osmValue
}
const localValue = currentTags[key]
if (localValue !== osmValue) {
console.log("Local value for ", key, ":", localValue, "upstream", osmValue)
somethingChanged = true;
currentTags[key] = osmValue
}
}
for (const currentKey in currentTags) {
if (currentKey.startsWith("_")) {
continue
}
if(this.metatags.has(currentKey)){
continue
}
if (currentKey in latestTags) {
continue
}
console.log("Removing key as deleted upstream", currentKey)
delete currentTags[currentKey]
somethingChanged = true
}
if (somethingChanged) {
console.log("Detected upstream changes to the object when opening it, updating...")
currentTagsSource.ping()
} else {
console.debug("Fetched latest tags for ", id, "but detected no changes")
}
} catch (e) {
console.error("Updating the tags of selected element ", id, "failed due to", e)
}
}

View file

@ -5,6 +5,7 @@ import TagRenderingAnswer from "../../UI/Popup/TagRenderingAnswer";
import Combine from "../../UI/Base/Combine";
import LayoutConfig from "../../Models/ThemeConfig/LayoutConfig";
import {ElementStorage} from "../ElementStorage";
import {Utils} from "../../Utils";
export default class TitleHandler {
constructor(state : {
@ -38,6 +39,9 @@ export default class TitleHandler {
currentTitle.addCallbackAndRunD(title => {
if(Utils.runningFromConsole){
return
}
document.title = title
})
}

View file

@ -21,11 +21,13 @@ export default class AllImageProviders {
)
]
public static defaultKeys = [].concat(AllImageProviders.ImageAttributionSource.map(provider => provider.defaultKeyPrefixes))
private static _cache: Map<string, UIEventSource<ProvidedImage[]>> = new Map<string, UIEventSource<ProvidedImage[]>>()
public static LoadImagesFor(tags: UIEventSource<any>, tagKey?: string): UIEventSource<ProvidedImage[]> {
public static LoadImagesFor(tags: UIEventSource<any>, tagKey?: string[]): UIEventSource<ProvidedImage[]> {
if (tags.data.id === undefined) {
return undefined;
}
@ -44,7 +46,7 @@ export default class AllImageProviders {
let prefixes = imageProvider.defaultKeyPrefixes
if(tagKey !== undefined){
prefixes = [...prefixes, tagKey]
prefixes = tagKey
}
const singleSource = imageProvider.GetRelevantUrls(tags, {

View file

@ -27,7 +27,8 @@ export default class ImgurUploader {
files,
function (url) {
console.log("File saved at", url);
self.success.setData([...self.success.data, url]);
self.success.data.push(url)
self.success.ping();
self._handleSuccessUrl(url);
},
function () {

View file

@ -97,6 +97,7 @@ export class Changes {
console.log("Is already uploading... Abort")
return;
}
console.log("Uploading changes due to: ", flushreason)
this.isUploading.setData(true)
this.flushChangesAsync()
@ -287,7 +288,7 @@ export class Changes {
v = undefined;
}
const oldV = obj.type[k]
const oldV = obj.tags[k]
if (oldV === v) {
continue;
}

View file

@ -66,7 +66,9 @@ export abstract class OsmObject {
const url = `${OsmObject.backendURL}api/0.6/${id}`;
const rawData = await Utils.downloadJsonCached(url, 1000)
return rawData.elements[0].tags
const tags = rawData.elements[0].tags
console.log("Tags are", tags)
return tags
}
static async DownloadObjectAsync(id: string): Promise<OsmObject> {
@ -263,7 +265,7 @@ export abstract class OsmObject {
continue;
}
const v = this.tags[key];
if (v !== "") {
if (v !== "" && v !== undefined) {
tags += ' <tag k="' + Utils.EncodeXmlValue(key) + '" v="' + Utils.EncodeXmlValue(this.tags[key]) + '"/>\n'
}
}

View file

@ -5,6 +5,7 @@ import LayoutConfig from "../../Models/ThemeConfig/LayoutConfig";
import {UIEventSource} from "../UIEventSource";
import {QueryParameters} from "../Web/QueryParameters";
import Constants from "../../Models/Constants";
import {Utils} from "../../Utils";
export default class FeatureSwitchState {
@ -137,7 +138,7 @@ export default class FeatureSwitchState {
let testingDefaultValue = false;
if (this.featureSwitchApiURL.data !== "osm-test" &&
if (this.featureSwitchApiURL.data !== "osm-test" && !Utils.runningFromConsole &&
(location.hostname === "localhost" || location.hostname === "127.0.0.1")) {
testingDefaultValue = true
}

View file

@ -286,6 +286,9 @@ export class UIEventSource<T> {
}
public stabilized(millisToStabilize): UIEventSource<T> {
if(Utils.runningFromConsole){
return this;
}
const newSource = new UIEventSource<T>(this.data);