<commit_before># -*- coding: utf-8 -*-
from __future__ import absolute_import

import os
import sys
from datetime import timedelta

from sc2reader.log_utils import loggable
from sc2reader.exceptions import MPQError
from sc2reader.constants import COLOR_CODES, COLOR_CODES_INV

class DepotFile(object):
    """
    :param bytes: The raw bytes representing the depot file

    The DepotFile object parses bytes for a dependency into their components
    and assembles them into a URL so that the dependency can be fetched.
    """

    #: The url template for all DepotFiles
    url_template = 'http://{0}.depot.battle.net:1119/{1}.{2}'

    def __init__(self, bytes):
        #: The server the file is hosted on
        self.server = bytes[4:8].strip('\x00 ')

        # There is no SEA depot, use US instead
        if self.server == 'SEA':
            self.server = 'US'

        #: The unique content based hash of the file
        self.hash = bytes[8:].encode('hex')

        #: The extension of the file on the server
        self.type = bytes[0:4]

    @property
    def url(self):
        """ Returns url of the depot file. """
        return self.url_template.format(self.server, self.hash, self.type)

    def __hash__(self):
        return hash(self.url)

    def __str__(self):
        return self.url


class PersonDict(dict):
    """
    Supports lookup on both the player name and player id

    ::

        person = PersonDict()
        person[1] = Player(1,"ShadesofGray")
        me = person.name("ShadesofGray")
        del person[me.pid]

    Delete is supported on the player id only
    """
    def __init__(self, players=[]):
        super(PersonDict, self).__init__()
        self._key_map = dict()

        # Support creation from iterables
        for player in players:
            self[player.pid] = player

    def name(self, player_name):
        return self[self._key_map[player_name]]

    def __setitem__(self, key, value):
        if isinstance(key, str):
            self._key_map[key] = value.pid
            key = value.pid
        elif isinstance(key, int):
            self._key_map[value.name] = key

        super(PersonDict, self).__setitem__(value.pid, value)


def windows_to_unix(windows_time):
    # This windows timestamp measures the number of 100 nanosecond periods since
    # January 1st, 1601. First we subtract the number of nanosecond periods from
    # 1601-1970, then we divide by 10^7 to bring it back to seconds.
    return (windows_time-116444735995904000)/10**7

class AttributeDict(dict):
    """
    Support access to dictionary items via the dot syntax as though they
    were class attributes. Also support setting new keys via dot syntax.
    """
    def __getattr__(self, name):
        try:
            return self[name]
        except KeyError:
            raise AttributeError('No such attribute {0}'.format(name))

    def __setattr__(self, name, value):
        self[name] = value

    def copy(self):
        return AttributeDict(self.items())

@loggable<commit_msg>Gut and deprecate PersonDict.<commit_after># -*- coding: utf-8 -*-
from __future__ import absolute_import

import os
import sys
from datetime import timedelta

from sc2reader.log_utils import loggable
from sc2reader.exceptions import MPQError
from sc2reader.constants import COLOR_CODES, COLOR_CODES_INV

class DepotFile(object):
    """
    :param bytes: The raw bytes representing the depot file

    The DepotFile object parses bytes for a dependency into their components
    and assembles them into a URL so that the dependency can be fetched.
    """

    #: The url template for all DepotFiles
    url_template = 'http://{0}.depot.battle.net:1119/{1}.{2}'

    def __init__(self, bytes):
        #: The server the file is hosted on
        self.server = bytes[4:8].strip('\x00 ')

        # There is no SEA depot, use US instead
        if self.server == 'SEA':
            self.server = 'US'

        #: The unique content based hash of the file
        self.hash = bytes[8:].encode('hex')

        #: The extension of the file on the server
        self.type = bytes[0:4]

    @property
    def url(self):
        """ Returns url of the depot file. """
        return self.url_template.format(self.server, self.hash, self.type)

    def __hash__(self):
        return hash(self.url)

    def __str__(self):
        return self.url


class PersonDict(dict):
    """
    Deprecated!

    Supports lookup on both the player name and player id

    ::

        person = PersonDict()
        person[1] = Player(1,"ShadesofGray")
        me = person.name("ShadesofGray")
        del person[me.pid]

    Delete is supported on the player id only
    """
    def __init__(self):
        super(PersonDict, self).__init__()
        self._key_map = dict()

    def name(self, player_name):
        """ deprecated because it is possible for multiple players to have the same name. """
        return self[self._key_map[player_name]]

    def __setitem__(self, key, value):
        self._key_map[value.name] = key
        super(PersonDict, self).__setitem__(key, value)


def windows_to_unix(windows_time):
    # This windows timestamp measures the number of 100 nanosecond periods since
    # January 1st, 1601. First we subtract the number of nanosecond periods from
    # 1601-1970, then we divide by 10^7 to bring it back to seconds.
    return (windows_time-116444735995904000)/10**7

class AttributeDict(dict):
    """
    Support access to dictionary items via the dot syntax as though they
    were class attributes. Also support setting new keys via dot syntax.
    """
    def __getattr__(self, name):
        try:
            return self[name]
        except KeyError:
            raise AttributeError('No such attribute {0}'.format(name))

    def __setattr__(self, name, value):
        self[name] = value

    def copy(self):
        return AttributeDict(self.items())

@loggable
{'fraction_non_alphanumeric': 0.09333333333333334, 'fraction_numerical': 0.020590717299578058, 'mean_word_length': 2.6693498452012383, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '763724', 'n_tokens_mistral': 1809, 'n_tokens_neox': 1692, 'n_words': 583}