J o: Nachtrag: Zeitdifferenz

Beitrag lesen

Hallo Rolf,

Erstmal vielen Dank für deine Mühe.

Die SyncedTime Klasse muss gar nicht so oft synchronisieren, man wird davon ausgehen können dass Client- und Server-Uhr in bspw. 5 Minuten nur um wenige Mikrosekunden auseinander laufen. Die 10 Sekunden aus meinem Aufrufbeispiel sind vermutlich viel zu viel.

Das denke ich auch, mal schauen welches Intervall ich dann wählen werde.

Wichtig ist nur, dass der Server die Time-Requests nicht queued, sondern sofort verarbeitet. Bei einem stark belasteten Server kann es zum Queueing kommen, wenn zu viele Requeste eintreffen. Die Laufzeitbalance von Request und Response ist dann schief. Es kann sinnvoll sein, für die Time Requests einen separaten Node laufen zu lassen.

Ich vermute, das habe ich schon unbedacht gelöst aber da möchte ich mich noch nicht zu weit aus dem Fenster lehnen. Hier einmal mein Ansatz:

var _sync = function () {
	this.total = {};
	this.checkList = [];
	this.checkLength = 5;
	this.check = function () {
		for ( let i = 1; i <= 5; i++ ) {
			// webSocket ist ein Objekt welches alle Requests an den Server beinhaltet.
			// webSocket.latency schickt das erzeugte Object zum Server
			// dort wird die Serverzeit ergänzt und das Objekt wird wieder zum Client geschickt
			// danach wird _sync.set aufgerufen und das Objekt in die checkList gepusht
			setTimeout(function(){ webSocket.latency( { clientStart: performance.now(), client: new Date().getTime() } ) }, 250 * i );
		}
	}
	this.set = function ( res ) {
		this.checkList.push( res );
		// wenn die checkList voll ist wird der Mittelwert aus allen Zeiten berechnet
		// und in this.total gespeichert
		if ( this.checkList.length === this.checkLength ) {
			var latency = 0;
			var total = {clientStart: 0, server: 0, clientEnd: 0, diff: 0, latency: 0};
			for ( v of this.checkList ) {
				v.diff = v.client - v.server;
				v.latency = (v.clientEnd - v.clientStart) / 2;
				for ( k in total ) {
					total[k] += v[k];
				}
			}
			for ( k in total ) {
				total[k] /= this.checkLength;
			}
			this.total = Object.assign( {}, total );
			this.checkList = [];
		}
	}
	this.time = function () {
		// hier kann dann die Serverzeit aus this.total und performance.now() berechnet werden
		return new Date(this.total.server + Math.floor(performance.now()) - this.total.clientStart).toLocaleTimeString();
	}
}

Getestet mit:

setTimeout(function(){ setInterval(function(){ console.log(_sync.time()); webSocket.test() }, 5000); }, 6000 );

Wobei webSocket.test() nur den Server anpingt und dieser dann seine Zeit in der Konsole ausgibt.

Und siehe da die Abweichung entspricht genau der Latenz! [ Der Server loggt Serverzeit + Latenz) auf 10 Millisekunden genau ].

Ich muss mir nochmal genau anschauen wie ich eine Grundlast des Servers erzeugen kann, da gibt es ein Modul für Node.js, meine ich in Erinnerung zu haben. Dann kann ich auch sehen welche Ergebnisse diese Berechnung für queued requests liefert.

Gruß
Jo