2012-05-10 17 views
7

İndirmek ve indirmek için bir dosyanın URL'sini ayıklamak için Ruby kullanıyorum. Dosya adının utf8 karakterleri vardır, örn .:ASCII karakterlerinin URL kodlamasını nasıl yaparım?

Yukarıdaki URL'yi indirmeye çalışırken, başarısız olur.

www.domain.com/.../%C3%96%C3%87%C3%84%C3%9C360%C3%93%C3%AF%C3%92%C3%B4%C3%96%C3%BA%C3%80%C3%AD.txt 

Ama URL Encoding Reference izlerseniz, çalışır:: URI::escape kullanmak da işe yaramaz bir URI üretir Aynı kesin yapar Ruby bir işlev aramak için çalıştı

www.domain.com/.../%D6%C7%C4%DC360%D3%EF%D2%F4%D6%FA%C0%ED.txt 

kodlama, ancak bulamadım. Yukarıdaki bağlantıdaki tabloyu uygulayan bir fonksiyon yazmaya başlamadan önce, bunu yapan herhangi bir kütüphaneyi bilen var mı diye sormak istiyorum. Ve eğer bunu yapmaya karar verirsem, şifrelemem gereken karakter dizisi, açıkçası, her şey değil.

Ben karakter kodlamaları => "1.8.7"

+1

Bayt C3 96, UTF-8 kodlu bir Ö'dir. Aynı karakter ASCII'de tek bayt D6 olarak temsil edilir. Bu nedenle, soruna yaklaşmanın bir yolu, UTF-8 karakterlerinizi, yapabileceğiniz ASCII'ye ve ardından URI :: çıkışına dönüştürmektir. Ancak bu, ASCII eşdeğeri olmayan Unicode karakterleri için size yardımcı olmaz. –

+0

['CGI.escape'] 'i (http://ruby-doc.org/stdlib-1.9.3/libdoc/cgi/rdoc/CGI.html#method-c-escape) denediniz mi? –

+0

@DavidGorsline: Bu işe yaramıyor. Sonunda '?' '360' ve '.txt' dışındaki tüm karakterler için. Yukarıdaki örnek gerçek bir örnektir, eğer herhangi bir fikriniz varsa bunları'ÖÇÄÜ360ÓïÒôÖúÀí.txt 'dizesinde test edebilir ve nasıl yapılacağını bana bildirin. Yardımınız için çok teşekkürler. – Rami

cevap

15

Ah, sevinçlerini RUBY_VERSION ile JRuby 1.6.2 kullanıyorum!

Burada olup bitenler şu şekildedir. Ruby dahili olarak, ayıkladığınız dizeyi dosya adının utf-8 kodlaması olan bayt dizisi olarak depolar. Üzerinde URI.escape aradığınızda, bu baytlar %xy biçiminde kaçtı ve artık yalnızca ASCII aralığındaki baytlardan oluşan sonuç dizesi, url olarak kullanılır.

ancak, farklı bir kodlamada sanki bu durumda ISO-8859-1 yılında, (%xy formdan onları atlanmaması, sonra) bu bayt yorumluyor alıcı sunucusu ve böylece ortaya çıkan dosya o şey o uymuyor ile geliyor vardır.

Kodlamalarda daha iyi destek sağladığı için, Ruby 1.9'u kullanarak bir gösteri.

1.9.3-p194 :003 > f 
=> "ÖÇÄÜ360ÓïÒôÖúÀí.txt" 
1.9.3-p194 :004 > f.encoding 
=> #<Encoding:UTF-8> 
1.9.3-p194 :005 > URI.escape f 
=> "%C3%96%C3%87%C3%84%C3%9C360%C3%93%C3%AF%C3%92%C3%B4%C3%96%C3%BA%C3%80%C3%AD.txt" 
1.9.3-p194 :006 > g = f.encode 'iso-8859-1' 
=> "\xD6\xC7\xC4\xDC360\xD3\xEF\xD2\xF4\xD6\xFA\xC0\xED.txt" 
1.9.3-p194 :007 > g.encoding 
=> #<Encoding:ISO-8859-1> 
1.9.3-p194 :008 > URI.escape g 
=> "%D6%C7%C4%DC360%D3%EF%D2%F4%D6%FA%C0%ED.txt" 

bu durumda çözüm onu kaçmadan önce ISO-8859-1 olarak dize kodlamak etmektir. Eğer (Ben aslında JRuby ile aşina değilim, JRuby Iconv içerir varsayarak) Iconv kullanabilirsiniz Ruby 1.9 size önceki sürümlerinde, yukarıdaki gibi bu do:

1.8.7 :001 > f 
=> "\303\226\303\207\303\204\303\234360\303\223\303\257\303\222\303\264\303\226\303\272\303\200\303\255.txt" 
1.8.7 :005 > g = Iconv.conv('iso-8859-1', 'utf-8', f) 
=> "\326\307\304\334360\323\357\322\364\326\372\300\355.txt" 
1.8.7 :006 > URI.escape f 
=> "%C3%96%C3%87%C3%84%C3%9C360%C3%93%C3%AF%C3%92%C3%B4%C3%96%C3%BA%C3%80%C3%AD.txt" 
1.8.7 :007 > URI.escape g 
=> "%D6%C7%C4%DC360%D3%EF%D2%F4%D6%FA%C0%ED.txt" 

Not 'genel olarak olabildiğince bu Belirli bir kodlamayı kullanarak sunucuya bağlı. ,'un utf-8'i kullanması gerekir, ancak açıkçası bu durumda değildir.

+0

Harika, teşekkürler! – Rami

+0

Bu çok yararlı oldu, kodlamadan sonra URI.escape için gereken bir ipucu yoktu. – KnuturO