2011-06-14 22 views
16

Bir URL'yi ayrıştırmam gerekiyor. Şu anda urlparse.urlparse() ve urlparse.urlsplit() kullanıyorum.Gerektiğinde 'http: //' protokolünü bir url'ye nasıl ekleyebilirim?

sorun şeması mevcut değilken ben URL'den "netloc" (ana bilgisayar) alınamıyor olmasıdır. Yani i aşağıdaki URL'yi varsa:

www.amazon.com/Programming-Python-Mark-Lutz/dp/0596158106/ref=sr_1_1?ie=UTF8 & qid = 1308060974 & sr = 8 -1

Ben netloc alamayan

:

sözdizimi özelliklerine ardından: piton docs göre www.amazon.com

RFC 1808, urlparse düzgün ‘//’ tarafından tanıtılan yalnızca bir netloc tanır. Aksi halde, girişin olduğu varsayılarak bir URL olarak ve bir yol bileşeni ile başlatılır.

Yani, bilerek yolu. Ancak, netloc'u bu URL'den nasıl alacağımı hala bilmiyorum.

ben düzeni varsa ben kontrol edebilir düşünüyorum ve eğer o değil, o ekleyin ve sonra ayrıştırmak. Ama bu çözüm gerçekten iyi görünmüyor.

Daha iyi bir fikrin var mı?

DÜZENLEME: tüm cevaplar için teşekkürler. Ama, Corey ve diğerlerinin önerdiği şeyleri başaramıyorum. Becouse, diğer protokol/şema ile bir URL alırsanız, ben onu dağıtırdım. Bkz:

ben bu URL'yi alırsanız: i "http: //" eklersiniz önerilen kod ile

ftp://something.com 

başlangıç ​​ve karışıklık o kadar olur.

i nota

if not urlparse.urlparse(url).scheme: 
    url = "http://"+url 
return urlparse.urlparse(url) 

şey bulduk çözüm:

İlk önce bazı doğrulama yapmak ve herhangi bir şema verilirse ben http olarak kabul: //

+0

mi: o pased eğer protokolünü kullanmak

return "http://" + url.split("://")[-1] 

Daha iyi bir seçenektir için Bunun nedeni, URL'nin protokol kısmı - 'http: //' - eksik mi? – ewall

+0

Evet, nedeni bu. Ancak, şema hala eksikse nasıl alabilirim? senin çözümde – santiagobasulto

+0

, ben hala kontrol ediyorum lider '//' (ve muhtemelen sadece '/'), uygun bir URL o olurdu çünkü bunu @TokenMacGuy – SingleNegationElimination

cevap

4

Belge, yapıştırdığınız metnin hemen altında bu tam örneğe sahiptir. Eğer yoksa '//' eklemek istediğinizi alacaktır. Protokol ve '//' olup olmayacağını bilmiyorsanız, eklemeniz gerekip gerekmediğini belirlemek için bir normal ifadeyi (hatta sadece '//' içeriyorsa bile) kullanabilirsiniz.

Diğer seçenek ('/') bölümünü kullanacak ve URL hiçbir protokol vardır veya '//' zaman SADECE çalışacak Döndürdüğü listenin ilk elemanını almak olacaktır.

DÜZENLEME (gelecek okuyucular için ekleme): protokolünü tespit etmek için regex sen netloc almak için protokol belirtmeniz gerekir gibi re.match('(?:http|ftp|https)://', url)

+0

olur Hala farklı protokoller sorunu (Bryan Yanıta yorumunu bakınız) var. (?: | Ftp | http vb): denetlemek - Teşekkür – santiagobasulto

+0

Sonra bir normal ifadeler kullanabilirsiniz // - ya da sadece varlığını kontrol edin: dizede '//'. Ne kadar sağlam olmasını istediğinize bağlı; Tam URL ayrıştırma karmaşıktır. – SteveMc

+0

+1 Haklısınız SteveMc. Daha hızlı ne olurdu? Yayınladığınız protokol listesini kullanarak veya önerdiğim urlparse ile ayrıştırdınız mı? (Ben bakmadım gerçi) – santiagobasulto

2

URL'nin başlangıcında "http: //" varlığını kontrol etmeyi düşündüğünüz var mı? Bir başka çözüm, ilk kısmın netloc olduğu ve göreceli bir url'nin parçası olmadığı varsayımıyla, her şeyi ilk "/" e götürmek ve bunu netloc olarak kullanmaktır.

+0

Evet, bu ben şu anda yapıyorum. Ama fazla sevmez. Daha iyi bir şey olmazsa onunla devam edeceğim. Teşekkürler! – santiagobasulto

+0

Hala bir sorunum var. Ya diğer protokol/şema kullanılırsa? Bu URL'de http: // olup olmadığını kontrol edersem: "ftp: // my.home.com" o zaman bunun mevcut olmadığını düşünürdüm. Bunu eklerseniz, ben karışıklık o kadar – santiagobasulto

9

gibi bir şey görünüyor olacaktır. Dokümanlar

import urlparse 

url = 'www.amazon.com/Programming-Python-Mark-Lutz' 
if '//' not in url: 
    url = '%s%s' % ('http://', url) 
p = urlparse.urlparse(url) 
print p.netloc 
4

: bu gibi görünebilir mevcut değilse eklemeden

RFC 1808'de sentaks özellikleri ardından, urlparse düzgün tanıtıldı yalnızca bir netloc tanır tarafından '//'. Aksi halde girişin göreceli bir URL olduğu ve dolayısıyla bir yol bileşeni ile başlayacağı varsayılır.

Yani tıpkı yapabilirsiniz:

In [1]: from urlparse import urlparse 

In [2]: def get_netloc(u): 
    ...:  if not u.startswith('http'): 
    ...:   u = '//' + u 
    ...:  return urlparse(u).netloc 
    ...: 

In [3]: get_netloc('www.amazon.com/Programming-Python-Mark-Lutz/dp/0596158106/ref=sr_1_1?ie=UTF8&qid=1308060974&sr=8-1') 
Out[3]: 'www.amazon.com' 

In [4]: get_netloc('http://www.amazon.com/Programming-Python-Mark-Lutz/dp/0596158106/ref=sr_1_1?ie=UTF8&qid=1308060974&sr=8-1') 
Out[4]: 'www.amazon.com' 

In [5]: get_netloc('https://www.amazon.com/Programming-Python-Mark-Lutz/dp/0596158106/ref=sr_1_1?ie=UTF8&qid=1308060974&sr=8-1') 
Out[5]: 'www.amazon.com' 
0

Bu bir liner yapardı.

netloc = urlparse('//' + ''.join(urlparse(url)[1:])).netloc 
4

protokol ise zaman http yalnızca bir satırını kullanabilirsiniz:

return url if "://" in url else "http://" + url 
+0

Yani "http: //" + url 'url else": // "if url demek? –

+1

Hata raporu için Robert Dodd'a teşekkürler. –

İlgili konular