from typing import OrderedDict
import math


def get_latencies_summary(latencies):
    """
    Given a raw timeseries of latencies, create a summary of each point in time,
    with the average standard deviation and mean, the minimum and maximum, and
    the minimum/maximum range for the percentiles (as we can't average them).
    """
    summaries = OrderedDict()

    for ts, lat in latencies.items():
        sum_samples = float(sum([c['samples'] for c in lat.values()]))

        # if sum of samples is zero, ignore (means end of metrics)
        if sum_samples == 0:
            continue

        avg_var  = 0.0
        avg_mean = 0.0
        mins = []
        maxs = []
        pcs = {'p50': [], 'p75': [], 'p95': [], 'p98': [], 'p99': [], 'p999': []}

        for c in lat.values():
            avg_var  += (float(c['samples']) / sum_samples) * math.pow(c['stddev'], 2)
            avg_mean += (float(c['samples']) / sum_samples) * c['mean']
            mins.append(c['min'])
            maxs.append(c['max'])

            for pc in pcs.keys():
                pcs[pc].append(c[pc])

        summary = {'stddev': math.sqrt(avg_var), 'mean': avg_mean,
                   'min': min(mins), 'max': max(maxs), 'samples': sum_samples}

        for pc, vals in pcs.items():
            summary[pc] = {'min': min(vals), 'max': max(vals)}

        summaries[ts] = summary

    return summaries