2009-04-14 12 views
32

ho ricevuto questo messaggio di errore:Come affrontare l'URISyntaxException

java.net.URISyntaxException: Illegal character in query at index 31: http://finance.yahoo.com/q/h?s=^IXIC 

My_Url = http://finance.yahoo.com/q/h?s=^IXIC

Quando ho copiato in un campo indirizzo del browser, ha mostrato la pagina corretta, è una valida URL, ma io non si può analizzare con questo: new URI(My_Url)

ho provato: My_Url=My_Url.replace("^","\\^"), ma

  1. Non sarà l'url ho bisogno
  2. Non funziona neanche

Come gestire questa situazione?

Frank

risposta

14

Usa % codifica per il ^ carattere, vale a dire. http://finance.yahoo.com/q/h?s=%5EIXIC

51

È necessario codificare l'URI per sostituire i caratteri non validi con i caratteri codificati legali. Se prima crei un URL (quindi non devi eseguire l'analisi da solo) e quindi fai un URI utilizzando lo five-argument constructor, il costruttore eseguirà la codifica per te.

import java.net.*; 

public class Test { 
    public static void main(String[] args) { 
    String myURL = "http://finance.yahoo.com/q/h?s=^IXIC"; 
    try { 
     URL url = new URL(myURL); 
     String nullFragment = null; 
     URI uri = new URI(url.getProtocol(), url.getHost(), url.getPath(), url.getQuery(), nullFragment); 
     System.out.println("URI " + uri.toString() + " is OK"); 
    } catch (MalformedURLException e) { 
     System.out.println("URL " + myURL + " is a malformed URL"); 
    } catch (URISyntaxException e) { 
     System.out.println("URI " + myURL + " is a malformed URL"); 
    } 
    } 
} 
+0

Assicurati di utilizzare URLDecoder se in seguito vuoi trasformare quell'URI in un URL, ad es. 'new FileInputStream (URLDecoder.decode (uri.toURL(). getFile()," UTF-8 "))' – MrDrews

+0

Provato molte altre soluzioni suggerite, questo sembra fare il trucco. Puoi usare "uri" direttamente nella tua "nuova HttpGet (uri)". –

+0

HELP ME ALOT @@@@@@@@@@@ >>>>>>>>>>>>>>> –

14

È necessario codificare i parametri.

Qualcosa di simile lo farà:

import java.net.*; 
import java.io.*; 

public class EncodeParameter { 

    public static void main(String [] args) throws URISyntaxException , 
             UnsupportedEncodingException { 

     String myQuery = "^IXIC"; 

     URI uri = new URI(String.format( 
          "http://finance.yahoo.com/q/h?s=%s", 
          URLEncoder.encode(myQuery , "UTF8"))); 

     System.out.println(uri); 

    } 
} 

http://java.sun.com/javase/6/docs/api/java/net/URLEncoder.html

1

coudn't immaginare nulla di meglio per
http://server.ru:8080/template/get?type=mail&format=html&key=ecm_task_assignment&label = Согласовать с контрагентом & descr = Описание & objectid = 2231
che:

public static boolean checkForExternal(String str) { 
    int length = str.length(); 
    for (int i = 0; i < length; i++) { 
     if (str.charAt(i) > 0x7F) { 
      return true; 
     } 
    } 
    return false; 
} 

private static final Pattern COLON = Pattern.compile("%3A", Pattern.LITERAL); 
private static final Pattern SLASH = Pattern.compile("%2F", Pattern.LITERAL); 
private static final Pattern QUEST_MARK = Pattern.compile("%3F", Pattern.LITERAL); 
private static final Pattern EQUAL = Pattern.compile("%3D", Pattern.LITERAL); 
private static final Pattern AMP = Pattern.compile("%26", Pattern.LITERAL); 

public static String encodeUrl(String url) { 
    if (checkForExternal(url)) { 
     try { 
      String value = URLEncoder.encode(url, "UTF-8"); 
      value = COLON.matcher(value).replaceAll(":"); 
      value = SLASH.matcher(value).replaceAll("/"); 
      value = QUEST_MARK.matcher(value).replaceAll("?"); 
      value = EQUAL.matcher(value).replaceAll("="); 
      return AMP.matcher(value).replaceAll("&"); 
     } catch (UnsupportedEncodingException e) { 
      throw LOGGER.getIllegalStateException(e); 
     } 
    } else { 
     return url; 
    } 
} 
1

Una soluzione generale richiede l'analisi dell'URL in un URI conforme a RFC 2396 (si noti che questa è una versione precedente dello standard URI, utilizzato da java.net.URI).

Ho scritto una libreria di analisi URL Java che lo rende possibile: galimatias. Con questa libreria, è possibile raggiungere il tuo comportamento desiderato con questo codice:

String urlString = //... 
URLParsingSettings settings = URLParsingSettings.create() 
    .withStandard(URLParsingSettings.Standard.RFC_2396); 
URL url = URL.parse(settings, urlString); 

noti che galimatias è in una fase molto precoce e alcune funzioni sono sperimentali, ma è già abbastanza solida per questo caso d'uso.

0

Ho avuto questa eccezione nel caso di un test per verificare alcuni URL effettivamente accessibili dagli utenti.

E gli URL qualche volta contengono un carattere illegale e sono bloccati da questo errore.

Così faccio una funzione per codificare solo i caratteri nella stringa dell'URL come questo.

String encodeIllegalChar(String uriStr,String enc) 
    throws URISyntaxException,UnsupportedEncodingException { 
    String _uriStr = uriStr; 
    int retryCount = 17; 
    while(true){ 
    try{ 
     new URI(_uriStr); 
     break; 
    }catch(URISyntaxException e){ 
     String reason = e.getReason(); 
     if(reason == null || 
     !(
      reason.contains("in path") || 
      reason.contains("in query") || 
      reason.contains("in fragment") 
     ) 
     ){ 
     throw e; 
     } 
     if(0 > retryCount--){ 
     throw e; 
     } 
     String input = e.getInput(); 
     int idx = e.getIndex(); 
     String illChar = String.valueOf(input.charAt(idx)); 
     _uriStr = input.replace(illChar,URLEncoder.encode(illChar,enc)); 
    } 
    } 
    return _uriStr; 
} 

prova:

String q = "\\'|&`^\"<>)(}{]["; 
String url = "http://test.com/?q=" + q + "#" + q; 
String eic = encodeIllegalChar(url,'UTF-8'); 
System.out.println(String.format(" original:%s",url)); 
System.out.println(String.format(" encoded:%s",eic)); 
System.out.println(String.format(" uri-obj:%s",new URI(eic))); 
System.out.println(String.format("re-decoded:%s",URLDecoder.decode(eic))); 
4

Piuttosto che codifica l'URL prima di mano è possibile effettuare le seguenti operazioni

String link = "http://foo.com"; 
URL url = null; 
URI uri = null; 

try { 
    url = new URL(link); 
} catch(MalformedURLException e) { 
    e.printStackTrace(); 
} 

try{ 
    uri = new URI(url.toString) 
} catch(URISyntaxException e { 
    try { 
     uri = new URI(url.getProtocol(), url.getUserInfo(), url.getHost(), 
         url.getPort(), url.getPath(), url.getQuery(), 
         url.getRef()); 
    } catch(URISyntaxException e1 { 
     e1.printStackTrace(); 
    } 
} 
try { 
    url = uri.toURL() 
} catch(MalfomedURLException e) { 
    e.printStackTrace(); 
} 

String encodedLink = url.toString(); 
0

Se stai usando RestangularV2 di inviare a un controller di primavera in Java può ottenere questa eccezione se si utilizza RestangularV2.one() anziché RestangularV2.all()

0

Sostituisci gli spazi nell'URL con + come Se url contiene dimensione1 = Incontinenza Liners quindi sostituiscilo con dimensione1 = Incontinenza + Liners.

Problemi correlati