Problema com o método canRead da classe File!

3 respostas
bcartaxo

Ao que me parece esse método está bugado.

Criei um objeto File passando uma String como caminho do arquivo no construtor dessa classe.
No windows retirei a permissão para leiura do arquivo.
chamei o método canRead() para verificar se o mesmo tem permissão de leitura, e esse método retornou true, quando deveria retornar false.

Debugei direitinho e realmente tudo em leva a crer q seja um bug nesse método.

Gostaria de ouvir a opinião de vcs.

[]´s

3 Respostas

T

Se você olhar o fonte de canRead no JDK ele usa a API do C “_access” com o parâmetro 4.

Cheque no arquivo Win32FileSystem_md.c (no diretório j2se\src\windows\native\java\io ), método Java_java_io_Win32FileSystem_checkAccess.

Olhando no fonte de _access (arquivo access.c do Microsoft Visual Studio, normalmente no diretório Microsoft Visual Studio\vc\crt\src), vemos que se o parâmetro for 4 ele chama a API do Windows GetFileAttributes, e checa apenas se conseguiu obter os atributos. Se não conseguiu obter (porque o arquivo não existe, ou porque seu diretório está inacessível para o usuário corrente), então canRead retorna false.

Em resumo: canRead retorna false apenas e tão somente se o usuário corrente não pode listar o diretório onde está o arquivo (por exemplo). OK?

bcartaxo

Se bem entendi oq vc disse, acho q talvez então o q o método canRead faz seria algo muito mais próximo do exists() e fica meio em discordância com o canWrite. Oq vc acha?

Descobri também que ja foi reportado esse problema para a Sun. Segue o link:

http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6203387

T

Se você leu direitinho o bug report, vai ver que canWrite também tem o mesmo problema porque chama absolutamente a mesma API (_access) do Microsoft Visual C++, só que com o parâmetro 2.
Essa API só checa se o atributo read-only está setado ou não.
O correto, segundo a própria avaliação, seria eles usarem a API do Windows AccessCheck, que é extremamente custosa para ser chamada, ou então usar o método da força bruta (se conseguir abrir o arquivo para leitura, então canRead tem de retornar true).
O problema é que essa API (canRead) você normalmente usa para ver se é possível abrir o arquivo, e você não deseja que o arquivo seja já aberto - principalmente se você repetir esse teste muitas vezes seguidas. Então eles se limitaram a deixar bugado mesmo.
Se você quiser checar isso direito, faça pelo método da força bruta - tente abrir o arquivo para leitura; se conseguir, então você pode ler ( :stuck_out_tongue: )

Criado 23 de outubro de 2007
Ultima resposta 24 de out. de 2007
Respostas 3
Participantes 2