2010-10-05 2 views
15

ero con successo in grado di rimuovere attributo di sola lettura su un file utilizzando il seguente frammento di codice:Rimozione sola lettura attributo su una directory utilizzando C#

In main.cs

FileSystemInfo[] sqlParentFileSystemInfo = dirInfo.GetFileSystemInfos(); 

foreach (var childFolderOrFile in sqlParentFileSystemInfo) 
{ 
    RemoveReadOnlyFlag(childFolderOrFile); 
} 

private static void RemoveReadOnlyFlag(FileSystemInfo fileSystemInfo) 
{ 
    fileSystemInfo.Attributes = FileAttributes.Normal; 
    var di = fileSystemInfo as DirectoryInfo; 

    if (di != null) 
    { 
     foreach (var dirInfo in di.GetFileSystemInfos()) 
      RemoveReadOnlyFlag(dirInfo); 
    } 
} 

Purtroppo, questo doesn' t lavorare sulle cartelle. Dopo aver eseguito il codice, quando vado nella cartella, fare clic destro e fare proprietà, ecco cosa vedo:

alt text

Il flag di sola lettura è ancora verificata, anche se rimosso dai file sotto di esso. Ciò causa il fallimento di un processo durante l'eliminazione di questa cartella. Quando rimuovo manualmente il flag e rieseguo il processo (un file bat), è in grado di eliminare il file (quindi so che questo non è un problema con il file bat)

Come rimuovo questo flag in C#?

risposta

8

Si potrebbe anche fare qualcosa di simile a sola lettura a chiare in modo ricorsivo (e archiviazione, ecc) per tutte le directory ei file all'interno di una directory padre specificato:

private void ClearReadOnly(DirectoryInfo parentDirectory) 
{ 
    if(parentDirectory != null) 
    { 
     parentDirectory.Attributes = FileAttributes.Normal; 
     foreach (FileInfo fi in parentDirectory.GetFiles()) 
     { 
      fi.Attributes = FileAttributes.Normal; 
     } 
     foreach (DirectoryInfo di in parentDirectory.GetDirectories()) 
     { 
      ClearReadOnly(di); 
     } 
    } 
} 

Si può quindi chiamare questo modo:

public void Main() 
{ 
    DirectoryInfo parentDirectoryInfo = new DirectoryInfo(@"c:\test"); 
    ClearReadOnly(parentDirectoryInfo); 
} 
6

Prova DirectoryInfo invece di FileInfo

DirectoryInfo di = new DirectoryInfo(@"c:\temp\content"); 
di.Attributes = FileAttributes.Normal; 

Per pulire attrbutes sul file-

foreach (string fileName in System.IO.Directory.GetFiles(@"c:\temp\content")) 
{ 
    System.IO.FileInfo fileInfo = new System.IO.FileInfo(fileName); 
    fileInfo.Attributes = FileAttributes.Normal; 
} 
+0

Questo non sembra funzionare nella directory. Vedo ancora gli attributi con set di sola lettura. – DotnetDude

1

Impostare la proprietà Attributes sull'originale dirInfo:

dirInfo.Attributes = FileAttributes.Normal; 

FileSystemInfo[] sqlParentFileSystemInfo = dirInfo.GetFileSystemInfos(); 

foreach (var childFolderOrFile in sqlParentFileSystemInfo) 
{ 
    RemoveReadOnlyFlag(childFolderOrFile); 
} 
+0

Non funziona. Vedi ancora gli attributi con il flag di sola lettura nello stato 'inteterminato' – DotnetDude

3

La finestra funziona in un modo abbastanza bizzarro. Si mostra sempre nel modo in cui lo vedi nella tua schermata, a prescindere dallo stato dell'attributo ReadOnly. La casella di controllo è nello stato "indeterminato". Devi cliccarlo e cancellarlo o controllarlo per farlo eseguire la sua azione. E nonostante il testo del prompt (ma non il suggerimento accanto alla casella di controllo), modifica solo l'attributo ReadOnly sui file nella directory, non sulla directory stessa.

Utilizzare il comando di riga di comando attrib per vedere cosa sta realmente accadendo. Con ogni probabilità, il tuo codice fallisce perché la directory contiene file con il set di attributi ReadOnly. Dovrai iterarli.

0

Vedo che @DotnetDude ha detto nei commenti che le soluzioni dei ragazzi non funzionano. A mio avviso, succede perché i ragazzi non hanno menzionato che è necessario utilizzare il metodo File.SetAttributes per applicare nuovi attributi.

-1
Shell("net share sharefolder=c:\sharefolder/GRANT:Everyone,FULL") 


Shell("net share sharefolder= c:\sharefolder/G:Everyone:F /SPEC B") 


Shell("Icacls C:\sharefolder/grant Everyone:F /inheritance:e /T") 


Shell("attrib -r +s C:\\sharefolder\*.* /s /d", AppWinStyle.Hide) 

questo codice sta lavorando per me .. per condividere una cartella per ogni uno con lettura e scrittura

+0

qualsiasi codice sorgente completo sulla classe Shell? – Kiquenet

+0

@Kiquenet, 'Shell' non è una classe; è una funzione VB.NET. In C#, è possibile utilizzare Process.Start() per un comportamento simile (ovvero, avviare un altro processo). Cercare la documentazione per le classi 'Process' e' ProcessStartInfo' per ulteriori informazioni. Allo scopo di disattivare solo la proprietà di sola lettura, come era la domanda originale, tuttavia, mi consiglia di utilizzare la risposta di Mark Avenius, piuttosto che avviare una nuova procedura. – reirab

1

Solo nel caso in cui uno qualsiasi accade tutto questo più tardi ...

TUTTO il altre risposte postate prima del mio sono o sbagliate o usano una ricorsione non necessaria.

Prima di tutto la casella di controllo "Sola lettura" nella finestra di dialogo delle proprietà di Windows ha sempre il contrassegno a tre stati per le cartelle. Questo perché la cartella stessa non è di sola lettura ma i file all'interno possono essere.

Se si desidera impostare/rimuovere il flag di sola lettura per TUTTI i file. si può fare semplicemente come segue:

void SetReadOnlyFlagForAllFiles(DirectoryInfo directory, bool isReadOnly) 
{ 
    // Iterate over ALL files using "*" wildcard and choosing to search all directories. 
    foreach(FileInfo File in directory.GetFiles("*", SearchOption.All.Directories)) 
    { 
     // Set flag. 
     File.IsReadOnly = isReadOnly; 
    } 
} 
+0

E cosa fai quando la directory è di sola lettura, quindi non puoi aggiungere/eliminare file dalla directory? Questo è ciò che l'OP ha chiesto. – Dunk

+0

@Dunk Non è stato chiesto cosa. E hai ancora la strana idea che una "Directory" abbia un attributo di sola lettura ... non è così. Hai provato qualcuno del codice? Il codice OP in realtà funziona, ma solo perché è possibile eseguire il cast di DirectoryInfo su FileInfo. Quello che fa veramente è solo impostare l'attributo su tutti i file, testarlo da soli. Una directory non può essere impostata su FileAttibutes.Normal o .ReadOnly è sempre .Directory. Come ho detto, l'esploratore SEMPRE visualizza lo stato intermedio per le directory. Inoltre, un file BAT può eliminare la directory "Sola lettura" in qualsiasi modo, quindi è più probabile che si blocca qualcos'altro sul suo PC. –

1

IEnumerable soluzione/Lambda per ricorsivamente la rimozione di sola lettura attributo di directory e file:

new DirectoryInfo(@"some\test\path").GetDirectories("*", SearchOption.AllDirectories).ToList().ForEach(
    di => { 
     di.Attributes &= ~FileAttributes.ReadOnly; 
     di.GetFiles("*", SearchOption.TopDirectoryOnly).ToList().ForEach(fi => fi.IsReadOnly = false); 
    } 
); 
2

La bandiera di sola lettura sulla directory di Windows è in realtà un termine improprio. La cartella non utilizza il flag di sola lettura. Il problema sarà con la personalizzazione. Il flag viene utilizzato da Windows per identificare che esistono delle personalizzazioni sulla cartella.

Questo è un vecchio post, con un problema che sta tramontando, ma, figurato, le persone potrebbero ancora imbattersi in esso, in quanto è piuttosto fastidioso quando lo colpisci.

Microsoft's Explanation

+0

sei morto corretto. – STLDeveloper

0

Questo può o non può essere correlato direttamente, ma il problema principale nel tuo caso potrebbe essere causato dai file sottostanti. Ad esempio, mi sono imbattuto in questo problema cercando di cancellare una directory:

System.IO.Directory.Delete(someDirectory, true) 

Questo si traduce in "L'accesso al 'blah' percorso negato". Per risolvere questo problema sottostante, ho rimosso l'attributo di sola lettura nei file secondari e ho quindi potuto rimuovere la directory principale. Nel mio caso, stavo usando PowerShell, quindi è possibile utilizzare l'equivalente .NET.

dir -r $PrePackageDirectory |% {if ($_.PSIsContainer -ne $true){$_.IsReadOnly = $false}}