Como codificar o parâmetro filename do cabeçalho Content-Disposition no HTTP?

535

Os aplicativos da Web que desejam forçar o download de um recurso, em vez de serem renderizados diretamente em um navegador da Web, emitem um Content-Dispositioncabeçalho na resposta HTTP do formulário:

Content-Disposition: attachment; filename=FILENAME

O filenameparâmetro pode ser usado para sugerir um nome para o arquivo no qual o recurso é baixado pelo navegador. A RFC 2183 (Content-Disposition), no entanto, afirma na seção 2.3 (O parâmetro FileName) que o nome do arquivo pode usar apenas caracteres US-ASCII:

A gramática atual [RFC 2045] restringe os valores dos parâmetros (e, portanto, os nomes dos arquivos Content-Disposition) para US-ASCII. Reconhecemos a grande conveniência de permitir conjuntos de caracteres arbitrários nos nomes de arquivos, mas está além do escopo deste documento definir os mecanismos necessários.

Há evidências empíricas, no entanto, de que os navegadores da Web mais populares hoje em dia parecem permitir caracteres não-USCI ASCII ainda (por falta de um padrão) discordam do esquema de codificação e da especificação do conjunto de caracteres do nome do arquivo. A questão é, então, quais são os vários esquemas e codificações empregados pelos navegadores populares se o nome do arquivo "naïvefile" (sem aspas e onde a terceira letra é U + 00EF) precisou ser codificado no cabeçalho Disposição de Conteúdo?

Para os fins desta pergunta, os navegadores populares são:

  • Raposa de fogo
  • Internet Explorer
  • Safári
  • Google Chrome
  • Ópera
Atif Aziz
fonte
Ele funcionou para o Mobile Safari (utf-8 bruto, como sugerido por @Martin Ørding-Thomsen), mas isso não funciona para o GoodReader no mesmo dispositivo. Alguma ideia?
Thilo
Veja também esta pergunta semelhante #
30516
1
A resposta de Kornel provou ser o caminho de menor resistência, se você pode definir o último segmento do caminho; junte isso com Content-Disposition: attachment.
Antti Haapala

Respostas:

94

Há discussões sobre isso, incluindo links para teste de navegador e compatibilidade com versões anteriores, na RFC 5987 proposta , "Conjunto de caracteres e codificação de idioma para parâmetros de campo de cabeçalho HTTP (Hypertext Transfer Protocol)".

A RFC 2183 indica que esses cabeçalhos devem ser codificados de acordo com a RFC 2184 , que foi obsoleta pela RFC 2231 , coberta pelo rascunho da RFC acima.

Jim
fonte
5
Observe também que o rascunho da Internet (e não o "rascunho da RFC") foi finalizado e o documento final é a RFC 5987 ( greenbytes.de/tech/webdav/rfc5987.html )
Julian Reschke
11
Relacionado a isso, descobri que o Firefox (versões 4-9 inclusive) é interrompido se houver vírgula (,) no nome do arquivo, por exemplo Content-Disposition: filename="foo, bar.pdf". O resultado é que o Firefox baixa o arquivo corretamente, mas mantém a .partextensão (por exemplo foo,bar.pdf-1.part). Então, é claro que o arquivo não abrirá corretamente porque o aplicativo não está associado .part. Outros caracteres ASCII parecem funcionar bem.
catchdave
3
Para obter mais informações sobre o comportamento do IE, consulte blogs.msdn.com/b/ieinternals/archive/2010/06/07/…
EricLaw
5
@ catchdave: Você esqueceu o "anexo"; parte.
Christoffer Hammarström
6
Em suma, isso não passa de uma resposta apenas de link com 74 votos positivos.
Antti Haapala
364

Eu sei que este é um post antigo, mas ainda é muito relevante. Eu descobri que os navegadores modernos oferecem suporte ao rfc5987, que permite a codificação utf-8, porcentagem codificada (codificada por url). Então o arquivo Naïve.txt se torna:

Content-Disposition: attachment; filename*=UTF-8''Na%C3%AFve%20file.txt

O Safari (5) não suporta isso. Em vez disso, você deve usar o padrão Safari para escrever o nome do arquivo diretamente no cabeçalho codificado utf-8:

Content-Disposition: attachment; filename=Naïve file.txt

O IE8 e versões anteriores também não são compatíveis e você precisa usar o padrão IE de codificação utf-8, porcentagem codificada:

Content-Disposition: attachment; filename=Na%C3%AFve%20file.txt

No ASP.Net, uso o seguinte código:

string contentDisposition;
if (Request.Browser.Browser == "IE" && (Request.Browser.Version == "7.0" || Request.Browser.Version == "8.0"))
    contentDisposition = "attachment; filename=" + Uri.EscapeDataString(fileName);
else if (Request.Browser.Browser == "Safari")
    contentDisposition = "attachment; filename=" + fileName;
else
    contentDisposition = "attachment; filename*=UTF-8''" + Uri.EscapeDataString(fileName);
Response.AddHeader("Content-Disposition", contentDisposition);

Testei o acima usando IE7, IE8, IE9, Chrome 13, Opera 11, FF5, Safari 5.

Atualização em novembro de 2013:

Aqui está o código que atualmente uso. Eu ainda tenho que dar suporte ao IE8, então não consigo me livrar da primeira parte. Acontece que os navegadores no Android usam o gerenciador de downloads interno do Android e não podem analisar nomes de arquivos de maneira confiável da maneira padrão.

string contentDisposition;
if (Request.Browser.Browser == "IE" && (Request.Browser.Version == "7.0" || Request.Browser.Version == "8.0"))
    contentDisposition = "attachment; filename=" + Uri.EscapeDataString(fileName);
else if (Request.UserAgent != null && Request.UserAgent.ToLowerInvariant().Contains("android")) // android built-in download manager (all browsers on android)
    contentDisposition = "attachment; filename=\"" + MakeAndroidSafeFileName(fileName) + "\"";
else
    contentDisposition = "attachment; filename=\"" + fileName + "\"; filename*=UTF-8''" + Uri.EscapeDataString(fileName);
Response.AddHeader("Content-Disposition", contentDisposition);

Os itens acima agora foram testados no IE7-11, Chrome 32, Opera 12, FF25, Safari 6, usando este nome de arquivo para download: 你好 abcABCæøåÆØÅäöüïëêîâéíáóúúññ½§! ^ ~ '-_,;. txt

No IE7, ele funciona para alguns caracteres, mas não para todos. Mas quem se importa com o IE7 hoje em dia?

Essa é a função que eu uso para gerar nomes de arquivos seguros para o Android. Observe que não sei quais caracteres são suportados no Android, mas testei que eles funcionam com certeza:

private static readonly Dictionary<char, char> AndroidAllowedChars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ._-+,@£$€!½§~'=()[]{}0123456789".ToDictionary(c => c);
private string MakeAndroidSafeFileName(string fileName)
{
    char[] newFileName = fileName.ToCharArray();
    for (int i = 0; i < newFileName.Length; i++)
    {
        if (!AndroidAllowedChars.ContainsKey(newFileName[i]))
            newFileName[i] = '_';
    }
    return new string(newFileName);
}

@TomZ: Eu testei no IE7 e IE8 e acabei não precisando escapar do apóstrofo ('). Você tem um exemplo em que falha?

@Dave Van den Eynde: Combinar os dois nomes de arquivos em uma linha, de acordo com o RFC6266, exceto o Android e o IE7 + 8, e atualizei o código para refletir isso. Obrigado pela sugestão.

@ Thilo: Não faço ideia do GoodReader ou de qualquer outro navegador que não seja. Você pode ter alguma sorte usando a abordagem do Android.

@Alex Zhukovskiy: Não sei por que, mas, como discutido no Connect , não parece funcionar muito bem.

Martin Ørding-Thomsen
fonte
1
Ele funcionou no Mobile Safari (utf-8 bruto, como sugerido acima), mas isso não funciona para o GoodReader no mesmo dispositivo. Alguma ideia?
Thilo
1
IE7 e 8 apóstrofos também precisam escapou: .Recoloque ( "'", Uri.HexEscape ( '\''))
TomZ
1
Escrever diretamente caracteres UTF-8 parece funcionar para as versões atuais do Firefox, Chrome e Opera. Não testou o Safari e o IE.
Martin Tournoij
20
Por que não combiná-los Content-Disposition: attachment; filename*=UTF-8''Na%C3%AFve%20file.txt; filename=Na%C3%AFve%20file.txte pular o navegador farejando? Isso funcionaria?
Dave Van den Eynde
9
O pessoal do fastmail encontrou outra solução alternativa: blog.fastmail.com/2011/06/24/download-non-english-filenames Disposição de conteúdo: anexo; filename = "foo-% c3% a4.html"; filename * = UTF-8''foo-% c3% a4.html A especificação do fileName duas vezes (uma vez sem o prefixo UTF-8 e outra vez) faz com que funcione no IE8-11, Edge, Chrome, Firefox e Safari ( parece safari maçã fixo, assim que trabalha lá também agora)
wullinkm
169

Existe uma alternativa simples e muito robusta: use uma URL que contenha o nome do arquivo que você deseja .

Quando o nome após a última barra é o desejado, você não precisa de cabeçalhos extras!

Esse truque funciona:

/real_script.php/fake_filename.doc

E se o seu servidor suportar a reescrita de URL (por exemplo, mod_rewriteno Apache), você poderá ocultar completamente a parte do script.

Os caracteres nos URLs devem estar em UTF-8, codificados em url byte a byte:

/mot%C3%B6rhead   # motörhead
Kornel
fonte
3
? Tente GetAttachment.aspx / fake_filename.doc id = 34 (embora possa ser Apache somente peculiaridade)
Kornel
2
esta é uma solução fantástica; realmente me ajudou muito. obrigado.
kristopolous
6
Desci a trilha dos coelhos e tentei algumas das outras soluções; tentar farejar o navegador e a versão corretos para definir os cabeçalhos corretamente é um pesadelo. O Chrome foi identificado incorretamente como Safari, que não se comporta de maneira nenhuma (as quebras de vírgulas se não forem codificadas corretamente). Salve-se do problema, use esta solução e alias o URL, conforme necessário.
MPEN
3
O /:id/:filenamemétodo é realmente simples e funciona, obrigado!
Luca Steeb #
2
Mil vezes "Sim". Você realmente ganhará tempo com isso. Mais ainda - alguns navegadores Android vai flat out ignorar o Content-Dispositione criar nomes muito interessantes em vez (que será gerada a partir de seu caminho). Assim, a única solução para a guarda de uma sanidade é apenas a criação Content-Disposition: attachmente passando o nome do arquivo desejado como o último componente do caminho:
Julik
73

O RFC 6266 descreve o " Uso do campo de cabeçalho de disposição de conteúdo no HTTP (Hypertext Transfer Protocol) ". Citando isso:

6. Considerações sobre internacionalização

O filename*parâmetro “ ” ( Seção 4.3 ), usando a codificação definida em [ RFC5987 ], permite ao servidor transmitir caracteres fora do conjunto de caracteres ISO-8859-1, e também especificar opcionalmente o idioma em uso.

E na seção de exemplos :

Este exemplo é o mesmo que o acima, mas adicionando o parâmetro "filename" para compatibilidade com agentes de usuários que não implementam o RFC 5987 :

Content-Disposition: attachment;
                     filename="EURO rates";
                     filename*=utf-8''%e2%82%ac%20rates

Nota: Os agentes de usuário que não suportam a codificação RFC 5987 ignoram “ filename*” quando ocorre após “ filename”.

No Apêndice D, há também uma longa lista de sugestões para aumentar a interoperabilidade. Ele também aponta para um site que compara implementações . Os testes de aprovação atuais adequados para nomes de arquivos comuns incluem:

  • attwithisofnplain : nome de arquivo ISO-8859-1 comum com aspas duplas e sem codificação. Isso requer um nome de arquivo que seja totalmente ISO-8859-1 e não contenha sinais de porcentagem, pelo menos não na frente de dígitos hexadecimais.
  • attfnboth : dois parâmetros na ordem descrita acima. Deve funcionar para a maioria dos nomes de arquivos na maioria dos navegadores, embora o IE8 use o filenameparâmetro " ".

Esse RFC 5987, por sua vez, faz referência ao RFC 2231 , que descreve o formato real. 2231 é principalmente para correio, e 5987 nos diz quais partes também podem ser usadas para cabeçalhos HTTP. Não confunda isso com os cabeçalhos MIME usados ​​dentro de um corpomultipart/form-data HTTP , que é governado pela RFC 2388 ( seção 4.4 em particular) e pelo rascunho do HTML 5 .

MvG
fonte
1
Eu tive problemas no Safari. Ao baixar arquivos com nomes russos receberam caracteres errados e ilegíveis. A solução ajudou. Mas precisamos enviar um cabeçalho em uma única linha (!!!).
evtuhovdo
16

O documento a seguir, vinculado ao rascunho da RFC mencionado por Jim em sua resposta, aborda mais a questão e definitivamente merece uma nota direta aqui:

Casos de teste para o cabeçalho HTTP-Disposition de conteúdo e codificação RFC 2231/2047

Atif Aziz
fonte
Observe que é possível fornecer os dois modos de codificação do parâmetro filename e que eles parecem funcionar corretamente com navegadores antigos e novos (sendo o MSIE8 e o Safari nesse caso o antigo). Verifique attfnboth no relatório mencionado por @AtifAziz.
Pablo Montilla
11

no asp.net mvc2 eu uso algo como isto:

return File(
    tempFile
    , "application/octet-stream"
    , HttpUtility.UrlPathEncode(fileName)
    );

Eu acho que se você não usar o mvc (2), poderia codificar o nome do arquivo usando

HttpUtility.UrlPathEncode(fileName)
Elmer
fonte
2
A codificação de URL para codificação de nome de arquivo não é válida, os navegadores não devem decodificá-los.
SerialSeb
O IE 11 definitivamente não decodifica a codificação de URL neste campo.
Pseudocoder
Mas precisava ser urlencoded quando o navegador é Chrome ou IE, outros, como FF, Safari e multa trabalho Opera com a codificação
Reza
11

Coloque o nome do arquivo entre aspas duplas. Resolvido o problema para mim. Como isso:

Content-Disposition: attachment; filename="My Report.doc"

http://kb.mozillazine.org/Filenames_with_spaces_are_truncated_upon_download

Eu testei várias opções. Os navegadores não suportam as especificações e agem de maneira diferente, acredito que aspas duplas é a melhor opção.

Dmitry Kaigorodov
fonte
3
Infelizmente, isso não resolve todos os problemas explicados nas respostas acima.
Luca Steeb 06/03
2
Isso permitirá que você para retornar um nome de arquivo com espaços, &, %, #etc. Então ele resolve isso.
Don Cheadle
E se o nome do arquivo contiver aspas duplas (sim, isso pode acontecer), conforme especificado na RFC 6266, o nome do arquivo é uma "string entre aspas" e, conforme especificado nas aspas duplas da RFC 2616 dentro de uma string entre aspas, deve ser escapado com uma barra invertida.
Christophe Roussy
10

Eu uso os seguintes trechos de código para codificação (assumindo que fileName contém o nome do arquivo e a extensão do arquivo, ou seja: test.txt):


PHP:

if ( strpos ( $_SERVER [ 'HTTP_USER_AGENT' ], "MSIE" ) > 0 )
{
     header ( 'Content-Disposition: attachment; filename="' . rawurlencode ( $fileName ) . '"' );
}
else
{
     header( 'Content-Disposition: attachment; filename*=UTF-8\'\'' . rawurlencode ( $fileName ) );
}

Java:

fileName = request.getHeader ( "user-agent" ).contains ( "MSIE" ) ? URLEncoder.encode ( fileName, "utf-8") : MimeUtility.encodeWord ( fileName );
response.setHeader ( "Content-disposition", "attachment; filename=\"" + fileName + "\"");
Vasilen Donchev
fonte
Certo, ele deve estar rawurlencodeno PHP pelo menos para o filename*=cabeçalho de disposição, já que é value-charsusado na ext-valueRFC 6266-> RFC 5987 (consulte tools.ietf.org/html/rfc6266#section-4.1 & tools.ietf.org/html/rfc5987#section -3.2.1 ) não permite espaço sem porcentagem de escape ( filename=por outro lado, parece que poderia permitir um espaço sem escape, embora apenas ASCII deva estar presente aqui). Não é necessário para codificar com o rigor cheio de rawurlencode, então alguns caracteres pode ser unescaped: gist.github.com/brettz9/8752120
Brett Zamir
9

Na API da Web do ASP.NET, eu codifico o nome do arquivo:

public static class HttpRequestMessageExtensions
{
    public static HttpResponseMessage CreateFileResponse(this HttpRequestMessage request, byte[] data, string filename, string mediaType)
    {
        HttpResponseMessage response = new HttpResponseMessage(HttpStatusCode.OK);
        var stream = new MemoryStream(data);
        stream.Position = 0;

        response.Content = new StreamContent(stream);

        response.Content.Headers.ContentType = 
            new MediaTypeHeaderValue(mediaType);

        // URL-Encode filename
        // Fixes behavior in IE, that filenames with non US-ASCII characters
        // stay correct (not "_utf-8_.......=_=").
        var encodedFilename = HttpUtility.UrlEncode(filename, Encoding.UTF8);

        response.Content.Headers.ContentDisposition =
            new ContentDispositionHeaderValue("attachment") { FileName = encodedFilename };
        return response;
    }
}

IE 9 Não corrigido
IE 9 Fixed

martinoss
fonte
5

Testei o seguinte código em todos os principais navegadores, incluindo Exploradores mais antigos (por meio do modo de compatibilidade), e funciona bem em qualquer lugar:

$filename = $_GET['file']; //this string from $_GET is already decoded
if (strstr($_SERVER['HTTP_USER_AGENT'],"MSIE"))
  $filename = rawurlencode($filename);
header('Content-Disposition: attachment; filename="'.$filename.'"');
Stano
fonte
5

Acabei com o seguinte código no meu script "download.php" (baseado neste post do blog e nesses casos de teste ).

$il1_filename = utf8_decode($filename);
$to_underscore = "\"\\#*;:|<>/?";
$safe_filename = strtr($il1_filename, $to_underscore, str_repeat("_", strlen($to_underscore)));

header("Content-Disposition: attachment; filename=\"$safe_filename\""
.( $safe_filename === $filename ? "" : "; filename*=UTF-8''".rawurlencode($filename) ));

Isso usa a maneira padrão do nome do arquivo = "...", desde que haja apenas caracteres iso-latin1 e "safe" usados; caso contrário, ele adiciona o nome do arquivo * = UTF-8 '' de maneira codificada por url. De acordo com este caso de teste específico , ele deve funcionar a partir do MSIE9 e no recente FF, Chrome, Safari; na versão inferior do MSIE, deve oferecer um nome de arquivo que contenha a versão ISO8859-1 do nome do arquivo, com sublinhados nos caracteres que não estão nessa codificação.

Nota final: o max. O tamanho de cada campo de cabeçalho é 8190 bytes no apache. UTF-8 pode ter até quatro bytes por caractere; após rawurlencode, é x3 = 12 bytes por um caractere. Bastante ineficiente, mas ainda deve ser teoricamente possível ter mais de 600 "sorrisos"% F0% 9F% 98% 81 no nome do arquivo.

apurkrt
fonte
... mas o tamanho máximo do nome do arquivo transferível também depende do cliente. Acabei de descobrir que no máximo [89 smiles😁] .pdf o nome do arquivo passa pelo MSIE11. No Firefox37, é no máximo [111x 😁] .pdf. Chrome41 trunca o nome do arquivo no 110º sorriso. Curiosamente, o sufixo é transferido ok.
apurkrt
5

Se você estiver usando um back-end nodejs, poderá usar o seguinte código que encontrei aqui

var fileName = 'my file(2).txt';
var header = "Content-Disposition: attachment; filename*=UTF-8''" 
             + encodeRFC5987ValueChars(fileName);

function encodeRFC5987ValueChars (str) {
    return encodeURIComponent(str).
        // Note that although RFC3986 reserves "!", RFC5987 does not,
        // so we do not need to escape it
        replace(/['()]/g, escape). // i.e., %27 %28 %29
        replace(/\*/g, '%2A').
            // The following are not required for percent-encoding per RFC5987, 
            // so we can allow for a little better readability over the wire: |`^
            replace(/%(?:7C|60|5E)/g, unescape);
}
Emanuele Spatola
fonte
1
Melhor usar encodeURI(str). Como exemplo com datas no nome do arquivo: encodeURIComponent('"Kornél Kovács 1/1/2016')=> "Kornél Kovács 1% 2F1% 2F2016" vs. encodeURI('"Kornél Kovács 1/1/2016')=> "Kornél Kovács 1/1/2016"
gdibble
4

No PHP, isso foi feito por mim (assumindo que o nome do arquivo seja codificado em UTF8):

header('Content-Disposition: attachment;'
    . 'filename="' . addslashes(utf8_decode($filename)) . '";'
    . 'filename*=utf-8\'\'' . rawurlencode($filename));

Testado contra IE8-11, Firefox e Chrome.
Se o navegador puder interpretar o nome do arquivo * = utf-8, ele usará a versão UTF8 do nome do arquivo, caso contrário, o nome do arquivo decodificado. Se o seu nome de arquivo contiver caracteres que não podem ser representados na ISO-8859-1, você pode considerar o uso iconv.

Gustav
fonte
3
Embora esse código possa responder à pergunta, fornecer um contexto adicional sobre por que e / ou como responde à pergunta melhoraria significativamente seu valor a longo prazo. Por favor edite sua resposta para adicionar alguma explicação.
Toby Speight
2
Uau, nenhuma das respostas somente de código acima foi rebaixada ou criticada dessa maneira. Também encontrei o porquê já foi respondido suficientemente bem: o IE não interpreta o nome do arquivo * = utf-8, mas precisa da versão ISO8859-1 do nome do arquivo, que este script oferece. Só queria dar ao preguiçoso um código simples e funcional para PHP.
Gustav
Acho que isso foi prejudicado porque a pergunta não é específica ao idioma, mas sobre o que os RFCs devem aderir ao implementar a codificação de cabeçalho. Obrigado, no entanto, por esta resposta, para PHP, esse código fez minhas mágoas desaparecerem.
J4k3 28/06
Obrigado. Esta resposta pode não ter respondido estritamente à pergunta, mas era exatamente o que eu estava procurando e me ajudou a resolver o problema no Python.
22616 Lyndsy Simon
1
Tenho certeza de que esse código pode ser usado como vetor de ataque se o usuário puder controlar o nome do arquivo.
Antti Haapala
3

Apenas uma atualização desde que eu estava tentando todas essas coisas hoje em resposta a um problema do cliente

  • Com exceção do Safari configurado para japonês, todos os navegadores testados por nossos clientes funcionaram melhor com o nome do arquivo = text.pdf - em que texto é um valor do cliente serializado pelo ASP.Net/IIS no utf-8 sem codificação de URL. Por alguma razão, o Safari configurado para inglês aceitaria e salvaria adequadamente um arquivo com o nome japonês do utf-8, mas o mesmo navegador configurado para o japonês salvaria o arquivo com os caracteres utf-8 não interpretados. Todos os outros navegadores testados pareciam funcionar melhor / bem (independentemente da configuração do idioma) com o nome de arquivo utf-8 codificado sem codificação de URL.
  • Eu não poderia encontrar um único navegador implementação Rfc5987 / 8187 em tudo . Testei com o Chrome mais recente, o Firefox constrói mais o IE 11 e o Edge. Tentei configurar o cabeçalho apenas com o nome do arquivo * = utf-8''texturlencoded.pdf, configurando-o com o nome do arquivo = text.pdf; nome do arquivo * = utf-8''texturlencoded.pdf. Nenhum recurso do Rfc5987 / 8187 parecia estar sendo processado corretamente em qualquer um dos itens acima.
user1664043
fonte
Esta é uma boa atualização. Você pode elaborar os testes específicos que tentou?
22419 Brad
3

PHP framework Symfony 4 tem $filenameFallbackem HeaderUtils::makeDisposition. Você pode procurar nessa função para obter detalhes - ela é semelhante às respostas acima.

Exemplo de uso:

$filenameFallback = preg_replace('#^.*\.#', md5($filename) . '.', $filename);
$disposition = $response->headers->makeDisposition(ResponseHeaderBag::DISPOSITION_ATTACHMENT, $filename, $filenameFallback);
$response->headers->set('Content-Disposition', $disposition);
luchaninov
fonte
1

Solução ASP clássica

A maioria dos navegadores modernos oferece suporte à aprovação de Filenamecomo UTF-8agora, mas como foi o caso de uma solução de Upload de Arquivos que eu uso baseada no FreeASPUpload.Net (o site não existe mais, os links apontam para archive.org ) , não funcionaria como a análise do O binário confiava na leitura de cadeias codificadas em ASCII de byte único, o que funcionava bem quando você passava dados codificados em UTF-8 até chegar aos caracteres que ASCII não suporta.

No entanto, consegui encontrar uma solução para obter o código para ler e analisar o binário como UTF-8.

Public Function BytesToString(bytes)    'UTF-8..
  Dim bslen
  Dim i, k , N 
  Dim b , count 
  Dim str

  bslen = LenB(bytes)
  str=""

  i = 0
  Do While i < bslen
    b = AscB(MidB(bytes,i+1,1))

    If (b And &HFC) = &HFC Then
      count = 6
      N = b And &H1
    ElseIf (b And &HF8) = &HF8 Then
      count = 5
      N = b And &H3
    ElseIf (b And &HF0) = &HF0 Then
      count = 4
      N = b And &H7
    ElseIf (b And &HE0) = &HE0 Then
      count = 3
      N = b And &HF
    ElseIf (b And &HC0) = &HC0 Then
      count = 2
      N = b And &H1F
    Else
      count = 1
      str = str & Chr(b)
    End If

    If i + count - 1 > bslen Then
      str = str&"?"
      Exit Do
    End If

    If count>1 then
      For k = 1 To count - 1
        b = AscB(MidB(bytes,i+k+1,1))
        N = N * &H40 + (b And &H3F)
      Next
      str = str & ChrW(N)
    End If
    i = i + count
  Loop

  BytesToString = str
End Function

O crédito é transferido para o Pure ASP File Upload implementando a BytesToString()função include_aspuploader.aspno meu próprio código UTF-8.


Links Úteis

Lankymart
fonte
-1

Tivemos um problema semelhante em um aplicativo Web e terminamos lendo o nome do arquivo no HTML <input type="file">e definindo-o no formulário codificado por URL em um novo HTML <input type="hidden">. É claro que tivemos que remover o caminho como "C: \ fakepath \" retornado por alguns navegadores.

Obviamente, isso não responde diretamente à pergunta dos OPs, mas pode ser uma solução para outros.

Andrei I
fonte
1
Problema completamente diferente. A pergunta é sobre o download , sua resposta é sobre o upload .
Oskar Berggren
-3

Normalmente codifico por URL (com% xx) os nomes dos arquivos e parece funcionar em todos os navegadores. Você pode querer fazer alguns testes de qualquer maneira.

Dario Solera
fonte
10
Eu testei em alguns e não funciona dessa maneira em todos os navegadores, daí a questão. :)
Atif Aziz