"Keine solche Datei oder Verzeichnis" beim Versuch, eine Datei zu entfernen, aber die Datei existiert?

21

Ich versuche, ein PNG-Bild zu entfernen, das über ein PHP-Skript auf meinen Server hochgeladen wurde. Immer wenn ich versuche, es sowohl über FTP als auch über das Terminal zu löschen, erhalte ich die Fehlermeldung

No such file or directory

Wenn ich mich jedoch lsim Verzeichnis befinde, wird die Datei aufgelistet und sie wird auch in meinem FTP-Client aufgelistet. Ich habe versucht, eine Datei mit demselben Namen zu erstellen, und am Ende erhalte ich zwei Dateien mit demselben Namen.

Ich kann die Datei öffnen, die angeblich nicht existiert, aber ich kann sie immer noch nicht entfernen. Ich habe auch versucht, meinen Server neu zu starten. Irgendwelche Ideen, was könnte das Problem sein? Ich verwende eine 64-Bit-Version von Ubuntu, glaube aber nicht, dass es sich um ein 32/64-Bit-Problem handelt. Ich sollte auch beachten, dass ich viele andere PNG-Dateien entfernt habe, die mit demselben PHP-Skript hochgeladen wurden.

Ausgabe für ls -l

total 224 
-rw-r--r-- 1 www-data www-data 222838 May 13 04:14 qyxdshyikfr_fishing_timeout.png 
-rw-r--r-- 1 root root 272 May 14 06:54 upload.php

Ausgabe beim Versuch rm

rm: cannot remove ‘qyxdshyikfr_fishing_timeout.png’: No such file or directory

upload.php: http://pastebin.com/z87eypTY

DevinFranzösisch
quelle
Kopieren Einfügen der Ausgabe von ls -laus dem Verzeichnis, auch der vollständige rmBefehl und seine Ausgabe ..
heemayl
@heemayl gesamt 224 -rw-r - r-- 1 www-daten www-daten 222838 13. Mai 04:14 qyxdshyikfr_fishing_timeout.png -rw-r - r-- 1 root root 272 14. Mai 06:54 upload.php rm: kann 'qyxdshyikfr_fishing_timeout.png' nicht entfernen: Keine solche Datei oder Verzeichnis
DevinFrench
1
@ DevinFranzösisch bearbeiten Sie bitte Ihre Frage, um Informationen hinzuzufügen.
muru
Aus welchem ​​Verzeichnis führen Sie den rmBefehl aus?
heemayl
1
@Samuel Warum deutet dies auf ein Dateisystemproblem hin? Der unlinkAufruf schlägt immer fehl, eine Datei zu finden, die nicht vorhanden ist. Wenn ich diesen straceBefehl auf meinem System ausführe und weiß, dass ich keine solche Datei habe, wird eine ähnliche Ausgabe erzeugt. Ich glaube nicht, dass ich ein Dateisystemproblem habe! Es ist weitaus wahrscheinlicher, dass sich der Name der Datei geringfügig von dem Namen der Datei unterscheidet qyxdshyikfr_fishing_timeout.pngund aufgrund von Einschränkungen bei der lsAnzeige von Dateinamen nur derselbe ist , wie in anderen Antworten vorgeschlagen.
Eliah Kagan,

Antworten:

21

Ich habe versucht, eine Datei mit demselben Namen zu erstellen, und am Ende erhalte ich zwei Dateien mit demselben Namen.

Das heißt, ohne Beschädigung des Dateisystems, dass Sie zwei Dateien haben mit zwei unterschiedlichen Namen haben , die aufgrund nicht druckbarer Zeichen oder Zeichen, die in Ihrem Zeichensatz / Ihrer Schriftart gleich aussehen, gleich aussehen. Die --escapeOption zu lsist in solchen Fällen Ihr Freund, ebenso wie Tools wie cat -v.

So ist es auch rm -i -- *

Weitere Lektüre

JdeBP
quelle
Ich war der Ersteller der Datei und der Dateiname, der hochgeladen wurde. Niemand hat versucht, meinen Server zu sabotieren, da ich die einzige Person bin, die den vollständigen Pfad zu upload.php kennt rm -i -- *.
DevinFrench
3
@DevinFrench Wenn diese Antwort Ihr Problem gelöst hat, markieren Sie sie bitte als akzeptierte Antwort, indem Sie auf die Markierung unter der Anzahl der Upvotes klicken, damit zukünftige Benutzer möglicherweise wissen, dass diese Lösung für Sie funktioniert hat.
Kos
1
Kann mir jemand den rm -i -- *Befehl erklären ?
User3731622
Soweit ich weiß: Beim Übergeben -i werden Sie vor dem Entfernen der einzelnen Dateien aufgefordert, diese zu übergeben. --before *wählt alle Dateien aus, unabhängig davon, ob ihre Namen Sonderzeichen enthalten. Referenz: https://explainshell.com/explain?cmd=rm+-i+--+*
MoltenMuffins
16

TL; DR: Führen ls -1bSie den Befehl aus, suchen Sie den Dateinamen, kopieren Sie die Zeile, in der er angezeigt wird, und geben Sie diesen an rm.

Wie andere vorgeschlagen haben, liegt dies höchstwahrscheinlich an Einschränkungen in der Art lsund Weise, und einige andere Programme, einschließlich Client- und Serversoftware, behandeln standardmäßig seltsame Dateinamen, wie z. B. solche, die Steuerzeichen enthalten. Ihr Erfolg mit der Antwort von JdeBP deutet stark darauf hin, dass dies der Fall war, obwohl es schon vorher eine gute Wette gewesen wäre.

  • Für ls, wenn die Standardausgabe ein Terminal ist,? Zeichen werden an ihrer Stelle aufgedruckt. Wenn Sie also lsdie Ausgabe nicht an einen anderen Befehl weiterleiten (oder zur Anzeige in ein Protokoll umleiten), enthält Ihr Dateiname wahrscheinlich keine Steuerzeichen. Es gibt aber auch andere problematische Zeichen - vielleicht enthält der Dateiname beispielsweise ein nachgestelltes Leerzeichen.

    Dieses Verhalten von ls kann verwirrend sein, stellt jedoch keinen Fehler dar und kann vom Benutzer explizit überschrieben werden (siehe unten).

  • Fehler in der Client- oder Serversoftware können zu solchen Problemen führen, wenn versucht wird, remote auf eine Datei zuzugreifen oder diese zu entfernen .

    Ich habe so etwas ftpmehrmals selbst erlebt , auch bei Dateien, deren Namen nachgestellte Leerzeichen enthalten. (Dass es nicht funktioniert hat, liegt an einem Fehler in meinem FTP-Client.) Auch wenn Sie eine Datei manuell erstellen, ist es manchmal recht einfach, versehentlich ein Leerzeichen oder ein anderes Leerzeichen einzufügen kann wie Leerzeichen aussehen, obwohl es nicht ist.

Dies ist eine Situation, in der ls -1b(oder dir -1) nützlich ist:

  • -1Zeigt lseinen Eintrag pro Zeile an. Auf diese Weise gibt es keine Verwirrung darüber, wo ein Dateiname endet und ein anderer beginnt. Dies ist praktisch für seltsam benannte Dateien.
  • -bWeist lsan, Escape-Sequenzen für Sonderzeichen zu drucken. Die Ausgabe von ls -bkann ohne zusätzliche Anführungszeichen wörtlich in einen Befehl kopiert und eingefügt werden : Alle problematischen Zeichen werden bereits so in Anführungszeichen gesetzt, dass die Shell sie als das erkennt, was sie sind.

Es gibt nur eine Einschränkung: Wenn das letzte Zeichen in einer Zeile zu sein scheint \, kopieren Sie danach ein Zeichen, da dies bedeutet\ ein Leerzeichen in Anführungszeichen gesetzt wird.

Sie können ls -1beinfach so laufen oder ein Shell-Glob-Muster übergeben (zB ls -1b qyx*). Beim Verschieben wird die Datei möglicherweise gefunden oder nicht, je nachdem, ob die Steuerzeichen (oder andere seltsame Zeichen) in dem Teil des Namens vorhanden sind, der im Verschiebungsmuster angezeigt wird.

Nachdem Sie die von \angegebene Version des Dateinamens kopiert haben ls, können Sie diese in einen Befehl einfügen. Sie müssen es in keiner Weise manuell ändern. Wenn Sie die Datei löschen möchten, geben Sie rmein Leerzeichen ein, fügen Sie die Zeile ein und drücken Sie Enter.

Weitere Lektüre:

Eliah Kagan
quelle
1
Sehr cool -bthx =) und +1
AB
Ich habe OP ausgelassen, als ich eine Datei mit demselben Namen in meinem FTP-Client erstellt habe, als ich versuchte, die erste Datei zu löschen, mit der ich Probleme hatte. Stattdessen wurde die neue Datei gelöscht, die ich erstellt habe. Aus diesem Grund habe ich nicht gedacht, dass es sich um Sonderzeichen handelt, und ich weiß immer noch nicht, was das Sonderzeichen ist, seit ich es verwendet habe rm -i -- *.
DevinFrench
@DevinFrench Das zusätzliche Zeichen ist ein Leerzeichen am Ende des Dateinamens. Es ist immer noch in der lsAusgabe in der Frage, kann aber nur im Textmodus angezeigt werden, wenn Sie auf "Bearbeiten" klicken.
Izkata
@ Izkata Guter Anruf! Ich hätte darüber nachdenken sollen, das zu überprüfen. Es wird auch angezeigt, wenn ich Revision 3 im Bearbeitungsverlauf erweitere (der vollständige Dateiname einschließlich des nachgestellten Leerzeichens wird grün hervorgehoben und ist somit erkennbar). Was Sie gesagt haben, ist die definitivste und genaueste Erklärung, die Sie bisher erhalten haben - wenn Sie eine Antwort gepostet haben, in der erklärt wird, dass sie aus einem nachgestellten Bereich stammt, und wie Sie wissen und welcher Befehl die Datei entfernen würde (wenn das OP sie noch hätte). Ich weiß, ich würde es stimmen.
Eliah Kagan,
@EliahKagan Fertig, mit Bildern
Izkata
3
  1. Verwenden find und überprüfen Sie die Ausgabe:

    Wird die Datei nicht gefunden, verkürzen Sie den Suchbegriff *qyxdshyikfr*leicht, zB: *qyxds*oder *fishing*.

    sudo find . -maxdepth 1 -type f -name "*qyxdshyikfr*"
    
  2. Wenn ok, dann findmit dem Suchbegriff in Schritt 1 und verwendenrm

    find . -maxdepth 1 -type f -name "*qyxdshyikfr*" -print0 | xargs -0  rm
    
AB
quelle
1
Anstatt Aufruf rmvon namentlich über ein Rohr findzu xargs, empfehle ich einfach mit find‚s -deleteAktion. Wird auch sudonicht benötigt. Weniger bedeutend, ich schlage vor, wegzulassen, es sei -type fdenn, dies ist eindeutig hilfreich. Wenn sich beispielsweise herausstellt, dass der zu löschende Eintrag eine symbolische Verknüpfung ist, möchten sie ihn weiterhin suchen und löschen. Die -deleteAktion löscht ein Verzeichnis nicht rekursiv. und dein rmBefehl auch nicht, da du keinen hast -r. Sie werden hier also nicht versehentlich einen ganzen (nicht leeren) Ordner zerstören, indem Sie ihn nicht verwenden -type.
Eliah Kagan,
OK, gib mir eine Sekunde.
AB
In meinem Fall find ... -deletesagt sogar "kann nicht löschen ... Keine solche Datei oder Verzeichnis"
Stop Harming Monica
1

Umschreiben im Detail, erweitert von meinem Kommentar zu Elias Antwort

Das Problem ist unsichtbar, kann jedoch angezeigt werden, wenn Sie wissen, wonach Sie suchen müssen: Der Dateiname enthält am Ende ein Leerzeichen. Da Sie die gesamte lsAusgabe kopiert / eingefügt haben , wird in der Frage angezeigt, ob Sie die Ausgabe markieren oder den Beitrag bearbeiten und den Cursor an das Ende bewegen oder (wie Eliah betont hat) den Unterschied im Bearbeitungsverlauf betrachten. Ich habe die lsAusgabe im Beitrag in diesem Screenshot hervorgehoben:

Zusätzlicher Platz

Eine kurze kleine Terminalsitzung, um das Problem zu duplizieren, mit Kommentaren:

$ touch 'foo '        # Create file with a space at the end
$ ls -l               # Space is not visible in ls output
total 0
-rw-rw-r-- 1 izkata izkata 0 May 14 21:59 foo 

$ rm foo              # Cannot remove it when not specifying the space
rm: cannot remove ‘foo’: No such file or directory

$ rm 'foo '           # Can remove it if we quote the file name and include the space
$ rm foo\             # Or can escape the space to tell bash to include it as part of the filename

Die Verwendung der Tabulatorvervollständigung hätte das Problem hier auch vollständig umgangen, da bash klug genug ist, um Leerzeichen korrekt zu umgehen (es ist auch eine gute Angewohnheit, die Eingabe von Pfaden so stark zu beschleunigen) .

Wenn ich zum Beispiel getippt hätte rm f<tab>, hätte es sich automatisch vervollständigt rm foo\<space><space>, wie im letzten Beispiel im obigen Codeblock.

Izkata
quelle
Ich erwähne besonders das Kopieren / Einfügen der lsAusgabe, da auf StackOverflow einmal etwas Ähnliches passiert ist (und das ist der ganze Grund, warum ich darüber nachgedacht habe): Jemand hat ein nicht druckbares Zeichen in seinem Code und der einzige Grund, warum es jemand herausgefunden hat Das liegt daran, dass dieser Benutzer beim Posten der Frage auch den Code kopiert / eingefügt hat, anstatt ihn erneut
einzugeben
0

Ich habe einmal eine Datei erstellt, um Nautilus als root zu öffnen, aber der Dateiname bei der Anzeige von Nautilus war "Dateibrowser (root)", und dann, als ich versuchte, als zu entfernen

$ rm "File Browser (Root)"
$ sudo rm "File Browser (Root)"
$ sudo rm "File Browser (Root).desktop"

Die einzige Antwort, die ich bekam, war: "rm: kann 'File Browser (Root) .desktop' nicht entfernen: Keine solche Datei oder Verzeichnis"

wenn ich dann renne:

$ ls -l

Ich sah / erinnerte mich, dass der Dateiname tatsächlich "Nautilus-root.desktop" war

Also renne ich:

$ sudo rm "Nautilus-root.desktop"

arbeitete für mich, hoffe es hilft!

Wagner Arcieri
quelle
0

Also hatte ich dieses Problem und keines dieser Dinge funktionierte für mich. Was funktionierte, war das Erstellen einer Datei mit genau demselben Namen. Es war ein Ordner mit dem Namen Example.1.2.3, also habe ich einen neuen Ordner erstellt und ihn genauso benannt wie den, den ich nicht löschen wollte. Der alte Ordner verschwand und ich löschte den neuen.

Jamison Lifsey
quelle
0

Ich hatte eine ähnliche Situation nach der Verwendung rsync ich mein Bilder- Verzeichnis auf einem Mac gesichert und unter Ubuntu gelesen hatte. Es gab zwei Dateien (tatsächlich Verzeichnisse) mit unterschiedlichen Namen, aber mit demselben Inhalt. Ich habe eines in den Papierkorb (mit Nautilus) gelöscht, das andere konnte ich jedoch nicht löschen, auch nicht über die Befehlszeile. Es würde sagen:

$ rmdir Pictures
rmdir: failed to remove 'Pictures': No such file or directory
$ rm Pictures
rm: cannot remove 'Pictures': Is a directory

Nach Überprüfung der Inode-Nummern mit ls -i -l stellte sich heraus, dass beide Verzeichnisse die gleiche Inode-Nummer haben. Sieht aus wie eine harte Verbindung ...

Die Lösung war überraschend einfach: Leeren Sie den Papierkorb, indem Sie mit der rechten Maustaste auf das Symbol klicken. Danach waren beide Verzeichnisse weg.

elomage
quelle