Como encontro links simbólicos quebrados automaticamente no Windows?

11

Não tenho certeza se esse é um estilo ruim, mas estou fazendo essa pergunta aqui porque não consegui encontrar a resposta em outro lugar e, então, resolvi uma solução sozinha. Eu estaria interessado em ver as soluções de outras pessoas, mas depois de alguns dias postarei as minhas.

No meu caso específico, estou executando o Windows 7, mas eu estaria interessado em respostas para outras / versões mais antigas do Windows. Percebo que uma resposta é "instale uma versão do Unix find e depois resolva como para o Unix ", mas eu queria uma solução mais "nativa".

EDIT 2012-07-17: Esclarecimento: por "automaticamente", idealmente, quero dizer algo que eu possa executar como parte de um script, em vez de uma ferramenta GUI que faz todo o trabalho com o pressionar de um botão, porque eu quero fazer isso desacompanhado.

HughG
fonte

Respostas:

4

um pouco tardio, mas aqui está a minha própria resposta à minha pergunta. É basicamente a mesma abordagem que a usual no Unix: encontre todos os links e atue nos que estão quebrados; não é tão conciso. O script abaixo exclui links simbólicos quebrados, depois de despejar algumas informações sobre eles.

@echo off

rem Grab the list of directories to scan, before we "pushd to dir containing this script",
rem so that we can have the default be "dir from which we ran this script".
setlocal
if x%CD%==x (echo Command Extensions must be enabled. && goto :eof)
set ORIGINAL_DIR=%CD%

pushd %~dp0

set DIRS_TO_CHECK=%*
if x%DIRS_TO_CHECK%==x (
    set DIRS_TO_CHECK=.
)

rem Find all the files which are both links (/al) and directories (/ad).
rem (We use "delims=" in case any paths have a space; space is a delim by default.)
rem If not, delete it (and assume something else will fix it later :-).
echo Deleting broken symlinks ...
echo.
for %%D in (%ORIGINAL_DIR%\%DIRS_TO_CHECK%) do (
    echo Checking %%D
    echo.
    pushd %%D
    if errorlevel 1 (
        echo Cannot find "%%D"
        echo.
        goto :Next_Dir
    )
    rem Clean up broken directory links.
    for /f "usebackq delims=" %%L in (`dir /adl /b`) do (
        rem Check the directory link works.
        rem Redirecting to nul just to hide "The system cannot find the file specified." message.
        pushd "%%L" >nul 2>&1
        if errorlevel 1 (
            echo Deleting broken directory symlink "%%L".
            rem First dump out some info on the link, before we delete it.
            rem I'd rather a more human-readable form, but don't know how to get that.
            fsutil reparsepoint query "%%L"
            rmdir "%%L"
            echo.
        ) else (
            popd
        )
    )
    rem Clean up broken file (non-directory) links.
    for /f "usebackq delims=" %%L in (`dir /a-dl /b`) do (
        rem Check the file link works.
        rem Redirecting to nul just to hide "The system cannot find the file specified." message.
        copy "%%L" nul >nul 2>&1
        if errorlevel 1 (
            echo Deleting broken file symlink "%%L".
            rem First dump out some info on the link, before we delete it.
            rem I'd rather a more human-readable form, but don't know how to get that.
            fsutil reparsepoint query "%%L"
            rm "%%L"
            echo.
        ) else (
            popd
        )
    )
    popd
    :Next_Dir
    rem Putting a label on the line immediately before a ')' causes a batch file parse error, hence this comment.
)
echo Deleting broken symlinks ... done.

:Finally
popd
HughG
fonte
3

As seguintes ferramentas podem ajudá-lo a encontrar e remover o link simbólico no Windows

  1. Junction Link Magic
  2. Diskjunction
Abhijeet Kasurde
fonte
Essas são as duas ferramentas úteis da GUI, mas não fiquei claro: quero algo que possa ser executado em um script. Eu editei a pergunta para esclarecer.
HughG
2

Você também pode tentar um utilitário de código aberto chamado SageLinks , que mostra e verifica junções do Windows NTFS, links simbólicos e até atalhos.

Nikolay Raspopov
fonte
0

Usando cygwin64 (find, xargs, sh, ls) (testado no win7 para links inativos ntfs mortos)

c:\>   find ./ -type l |  xargs -I % sh -c "ls % > /dev/null 2>&1 || echo %" 

Nota: test -e não funciona como esperado com o hardlink ntfs morto.

mosh
fonte
1
Obrigado @mosh, mas, como eu disse, quero algo que não envolva "instalar uma versão dos utilitários Unix" - porque quero um script que outros possam executar sem preparação.
HughG