'Read an at-rule from a token stream.
:param at_keyword_token:
The ATKEYWORD token that starts this at-rule
You may have read it already to distinguish the rule
from a ruleset.
:param tokens:
An iterator of subsequent tokens. Will be consumed just enough
for one at-rule.
:return:
An unparsed :class:`AtRule`.
:raises:
:class:`~.parsing.ParseError` if the head is invalid for the core
grammar. The body is **not** validated. See :class:`AtRule`.'

def read_at_rule(self, at_keyword_token, tokens):

    at_keyword = at_keyword_token.value.lower()
    head = []
    token = at_keyword_token
    for token in tokens:
        if (token.type in u'{;'):
            break
        else:
            head.append(token)
    head = strip_whitespace(head)
    for head_token in head:
        validate_any(head_token, u'at-rule    head')
    body = (token.content if (token.type == u'{') else None)
    return AtRule(at_keyword, head, body, at_keyword_token.line, at_keyword_token.column)
