【问题标题】:How to detect C# project type and / or how to detect Console availability如何检测 C# 项目类型和/或如何检测控制台可用性
【发布时间】:2010-03-11 12:26:39
【问题描述】:

我有两个用 C# 编写的 Windows 服务。一项服务是“控制台应用程序”,第二项服务是“Windows 应用程序”(无法更改)。 两种服务应用程序都可以在几种模式下执行(取决于命令行参数和Environment.UserInteractive 标志):

  • 当 (Environment.UserInteractive == false) 和...
    • 当没有提供命令行参数时 - 执行标准的生成代码(SCM 需要) - ServiceBase.Run(ServicesToRun)
  • 当 (Environment.UserInteractive == true) 和...
    • 当提供“-i”命令行参数时 - 服务应用程序自行安装(类似于 installutil -i [scv_app]
    • 当提供“-u”命令行参数时 - 服务应用程序自行卸载(类似于 installutil -u [scv_app]
    • 当提供“-c”命令行参数时 - 服务以“控制台”模式执行(用于调试目的)

两个服务都使用类库中的静态方法来选择和处理描述的执行路径。 但是,我在这个类库中有一个问题——当应用程序的类型为“Windows 应用程序”时,Console.WriteLine() 没有可见的效果。在这种情况下,我可以使用 Win32 AttachConsole() 或类似的东西,但我更喜欢通过 MessageBox.Show() 显示汇总消息。 因此,我认为在类库中我需要知道应用程序是“控制台应用程序”还是“Windows 应用程序”......你知道该怎么做吗?

一开始,我没有尝试检测应用类型,而是尝试编写类似的内容:

if (string.IsNullOrEmpty(Console.Title) == false) Console.WriteLine(msg); 

在Win7下可以,但是在Win2k3下不行。 那么也许有更好的方法来检测Console.WriteLine(msg) / Console.ReadLine 是否按预期工作? 我看到了一些其他的建议 (sublinked here),但对我来说都不是很好。我正在寻找“不错”的解决方案(!= p/invoke;!= 访问 try/catch 块内的任何控制台对象属性(例如标题))。

【问题讨论】:

  • 您可以使用格式按钮格式化代码吗? (代码按钮看起来像 1 和 0)。
  • 库真的不应该与用户界面交互,你能用日志库代替吗?

标签: c# windows-services console-application windows


【解决方案1】:
  1. Windows 服务不应该有 ui。这包括控制台和消息框。

不碍事...

您是否考虑过将适当的跟踪侦听器连接到System.Diagnostics.Trace.TraceListeners?根据您的命令行,您可以添加 MessageBox 跟踪侦听器或将跟踪消息转储到控制台的跟踪侦听器吗?您将利用经过广泛测试的内置调试机制,并且以它们自己的方式具有极强的可扩展性。您还将隐式区分在发布模式下显示的消息与在调试模式下显示的消息(通过System.Diagnostics.Trace.Write()System.Diagnostics.Debug.Write())。

【讨论】:

    【解决方案2】:

    在处理类库时,我根据调用类库的环境传入一个 UI 对象。

    public interface IAlerts { 
        void Show(string message);
    }
    
    public class EventLogAlerts : IAlerts { ... }
    
    public class WindowsAlerts : IAlerts { ... }
    
    public class ConsoleAlerts : IAlerts { ... }
    
    public class MyLibrary {
        private IAlerts alertImpl = new EventLogAlerts();
        public void SetUserInterface(IMyUserInterface impl) 
        {
            this.alertImpl = impl;
        }
    
        public void DoSomething()
        {
            try 
            {
                ...
            }
            catch (Exception)
            {
                this.alertImpl.Show("Whoops!");
            }  
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2012-03-07
      • 2011-10-05
      • 2011-12-19
      • 2012-08-20
      • 2021-04-10
      • 1970-01-01
      • 2020-07-13
      • 1970-01-01
      相关资源
      最近更新 更多