2012-01-31 3 views
3

컴퓨터에서 특정 파일을 찾아서 삭제하려고합니다. 코드는 부분적으로 만 작동하고VBS 스크립트 파일 찾기 및 삭제

Const DeleteReadOnly = True 

Set oFSO = CreateObject("Scripting.FileSystemObject") 
Set oWshShell = CreateObject("WScript.Shell") 
sDir = oWshShell.ExpandEnvironmentStrings("%temp%\dir.txt") 
sFileName = "\date.vbs" 

If oFSO.FileExists(sDir) Then oFSO.DeleteFile(sDir) 

For Each oDrive In oFSO.Drives 
if oDrive.DriveType = 2 Then Search oDrive.DriveLetter 
Next 

Set oFile = oFSO.OpenTextFile(sDir, 1) 
aNames = Split(oFile.ReadAll, VbCrLf) 
oFile.Close 
For Each sName In aNames 
If InStr(1, sName, sFileName, 1) > 0 Then WScript.Echo sName 
Next 

dim filesys 
Set filesys = CreateObject("Scripting.FileSystemObject") 
filesys.CreateTextFile "\date.vbs", True 
If filesys.FileExists("\date.vbs") Then 
filesys.DeleteFile "\date.vbs" 
Wscript.Echo("File deleted") 
End If 


Sub Search(sDrive) 
WScript.Echo "Scanning drive " & sDrive & ":" 
oWshShell.Run "cmd /c dir /s /b " & sDrive & ":\" & sName & " >>" & sDir, 0, True 
End Sub 

:

내 코드입니다. "date.vbs"파일이 루트 폴더 (C : \ date.vbs)에 있으면 삭제되지만 폴더 (C : \ backup \ date.vbs)에 있으면 삭제되지 않습니다. 루트가 아니라 컴퓨터의 어느 곳에 있더라도 파일을 삭제할 수 있도록 변경해야하는 코드 변경을 아십니까?

감사합니다. V.

UPDATE : 코드는 거의 지금 노력하고 있습니다

. 파일을 삭제할 최종 문제가 생겼습니다. 속성을 읽기 전용에서 일반으로 변경할 수 있지만 여전히 액세스 거부 오류가 발생합니다.

Const DeleteReadOnly = True 
Dim oFSO, oDrive, sFileName, ws, WshS, fso, usrProfile, oFolder, skypefolder 

Set oFSO = CreateObject("Scripting.FileSystemObject") 
sFileName = "Skype.exe" 

Set WshS = WScript.CreateObject("WScript.Shell") 
usrProfile = WshS.ExpandEnvironmentStrings("%UserProfile%") 
skypefolder = "C:\Program Files (x86)\Skype\" 

For Each oDrive In oFSO.Drives 
    If oDrive.DriveType = 2 Then Recurse oFSO.GetFolder(skypefolder) 
Next 

Sub Recurse(oFolder) 
    Set oFile = CreateObject("Scripting.FileSystemObject") 
    Dim oSubFolder, oFile 

    If IsAccessible(oFolder) Then 
    For Each oSubFolder In oFolder.SubFolders 
    Recurse oSubFolder 
    Next 
    WScript.Echo oFolder.Path 

    For Each oFile In oFolder.Files 
     If oFile.Name = sFileName And oFile.Attributes And 1 Then 
     oFile.Attributes = 0 
     oFile.Delete True 

     End If 
     Next 
    End If 
End Sub 

Function IsAccessible(oFolder) 
    On Error Resume Next 
    IsAccessible = oFolder.SubFolders.Count >= 0 
End Function 

도움을 주셔서 감사합니다 :

이 내 코드입니다!

코드 스크립트를 ADMIN (으)로 실행하는 데 사용합니다. 그 후 MessageBox를 보여주기 시작했습니다. 콘솔에서 실행되기 전에.

If WScript.Arguments.Named.Exists("elevated") = False Then 

    CreateObject("Shell.Application").ShellExecute "wscript.exe", """" &  WScript.ScriptFullName & """ /elevated", "", "runas", 1 
    WScript.Quit 
Else 

    Set oShell = CreateObject("WScript.Shell") 
    oShell.CurrentDirectory =  CreateObject("Scripting.FileSystemObject").GetParentFolderName(WScript.ScriptFullName) 
    'WScript.Echo("Now running with elevated permissions") 

End If 

그래서이 코드에는 문제가 있다고 생각됩니다.

+1

일반적인주의 사항 : 코드를 올바르게 들여 씁니다. – Tomalak

답변

4

당신의 접근 방식은 너무 복잡합니다. 간단한 재귀 함수를 사용하여

Option Explicit 

Const DeleteReadOnly = True 
Dim oFSO, oDrive, sFileName 

Set oFSO = CreateObject("Scripting.FileSystemObject") 
sFileName = "date.vbs" 

For Each oDrive In oFSO.Drives 
    If oDrive.DriveType = 2 Then Recurse oDrive.RootFolder 
Next 

Sub Recurse(oFolder) 
    Dim oSubFolder, oFile 

    If IsAccessible(oFolder) Then 
    For Each oSubFolder In oFolder.SubFolders 
    Recurse oSubFolder 
    Next 

    For Each oFile In oFolder.Files 
     If oFile.Name = sFileName Then 
     'oFile.Delete ' or whatever 
     End If 
    Next 
    End If 
End Sub 

Function IsAccessible(oFolder) 
    On Error Resume Next 
    IsAccessible = oFolder.SubFolders.Count >= 0 
End Function 

는 대소 문자를 구분 파일 이름 비교를 달성하기 위해, 당신은 연습으로

If StrComp(oFile.Name, sFileName, vbTextCompare) = 0 Then 
+0

감사합니다, 나는 일종의 진행 상황을 알고 있기 때문에 일종의 스캐닝 부분을 좋아했습니다. 그런 다음 어떻게 삭제를 구현할 수 있습니까? 어떤 구문을 사용해도 작동하지 않습니다. oFile.Delete (sFileName) 시도 파일 이름으로 파일 이름을 사용하고 여전히 오류를 반환합니다. – Vojtech

+0

@Vojtech'oFile.Delete' 잘 작동합니다. 무슨 일이 일어나고 있는지 알고 싶다면'IsAccessible()'체크 바로 앞에'WScript.Echo oFolder.Path'를 추가하십시오. 'cscript.exe yourscript.vbs'를 사용하여 명령 행에서 스크립트를 실행해야합니다. 그렇지 않으면 (즉, doubleclick을 통해 시작하는 경우) 각 폴더에 대해 하나의 MessageBox가 생성됩니다. – Tomalak

3

을 사용할 수 또한 특정 파일을 찾기 위해 WMI 서비스를 사용할 수 있습니다.

Function find_file(filename) 

    Dim objWMIService, colItems, objItem, strComputer 
    strComputer = "." 

    Set objWMIService = GetObject("winmgmts:{impersonationLevel=impersonate}!\\" & strComputer & "\root\cimv2") 
    Set colItems = objWMIService.ExecQuery("SELECT * FROM CIM_DataFile WHERE FileName='" & filename & "'",,48) 

    For Each objItem in colItems 
     msgbox "Found " & objItem.Name & " in " objItem.Path 
    Next 

End Function 

참고 : 당신은 그냥 폴더에 모든 드라이브의 파일을 조회, 모든 폴더를 통해 갈 필요가 없습니다 함수의 결과를 반환하기 전에 그것은 오래 걸릴 수 있습니다.

+0

+1, 아주 좋습니다. 성능 향상을위한 두 가지 해결책을 모색 할 때주의해야합니까? :) – Tomalak

+0

WMI 솔루션은 0.4 초가 걸리고 재귀 검색은 12 초가 걸렸습니다. 성능은 C : 드라이브에서만 측정되었습니다. – AutomatedChaos

+0

흥미 롭습니다. 나는 WMI가 더 빠를 것이라고 생각했지만, 그 차이는 놀랍다. Windows 파일 시스템 캐싱의 효과를 보완하기 위해 여러 번 실행 했습니까? – Tomalak