File size: 4,546 Bytes
4cadbaf
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
import { __extends } from "tslib";
import { EventEmitter } from "events";
import sha1 from "sha1";
import * as diff from "diff";
var RemoteFile = /** @class */ (function (_super) {
    __extends(RemoteFile, _super);
    function RemoteFile(_a) {
        var _b = (_a === void 0 ? {} : _a).autoReconnect, autoReconnect = _b === void 0 ? false : _b;
        var _this = _super.call(this) || this;
        _this.connected = false;
        _this.autoReconnect = autoReconnect;
        return _this;
    }
    Object.defineProperty(RemoteFile.prototype, "hash", {
        get: function () {
            return sha1(this._content);
        },
        enumerable: false,
        configurable: true
    });
    Object.defineProperty(RemoteFile.prototype, "content", {
        get: function () {
            return this._content;
        },
        set: function (value) {
            var timestamp = Date.now();
            var patch = diff.createPatch(this.filePath, this._content, value);
            this.socket.send(JSON.stringify({
                command: "increase",
                timestamp: timestamp,
                fromHash: this.hash,
                toHash: sha1(value),
                patch: patch,
            }));
            this.timestamp = timestamp;
            this._content = value;
        },
        enumerable: false,
        configurable: true
    });
    RemoteFile.prototype.connect = function (host, filePath) {
        var _this = this;
        if (this.socket)
            this.socket.close();
        this.socket = new WebSocket(host, "editor-frontend");
        this.socket.onopen = function () {
            console.debug("[RemoteFile]	socket open.");
            _this.connected = true;
            _this.emit("connected");
            _this.socket.send(JSON.stringify({ command: "bindFile", filePath: filePath }));
        };
        this.socket.onclose = function (event) {
            console.debug("Synchronizer service socket closed:", event.code, event.reason);
            _this.connected = false;
            _this.emit("disconnected");
            if (_this.autoReconnect && event.code === 1006) {
                console.log("[RemoteFile]	try to reconnect...");
                setTimeout(function () { return _this.connect(host, filePath); }, 100);
            }
        };
        this.socket.onmessage = function (event) {
            var message = JSON.parse(event.data);
            switch (message.command) {
                case "failure":
                    console.warn("service failure:", message.description);
                    _this.close();
                    break;
                case "fullSync":
                    _this.timestamp = message.timestamp;
                    _this._content = message.content;
                    console.assert(_this.hash === message.hash, "[RemoteFile] verify failed:", _this.hash, message.hash);
                    _this.emit("sync", { timestamp: _this.timestamp });
                    break;
                case "increase":
                    //console.log("increase:", this.hash, message);
                    // already consistent with remote, update timestemp only
                    if (_this.hash === message.toHash) {
                        _this.timestamp = Math.max(_this.timestamp, message.timestamp);
                        break;
                    }
                    if (_this.hash !== message.fromHash) {
                        if (message.timestamp < _this.timestamp)
                            break;
                        console.warn("hash mismatched:", _this.hash, message.fromHash);
                        _this.socket.send(JSON.stringify({ command: "requestFullSync", timestamp: _this.timestamp }));
                    }
                    else {
                        _this.timestamp = message.timestamp;
                        _this._content = diff.applyPatch(_this._content, message.patch);
                        console.assert(_this.hash === message.toHash, "[RemoteFile] verify failed:", _this.hash, message.toHash);
                        _this.emit("sync", { timestamp: _this.timestamp });
                    }
                    break;
                default:
                    console.warn("[RemoteFile]	unexpected command:", message);
            }
        };
        this.filePath = filePath;
    };
    RemoteFile.prototype.close = function () {
        this.socket.close();
    };
    return RemoteFile;
}(EventEmitter));
export default RemoteFile;
;
//# sourceMappingURL=remoteFile.js.map