All files / src/utility stampLog.ts

100% Statements 45/45
100% Branches 12/12
100% Functions 2/2
100% Lines 41/41

Press n or j to go to the next uncovered block, b, p or k for the previous block.

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            57x 65x 65x 64x 63x                   57x 9x 3x           3x 3x 3x 3x 10x 10x 10x 10x 10x 10x 10x 10x 10x     3x 3x   3x 3x 3x 2x 2x   3x 3x 3x 2x 2x 2x 2x     3x 2x 8x 8x 8x   2x  
/**
 * If a log is being kept, add a time stamped line.
 * @param log  Optional time stamped log to extend, or an object with a log property to update
 * @param lineToAdd Content to add to line.
 * @returns undefined or log extended by time stamped `lineToAdd` and new line.
 */
export function stampLog(log: string | undefined | { log?: string }, lineToAdd: string): string | undefined {
    const add = `${new Date().toISOString()} ${lineToAdd}\n`
    if (typeof log === 'object' && typeof log.log === 'string') return log.log = log.log + add
    if (typeof log === 'string') return log + add
    return undefined
}
 
/**
 * Replaces individual timestamps with delta msecs.
 * Looks for two network crossings and adjusts clock for clock skew if found.
 * Assumes log built by repeated calls to `stampLog`
 * @param log Each logged event starts with ISO time stamp, space, rest of line, terminated by `\n`.
 * @returns reformated multi-line event log
 */
export function stampLogFormat(log?: string): string {
    if (typeof (log) !== 'string') return ''
    const logLines = log.split('\n')
    const data: {
        when: number,
        rest: string,
        delta: number,
        newClock: boolean
    }[] = []
    let last = 0
    const newClocks: number[] = []
    for (const line of logLines) {
        const spaceAt = line.indexOf(' ')
        if (spaceAt > -1) {
            const when = new Date(line.substring(0, spaceAt)).getTime()
            const rest = line.substring(spaceAt + 1)
            const delta = when - (last || when)
            const newClock = rest.indexOf('**NETWORK**') > -1
            if (newClock) newClocks.push(data.length)
            data.push({ when, rest, delta, newClock })
            last = when
        }
    }
    const total = data[data.length - 1].when - data[0].when
    if (newClocks.length % 2 === 0) {
        // Adjust for paired network crossing times and clock skew between clocks.
        let network = total
        let lastNewClock = 0
        for (const newClock of newClocks) {
            network -= data[newClock - 1].when - data[lastNewClock].when
            lastNewClock = newClock
        }
        network -= data[data.length - 1].when - data[lastNewClock].when
        let networks = newClocks.length
        for (const newClock of newClocks) {
            const n = networks > 1 ? Math.floor(network / networks) : network
            data[newClock].delta = n
            network -= n
            networks--
        }
    }
    let log2 = `${new Date(data[0].when).toISOString()} Total = ${total} msecs\n`
    for (const d of data) {
        let df = d.delta.toString()
        df = `${' '.repeat(8 - df.length)}${df}`
        log2 += `${df} ${d.rest}\n`
    }
    return log2
}