# -*- coding: utf-8 -*- """ hyper/http20/util ~~~~~~~~~~~~~~~~~ Utility functions for use with hyper. """ from collections import defaultdict def combine_repeated_headers(kvset): """ Given a list of key-value pairs (like for HTTP headers!), combines pairs with the same key together, separating the values with NULL bytes. This function maintains the order of input keys, because it's awesome. """ def set_pop(set, item): set.remove(item) return item headers = defaultdict(list) keys = set() for key, value in kvset: headers[key].append(value) keys.add(key) return [(set_pop(keys, k), b'\x00'.join(headers[k])) for k, v in kvset if k in keys] def split_repeated_headers(kvset): """ Given a set of key-value pairs (like for HTTP headers!), finds values that have NULL bytes in them and splits them into a dictionary whose values are lists. """ headers = defaultdict(list) for key, value in kvset: headers[key] = value.split(b'\x00') return dict(headers) def h2_safe_headers(headers): """ This method takes a set of headers that are provided by the user and transforms them into a form that is safe for emitting over HTTP/2. Currently, this strips the Connection header and any header it refers to. """ stripped = { i.lower().strip() for k, v in headers if k == 'connection' for i in v.split(',') } stripped.add('connection') return [header for header in headers if header[0] not in stripped]