aboutsummaryrefslogtreecommitdiff
path: root/src/client/DocServer.ts
blob: 615e48af0d73ddcc5dae480ba6b318c4454406d3 (plain)
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
import * as OpenSocket from 'socket.io-client';
import { MessageStore, Types } from "./../server/Message";
import { Opt, FieldWaiting, RefField, HandleUpdate } from '../new_fields/Doc';
import { Utils } from '../Utils';
import { SerializationHelper } from './util/SerializationHelper';

export namespace DocServer {
    const _cache: { [id: string]: RefField | Promise<Opt<RefField>> } = {};
    const _socket = OpenSocket(`${window.location.protocol}//${window.location.hostname}:4321`);
    const GUID: string = Utils.GenerateGuid();

    export async function GetRefField(id: string): Promise<Opt<RefField>> {
        let cached = _cache[id];
        if (cached === undefined) {
            const prom = Utils.EmitCallback(_socket, MessageStore.GetRefField, id).then(fieldJson => {
                const field = fieldJson === undefined ? fieldJson : SerializationHelper.Deserialize(fieldJson);
                if (field) {
                    _cache[id] = field;
                } else {
                    delete _cache[id];
                }
                return field;
            });
            _cache[id] = prom;
            return prom;
        } else if (cached instanceof Promise) {
            return cached;
        } else {
            return cached;
        }
    }

    export function UpdateField(id: string, diff: any) {
        Utils.Emit(_socket, MessageStore.UpdateField, { id, diff });
    }

    export function CreateField(initialState: any) {
        if (!("id" in initialState)) {
            throw new Error("Can't create a field on the server without an id");
        }
        Utils.Emit(_socket, MessageStore.CreateField, initialState);
    }

    function respondToUpdate(diff: any) {
        const id = diff.id;
        if (id === undefined) {
            return;
        }
        const field = _cache[id];
        const update = (f: Opt<RefField>) => {
            if (f === undefined) {
                return;
            }
            const handler = f[HandleUpdate];
            if (handler) {
                handler(diff);
            }
        };
        if (field instanceof Promise) {
            field.then(update);
        } else {
            update(field);
        }
    }

    function connected(message: string) {
        _socket.emit(MessageStore.Bar.Message, GUID);
    }

    Utils.AddServerHandler(_socket, MessageStore.Foo, connected);
    Utils.AddServerHandler(_socket, MessageStore.UpdateField, respondToUpdate);
}