System.IO.IOException:使用System.IO.Path.GetTempFileName()时parsing“该文件存在”?

我的一个客户每次尝试使用我的产品时都会遇到exception情况。 我得到了发生的exception的调用堆栈,其中最重要的是:

at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath) at System.IO.__Error.WinIOError() at System.IO.Path.GetTempFileName() at System.Windows.Input.Cursor.LoadFromStream(Stream cursorStream) at System.Windows.Input.Cursor..ctor(Stream cursorStream) 

使用谷歌search这个,我发现很多博客post指出,当%TEMP%文件夹中有超过65535个临时文件时,会抛出这个exception,并且解决scheme是简单地清除旧的临时文件。 我可以要求客户这样做,但这可能只是一个临时解决scheme – 如果他们经常运行其他一些频繁调用GetTempFileName的软件,会不会反复出现问题呢?

我不能以编程方式清除%TEMP%文件夹,因为这可能会损坏别的东西,我不能避免调用GetTempFileName(而是使用我自己的临时文件夹),因为它不是我,而是调用它的WPF代码。

有没有永久的解决scheme呢?

更新 :我已经确认%TEMP%文件夹溢出日志文件的问题不是由我自己的代码引起的,必须由客户机器上的其他第三方应用程序引起。 我也研究了Cursor.LoadFromStream的实现,它肯定没有错 – 它生成一个临时文件,但是finallyfinally块中删除它。

正如我在上一个评论中提到的,我认为你唯一的安全的方法就是询问用户是否希望你删除文件并重试。 你必须得到用户的意见,这样才是自己的危险。 在我的脑海里,有一些类似的东西。

 public Stream GetStream(Stream cursorStream) { try { //getting stream } catch(IOE) { MessageBox.Show(this, "Unable to get stream, your temporary folder may be full, do you want to try deleting some and try again?"); if(yes) try { //delete and try again return GetStream(cursorStream); } catch(IOE) { //no luck } else return null; } } 

一个可选的检查,以确保可以,

 Directory.EnumerateFiles(Path.GetTempPath(), "*", SearchOption.TopLevelOnly) .Count() == ushort.MaxValue; 

下面是我最后使用的代码,并在可能发生对Cursor.LoadFromStream任何调用之前尽早放入应用程序的初始化代码path中:

  private void WarnUserIfTempFolderFull() { string tempFile = null; try { tempFile = Path.GetTempFileName(); } catch (IOException e) { string problem = "The Temporary Folder is full."; string message = "{ProductName} has detected that the Windows Temporary Folder is full. \n" + "This may prevent the {ProductName} from functioning correctly.\n" + "Please delete old files in your temporary folder (%TEMP%) and try again."; Logger.Warn(problem); MessageBox.Show(message, caption: problem); } finally { if (tempFile != null) File.Delete(tempFile); } } 

正如Sayse所build议的那样,当您的应用程序启动时,您可以尝试设置%TEMP%环境variables。

 Environment.SetEnvironmentVariable("TEMP", "<dir>"); 

解决scheme:

  1. 正确的那一个。 检测一个应用程序,它会产生如此多的临时文件,而不会删除它们。 像Process monitor这样的工具可以帮助你。 然后修复一个应用程序,把它扔掉。 是的,这可能是你的应用程序,这就是为什么我build议你检测邪恶的来源。
  2. 最简单的一个。 使用你自己的临时目录。 如果从您的代码创build文件,这将无济于事。
  3. 最丑的一个。 从您的应用程序清除临时目录。 你的后果绝对正确 – 你可能会破坏另一个应用程序。

对于遇到此问题的任何人,无法find任何溢出的临时文件夹 – 检查“C:/ Windows / Temp”文件夹。 清理此文件夹解决了我的问题。