#-*- coding: utf-8 -*-
import re
from copy import copy

from django.template.defaultfilters import slugify
        

def slughifi(value, do_slugify=True, overwrite_char_map={}):
    u"""
    High Fidelity slugify - slughifi.py
        
    Examples :
    >>> s = 'Mała skacząca żabka śmieje się ze swojego kolegi królika.'
    >>> isinstance(s, str)
    True
    >>> slughifi(s)
    u'mala-skaczaca-zabka-smieje-sie-ze-swojego-kolegi-krolika'
    >>> slughifi(s.decode('utf-8'))
    u'mala-skaczaca-zabka-smieje-sie-ze-swojego-kolegi-krolika'

    while the slugify function ignores letter 'Å‚'
    >>> slugify(s)
    u'maa-skaczaca-zabka-smieje-sie-ze-swojego-kolegi-krolika'

    >>> slughifi(s, False)
    'Mala skaczaca zabka smieje sie ze swojego kolegi krolika.'

    >>> slughifi(s, True, {u'ż': 'b'})
    u'mala-skaczaca-babka-smieje-sie-ze-swojego-kolegi-krolika'

    >>> slughifi(s, True, {u'Å‚': 'j'})
    u'maja-skaczaca-zabka-smieje-sie-ze-swojego-kolegi-krolika'
    """

    # unicodification
    if not isinstance(value, unicode):
        value = unicode(value, 'utf-8', 'ignore')
     
    # overwrite chararcter mapping
    if overwrite_char_map:
        local_char_map = copy(CHAR_MAP)
        local_char_map.update(overwrite_char_map)
    else:
        local_char_map = CHAR_MAP

    def replace_char(m):
        char = m.group()
        if local_char_map.has_key(char):
            return local_char_map[char]
        else:
            return char

    # try to replace chars
    value = re.sub(r'[^a-zA-Z0-9\s\-]{1}', replace_char, value)
    
    # apply django default slugify
    if do_slugify:
        return slugify(value)
        
    return value.encode('ascii', 'ignore')


# default unicode character mapping ( you may not see some chars, leave as is )
CHAR_MAP = {
    u'À': 'A',
    u'Á': 'A',
    u'Â': 'A',
    u'Ã': 'A',
    u'Ä': 'Ae',
    u'Ã…': 'A',
    u'Æ': 'A',
    u'Ä€': 'A',
    u'Ä„': 'A',
    u'Ä‚': 'A',
    u'Ç': 'C',
    u'Ć': 'C',
    u'Č': 'C',
    u'Ĉ': 'C',
    u'ÄŠ': 'C',
    u'ÄŽ': 'D',
    u'Đ': 'D',
    u'È': 'E',
    u'É': 'E',
    u'Ê': 'E',
    u'Ë': 'E',
    u'Ä’': 'E',
    u'Ę': 'E',
    u'Äš': 'E',
    u'Ä”': 'E',
    u'Ä–': 'E',
    u'Ĝ': 'G',
    u'Äž': 'G',
    u'Ä ': 'G',
    u'Ä¢': 'G',
    u'Ĥ': 'H',
    u'Ħ': 'H',
    u'Ì': 'I',
    u'Í': 'I',
    u'ÃŽ': 'I',
    u'Ï': 'I',
    u'Ī': 'I',
    u'Ĩ': 'I',
    u'Ĭ': 'I',
    u'Ä®': 'I',
    u'Ä°': 'I',
    u'IJ': 'IJ',
    u'Ä´': 'J',
    u'Ķ': 'K',
    u'Ľ': 'K',
    u'Ĺ': 'K',
    u'Ä»': 'K',
    u'Ä¿': 'K',
    u'Ł': 'L',
    u'Ñ': 'N',
    u'Ń': 'N',
    u'Ň': 'N',
    u'Å…': 'N',
    u'ÅŠ': 'N',
    u'Ã’': 'O',
    u'Ó': 'O',
    u'Ô': 'O',
    u'Õ': 'O',
    u'Ö': 'Oe',
    u'Ø': 'O',
    u'Ō': 'O',
    u'Ő': 'O',
    u'ÅŽ': 'O',
    u'Å’': 'OE',
    u'Å”': 'R',
    u'Ř': 'R',
    u'Å–': 'R',
    u'Åš': 'S',
    u'Åž': 'S',
    u'Ŝ': 'S',
    u'Ș': 'S',
    u'Å ': 'S',
    u'Ť': 'T',
    u'Å¢': 'T',
    u'Ŧ': 'T',
    u'Èš': 'T',
    u'Ù': 'U',
    u'Ú': 'U',
    u'Û': 'U',
    u'Ü': 'Ue',
    u'Ū': 'U',
    u'Å®': 'U',
    u'Å°': 'U',
    u'Ŭ': 'U',
    u'Ũ': 'U',
    u'Ų': 'U',
    u'Å´': 'W',
    u'Ŷ': 'Y',
    u'Ÿ': 'Y',
    u'Ý': 'Y',
    u'Ź': 'Z',
    u'Å»': 'Z',
    u'Ž': 'Z',
    u'à': 'a',
    u'á': 'a',
    u'â': 'a',
    u'ã': 'a',
    u'ä': 'ae',
    u'ā': 'a',
    u'Ä…': 'a',
    u'ă': 'a',
    u'Ã¥': 'a',
    u'æ': 'ae',
    u'ç': 'c',
    u'ć': 'c',
    u'č': 'c',
    u'ĉ': 'c',
    u'Ä‹': 'c',
    u'ď': 'd',
    u'Ä‘': 'd',
    u'è': 'e',
    u'é': 'e',
    u'ê': 'e',
    u'ë': 'e',
    u'Ä“': 'e',
    u'Ä™': 'e',
    u'Ä›': 'e',
    u'Ä•': 'e',
    u'Ä—': 'e',
    u'Æ’': 'f',
    u'ĝ': 'g',
    u'ÄŸ': 'g',
    u'Ä¡': 'g',
    u'Ä£': 'g',
    u'Ä¥': 'h',
    u'ħ': 'h',
    u'ì': 'i',
    u'í': 'i',
    u'î': 'i',
    u'ï': 'i',
    u'Ä«': 'i',
    u'Ä©': 'i',
    u'Ä­': 'i',
    u'į': 'i',
    u'ı': 'i',
    u'ij': 'ij',
    u'ĵ': 'j',
    u'Ä·': 'k',
    u'ĸ': 'k',
    u'Å‚': 'l',
    u'ľ': 'l',
    u'ĺ': 'l',
    u'ļ': 'l',
    u'Å€': 'l',
    u'ñ': 'n',
    u'Å„': 'n',
    u'ň': 'n',
    u'ņ': 'n',
    u'ʼn': 'n',
    u'Å‹': 'n',
    u'ò': 'o',
    u'ó': 'o',
    u'ô': 'o',
    u'õ': 'o',
    u'ö': 'oe',
    u'ø': 'o',
    u'ō': 'o',
    u'Å‘': 'o',
    u'ŏ': 'o',
    u'Å“': 'oe',
    u'Å•': 'r',
    u'Å™': 'r',
    u'Å—': 'r',
    u'Å›': 's',
    u'Å¡': 's',
    u'Å¥': 't',
    u'ù': 'u',
    u'ú': 'u',
    u'û': 'u',
    u'ü': 'ue',
    u'Å«': 'u',
    u'ů': 'u',
    u'ű': 'u',
    u'Å­': 'u',
    u'Å©': 'u',
    u'ų': 'u',
    u'ŵ': 'w',
    u'ÿ': 'y',
    u'ý': 'y',
    u'Å·': 'y',
    u'ż': 'z',
    u'ź': 'z',
    u'ž': 'z',
    u'ß': 'ss',
    u'Å¿': 'ss',
    u'Α': 'A',
    u'Ά': 'A',
    u'Ἀ': 'A',
    u'Ἁ': 'A',
    u'Ἂ': 'A',
    u'Ἃ': 'A',
    u'Ἄ': 'A',
    u'Ἅ': 'A',
    u'Ἆ': 'A',
    u'Ἇ': 'A',
    u'ᾈ': 'A',
    u'ᾉ': 'A',
    u'ᾊ': 'A',
    u'ᾋ': 'A',
    u'ᾌ': 'A',
    u'ᾍ': 'A',
    u'ᾎ': 'A',
    u'ᾏ': 'A',
    u'Ᾰ': 'A',
    u'á¾¹': 'A',
    u'Ὰ': 'A',
    u'á¾»': 'A',
    u'á¾¼': 'A',
    u'Î’': 'B',
    u'Γ': 'G',
    u'Δ': 'D',
    u'Ε': 'E',
    u'Έ': 'E',
    u'Ἐ': 'E',
    u'á¼™': 'E',
    u'Ἒ': 'E',
    u'á¼›': 'E',
    u'Ἔ': 'E',
    u'Ἕ': 'E',
    u'Έ': 'E',
    u'Ὲ': 'E',
    u'Ζ': 'Z',
    u'Η': 'I',
    u'Ή': 'I',
    u'Ἠ': 'I',
    u'Ἡ': 'I',
    u'Ἢ': 'I',
    u'Ἣ': 'I',
    u'Ἤ': 'I',
    u'á¼­': 'I',
    u'á¼®': 'I',
    u'Ἧ': 'I',
    u'ᾘ': 'I',
    u'á¾™': 'I',
    u'ᾚ': 'I',
    u'á¾›': 'I',
    u'ᾜ': 'I',
    u'ᾝ': 'I',
    u'ᾞ': 'I',
    u'ᾟ': 'I',
    u'á¿Š': 'I',
    u'á¿‹': 'I',
    u'ῌ': 'I',
    u'Θ': 'TH',
    u'Ι': 'I',
    u'Ί': 'I',
    u'Ϊ': 'I',
    u'Ἰ': 'I',
    u'á¼¹': 'I',
    u'Ἲ': 'I',
    u'á¼»': 'I',
    u'á¼¼': 'I',
    u'á¼½': 'I',
    u'á¼¾': 'I',
    u'Ἷ': 'I',
    u'Ῐ': 'I',
    u'á¿™': 'I',
    u'á¿š': 'I',
    u'á¿›': 'I',
    u'Κ': 'K',
    u'Λ': 'L',
    u'Μ': 'M',
    u'Ν': 'N',
    u'Ξ': 'KS',
    u'Ο': 'O',
    u'Ό': 'O',
    u'Ὀ': 'O',
    u'Ὁ': 'O',
    u'Ὂ': 'O',
    u'Ὃ': 'O',
    u'Ὄ': 'O',
    u'Ὅ': 'O',
    u'Ὸ': 'O',
    u'Ό': 'O',
    u'Π': 'P',
    u'Ρ': 'R',
    u'Ῥ': 'R',
    u'Σ': 'S',
    u'Τ': 'T',
    u'Î¥': 'Y',
    u'ÎŽ': 'Y',
    u'Ϋ': 'Y',
    u'á½™': 'Y',
    u'á½›': 'Y',
    u'Ὕ': 'Y',
    u'Ὗ': 'Y',
    u'Ῠ': 'Y',
    u'á¿©': 'Y',
    u'Ὺ': 'Y',
    u'á¿«': 'Y',
    u'Φ': 'F',
    u'Χ': 'X',
    u'Ψ': 'PS',
    u'Ω': 'O',
    u'Ώ': 'O',
    u'Ὠ': 'O',
    u'Ὡ': 'O',
    u'Ὢ': 'O',
    u'Ὣ': 'O',
    u'Ὤ': 'O',
    u'á½­': 'O',
    u'á½®': 'O',
    u'Ὧ': 'O',
    u'ᾨ': 'O',
    u'ᾩ': 'O',
    u'ᾪ': 'O',
    u'ᾫ': 'O',
    u'ᾬ': 'O',
    u'á¾­': 'O',
    u'á¾®': 'O',
    u'ᾯ': 'O',
    u'Ὼ': 'O',
    u'á¿»': 'O',
    u'ῼ': 'O',
    u'α': 'a',
    u'ά': 'a',
    u'á¼€': 'a',
    u'ἁ': 'a',
    u'ἂ': 'a',
    u'ἃ': 'a',
    u'ἄ': 'a',
    u'á¼…': 'a',
    u'ἆ': 'a',
    u'ἇ': 'a',
    u'á¾€': 'a',
    u'ᾁ': 'a',
    u'ᾂ': 'a',
    u'ᾃ': 'a',
    u'ᾄ': 'a',
    u'á¾…': 'a',
    u'ᾆ': 'a',
    u'ᾇ': 'a',
    u'á½°': 'a',
    u'á½±': 'a',
    u'á¾°': 'a',
    u'á¾±': 'a',
    u'á¾²': 'a',
    u'á¾³': 'a',
    u'á¾´': 'a',
    u'ᾶ': 'a',
    u'á¾·': 'a',
    u'β': 'b',
    u'γ': 'g',
    u'δ': 'd',
    u'ε': 'e',
    u'έ': 'e',
    u'ἐ': 'e',
    u'ἑ': 'e',
    u'á¼’': 'e',
    u'ἓ': 'e',
    u'á¼”': 'e',
    u'ἕ': 'e',
    u'á½²': 'e',
    u'á½³': 'e',
    u'ζ': 'z',
    u'η': 'i',
    u'ή': 'i',
    u'á¼ ': 'i',
    u'ἡ': 'i',
    u'á¼¢': 'i',
    u'á¼£': 'i',
    u'ἤ': 'i',
    u'á¼¥': 'i',
    u'ἦ': 'i',
    u'ἧ': 'i',
    u'ᾐ': 'i',
    u'ᾑ': 'i',
    u'á¾’': 'i',
    u'ᾓ': 'i',
    u'á¾”': 'i',
    u'ᾕ': 'i',
    u'á¾–': 'i',
    u'á¾—': 'i',
    u'á½´': 'i',
    u'á½µ': 'i',
    u'á¿‚': 'i',
    u'ῃ': 'i',
    u'á¿„': 'i',
    u'ῆ': 'i',
    u'ῇ': 'i',
    u'θ': 'th',
    u'ι': 'i',
    u'ί': 'i',
    u'ÏŠ': 'i',
    u'ΐ': 'i',
    u'á¼°': 'i',
    u'á¼±': 'i',
    u'á¼²': 'i',
    u'á¼³': 'i',
    u'á¼´': 'i',
    u'á¼µ': 'i',
    u'ἶ': 'i',
    u'á¼·': 'i',
    u'ὶ': 'i',
    u'á½·': 'i',
    u'ῐ': 'i',
    u'á¿‘': 'i',
    u'á¿’': 'i',
    u'á¿“': 'i',
    u'á¿–': 'i',
    u'á¿—': 'i',
    u'κ': 'k',
    u'λ': 'l',
    u'μ': 'm',
    u'ν': 'n',
    u'ξ': 'ks',
    u'ο': 'o',
    u'ό': 'o',
    u'á½€': 'o',
    u'ὁ': 'o',
    u'ὂ': 'o',
    u'ὃ': 'o',
    u'ὄ': 'o',
    u'á½…': 'o',
    u'ὸ': 'o',
    u'á½¹': 'o',
    u'Ï€': 'p',
    u'ρ': 'r',
    u'ῤ': 'r',
    u'á¿¥': 'r',
    u'σ': 's',
    u'Ï‚': 's',
    u'Ï„': 't',
    u'Ï…': 'y',
    u'ύ': 'y',
    u'Ï‹': 'y',
    u'ΰ': 'y',
    u'ὐ': 'y',
    u'ὑ': 'y',
    u'á½’': 'y',
    u'ὓ': 'y',
    u'á½”': 'y',
    u'ὕ': 'y',
    u'á½–': 'y',
    u'á½—': 'y',
    u'ὺ': 'y',
    u'á½»': 'y',
    u'á¿ ': 'y',
    u'á¿¡': 'y',
    u'á¿¢': 'y',
    u'á¿£': 'y',
    u'ῦ': 'y',
    u'ῧ': 'y',
    u'φ': 'f',
    u'χ': 'x',
    u'ψ': 'ps',
    u'ω': 'o',
    u'ÏŽ': 'o',
    u'á½ ': 'o',
    u'ὡ': 'o',
    u'á½¢': 'o',
    u'á½£': 'o',
    u'ὤ': 'o',
    u'á½¥': 'o',
    u'ὦ': 'o',
    u'ὧ': 'o',
    u'á¾ ': 'o',
    u'ᾡ': 'o',
    u'á¾¢': 'o',
    u'á¾£': 'o',
    u'ᾤ': 'o',
    u'á¾¥': 'o',
    u'ᾦ': 'o',
    u'ᾧ': 'o',
    u'á½¼': 'o',
    u'á½½': 'o',
    u'ῲ': 'o',
    u'ῳ': 'o',
    u'á¿´': 'o',
    u'ῶ': 'o',
    u'á¿·': 'o',
    u'¨': '',
    u'Î…': '',
    u'᾿': '',
    u'῾': '',
    u'῍': '',
    u'῝': '',
    u'á¿Ž': '',
    u'á¿ž': '',
    u'῏': '',
    u'á¿Ÿ': '',
    u'á¿€': '',
    u'῁': '',
    u'΄': '',
    u'á¿®': '',
    u'`': '',
    u'á¿­': '',
    u'ͺ': '',
    u'á¾½': '',
    u'А': 'A',
    u'Б': 'B',
    u'Ð’': 'V',
    u'Г': 'G',
    u'Д': 'D',
    u'Е': 'E',
    u'Ё': 'E',
    u'Ж': 'ZH',
    u'З': 'Z',
    u'И': 'I',
    u'Й': 'I',
    u'К': 'K',
    u'Л': 'L',
    u'М': 'M',
    u'Н': 'N',
    u'О': 'O',
    u'П': 'P',
    u'Р': 'R',
    u'С': 'S',
    u'Т': 'T',
    u'У': 'U',
    u'Ф': 'F',
    u'Ð¥': 'KH',
    u'Ц': 'TS',
    u'Ч': 'CH',
    u'Ш': 'SH',
    u'Щ': 'SHCH',
    u'Ы': 'Y',
    u'Э': 'E',
    u'Ю': 'YU',
    u'Я': 'YA',
    u'а': 'A',
    u'б': 'B',
    u'в': 'V',
    u'г': 'G',
    u'д': 'D',
    u'е': 'E',
    u'Ñ‘': 'E',
    u'ж': 'ZH',
    u'з': 'Z',
    u'и': 'I',
    u'й': 'I',
    u'к': 'K',
    u'л': 'L',
    u'м': 'M',
    u'н': 'N',
    u'о': 'O',
    u'п': 'P',
    u'Ñ€': 'R',
    u'с': 'S',
    u'Ñ‚': 'T',
    u'у': 'U',
    u'Ñ„': 'F',
    u'Ñ…': 'KH',
    u'ц': 'TS',
    u'ч': 'CH',
    u'ш': 'SH',
    u'щ': 'SHCH',
    u'Ñ‹': 'Y',
    u'э': 'E',
    u'ÑŽ': 'YU',
    u'я': 'YA',
    u'Ъ': '',
    u'ÑŠ': '',
    u'Ь': '',
    u'ь': '',
    u'ð': 'd',
    u'Ð': 'D',
    u'þ': 'th',
    u'Þ': 'TH',
    u'ა': 'a',
    u'ბ': 'b',
    u'გ': 'g',
    u'დ': 'd',
    u'ე': 'e',
    u'ვ': 'v',
    u'ზ': 'z',
    u'თ': 't',
    u'ი': 'i',
    u'კ': 'k',
    u'ლ': 'l',
    u'მ': 'm',
    u'ნ': 'n',
    u'ო': 'o',
    u'პ': 'p',
    u'ჟ': 'zh',
    u'რ': 'r',
    u'ს': 's',
    u'ტ': 't',
    u'უ': 'u',
    u'ფ': 'p',
    u'ქ': 'k',
    u'ღ': 'gh',
    u'ყ': 'q',
    u'შ': 'sh',
    u'ჩ': 'ch',
    u'ც': 'ts',
    u'ძ': 'dz',
    u'წ': 'ts',
    u'ჭ': 'ch',
    u'ხ': 'kh',
    u'ჯ': 'j',
    u'ჰ': 'h' 
}


if __name__ == "__main__":
    import doctest
    doctest.testmod()