Pergunta

Eu tenho uma matriz de bytes SHA-1 que eu gostaria de usar em uma solicitação GET. Eu preciso para codificar isso. URLEncoder espera uma corda, e se eu criar uma cadeia do mesmo e, em seguida, codificá-lo, ele fica corrompido?

Para esclarecer, isso é meio um acompanhamento para uma outra pergunta da mina. (Request Bitorrent Tracker) posso obter o valor como uma string hex, mas que não é reconhecido pela rastreador. Por outro lado, marca de resposta codificado fornecido retorno 200 OK.

Então eu preciso para converter a representação hexadecimal que eu tenho:

9a81333c1b16e4a83c10f3052c1590aadf5e2e20

em forma codificada

%9A%813%3C%1B%16%E4%A8%3C%10%F3%05%2C%15%90%AA%DF%5E.%20
Foi útil?

Solução

Pergunta foi editado enquanto eu estava respondendo, a seguir é o código adicional e deve funcionar (com o meu código de conversão hex):

//Inefficient, but functional, does not test if input is in hex charset, so somewhat unsafe
//NOT tested, but should be functional
public static String encodeURL(String hexString) throws Exception {
  if(hexString==null || hexString.isEmpty()){
     return "";
  }
  if(hexString.length()%2 != 0){
    throw new Exception("String is not hex, length NOT divisible by 2: "+hexString);
  }
  int len = hexString.length();
  char[] output = new char[len+len/2];
  int i=0;
  int j=0;
  while(i<len){
      output[j++]='%';
      output[j++]=hexString.charAt(i++);
      output[j++]=hexString.charAt(i++);
  }
  return new String(output);
}

Você vai precisar para converter os bytes brutos para caracteres hexadecimais ou qualquer codificação-friendly URL que eles estão usando. Base32 ou Base64 codificações são possíveis, mas caracteres hexadecimais retas é o mais comum. URLEncoder não é necessário para essa sequência porque ele não deve conter quaisquer caracteres que exigiriam URL Encoding para o formato NN%.

A seguir irá converter bytes para um hash (SHA-1, MD5SUM, etc.) para uma cadeia hexadecimal:

/** Lookup table: character for a half-byte */
    static final char[] CHAR_FOR_BYTE = {'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
         /** Encode byte data as a hex string... hex chars are UPPERCASE*/
         public static String encode(byte[] data){
             if(data == null || data.length==0){
                 return "";
             }
             char[] store = new char[data.length*2];
             for(int i=0; i<data.length; i++){
                 final int val = (data[i]&0xFF);
                 final int charLoc=i<<1;
                 store[charLoc]=CHAR_FOR_BYTE[val>>>4];
                 store[charLoc+1]=CHAR_FOR_BYTE[val&0x0F];
             }
             return new String(store);
         }

Este código é bastante otimizado e rápido, e eu estou usando-o para o meu próprio SHA-1 byte codificação. Note que você pode precisar converter maiúsculas para minúsculas com o String.toLowerCase () método, dependendo de qual forma o servidor aceita.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top