Добавить поддержку utf-8 в tcl - PullRequest
1 голос
/ 14 апреля 2011
set botlisten(port) "3333"
set botlisten(password) "123456"
set botlisten(channel) "#chan"
listen $botlisten(port) script botlisten
proc botlisten {idx} {
    control $idx botlisten2
}
proc botlisten2 {idx args} {
global botlisten newTorrentChannel
set args [join $args]
set botlisten(pass) [lindex [split $args] 0]
set botlisten(message) [join [lrange [split $args] 1 end]]
if {[string match $botlisten(pass) $botlisten(password)]} then {
   putquick "PRIVMSG $botlisten(channel) :$botlisten(message)"
 } else {
  putlog "Unauthorized person tried to connect to the bot"
  }
}  

Пусть, скажем, сообщение имеет следующие символы: ąčęėįšįūž, так что бот выдает странные символы. Поэтому, на мой взгляд, решение - добавить поддержку utf-8.

1 Ответ

6 голосов
/ 15 апреля 2011

Tcl имеет полностью интегрированную поддержку UTF-8 уже более десяти лет (начиная с Tcl 8.1, хотя никто больше не использует эту версию в здравом уме, поскольку есть монотонно лучшие).

Однако, как правило, необходимо сообщить Tcl о том, какая кодировка используется в конкретном канале связи с внешним миром (с параметром fconfigure -encoding). Tcl использует предположение по умолчанию, которое зависит от системы; в моей системе это на самом деле UTF-8, но в других это ISO 8859-1 или -15 или соответствующая кодовая страница Windows. (Tcl хорошо умеет делать предположения по умолчанию, кстати.) В сокетах это более неудобно, так как кодирование - это то, что на самом деле является решением на уровне протокола (некоторые протоколы задают определенную кодировку - SMTP делает, IIRC - некоторые кодировки коммутатора во время работы протокола - HTTP является ярким примером этого - а некоторые вообще не указывают - IRC является классическим примером этого). В некоторых случаях необходима команда encoding, чтобы сценарии могли вручную управлять преобразованием между последовательностями байтов и символами. Это довольно редко, хотя.

Конечно, если используемый код просто берет строки Tcl и вслепую проталкивает их по сети, используя низкоуровневую сеть (привет, eggdrop!), Тогда на самом деле не все, что может сделать общий уровень Tcl. Обходные пути в этом случае - либо создать eggdrop, чтобы использовать другую кодировку (как говорит Ноль из его комментария ), либо использовать encoding, чтобы выполнить поиск, например:

Преобразование UTF-8 в закодированную форму:

set encoded [encoding convertto utf-8 $normalString]

Преобразование закодированного UTF-8 обратно в обычную строку:

set normalString [encoding convertfrom utf-8 $encoded]
...