«Write-Error» (запись в Powershell, используется в C #) работает, НО Write-Debug не работает. Почему? - PullRequest
4 голосов
/ 22 октября 2010

Я написал программу на C #, которая создает файл журнала и заполняет его с помощью log4net.Эта программа запускает powershell-скрипты.Скрипты тоже используют log4net. Это работает:

> C#:   
> ps.Runspace.SessionStateProxy.SetVariable("myMethod",(Action<Level,string>)myMethod);
> ps.AddCommand(System.IO.Path.Combine(pathScripts, testSkripte[i].ToString()));  
> ps.Invoke();

> Powershell:                     
> $ScriptLog.Invoke([log4net.Core.Level]::Debug, "TestFile_Debug")                     
> $ScriptLog.Invoke([log4net.Core.Level]::Warn, "TestFile_Warn") $ScriptLog         
> $ScriptLog.Invoke([log4net.Core.Level]::Error, "TestFile_Error")

Теперь я хочу добавить, чтобы использовать стандартные записи-ошибки, записи-отладки и т. Д. CMDlets в моем скрипте.
( выглядит такздесь - ответ Хинека).

Powershell:
   Write-Warning "Write-Warning"      
  AND         
   Write-Error "Write-Error"

работает, но не работает следующее:

Write-Debug "Write-Debug"         (I don´t get an item in my logfile)   OR    
Write-Debug "Write-Debug" -debug  (for this I get an item in my logfile, but ...)

... Я тоже получаю ошибку в своем лог-файле,Ошибка выглядит следующим образом:

[2010-10-22 13:10:58,097] DEBUG : Write-Debug                                     
[2010-10-22 13:10:58,113] ERROR : Cannot invoke this function because the current
                                  host does not implement it

(я думаю, что все пространства имен.)

Что означает сообщение об ошибке и что я могу сделать еще раз?

спасибо

Ответы [ 3 ]

4 голосов
/ 22 октября 2010

Сообщение «текущий хост не реализует его» говорит о том, что вы должны предоставить хост, который реализует пропущенные функции.Предположительно, вы должны реализовать свои собственные PSHost и PSHostUserInterface, по крайней мере, то, что вам действительно нужно там.В последнем классе вы реализуете методы типа WriteDebugLine и WriteErrorLine.Затем командлеты Write-Warning и Write-Debug запускают эти методы внутренне.

Полный пример хоста с пользовательским интерфейсом и этих методов: http://msdn.microsoft.com/en-us/library/ee706577(v=VS.85).aspx (Возможно, вам не нужно большинство других методовпредоставьте несколько манекенов)

3 голосов
/ 25 октября 2010

Вот обходное решение: переопределите команду по умолчанию Write-Debug (которая на самом деле не реализована) с помощью функции:

function global:Write-Debug
(
    [string]
    $Message,
    [switch]
    $Debug
)
{
    # check both the $Debug switch and the $DebugPreference variable:
    if ($Debug -or ($DebugPreference -ne 'SilentlyContinue')) {
        # do job; in this demo just write to the console:
        [Console]::WriteLine("DEBUG: $Message")
    }
}

В C # поместите этот код в строку и вызовите его один раз вто же пространство выполнения, где будет вызываться основной скрипт.Этот «профильный» код устанавливает глобальную функцию Write-Debug, которая семантически совпадает с исходным командлетом.Затем, когда основной код вызывает Write-Debug, эта функция вызывается, а не командлет по умолчанию.

PS Я не пробовал таким образом, я предпочитаю использовать свой собственный хост (см. Мой другой ответ).Но этот способ должен работать во многих случаях (возможно, не во всех).

1 голос
/ 26 октября 2010

Теперь я нашел ответ сам:

C#-Code:
    using (ps = PowerShell.Create())
    {
         int a = testSkripte.Count;
         for (int i = 0; i < a; i++)
         {                        
            ps.Runspace.SessionStateProxy.SetVariable("portalpfad", pathExecuteScript);
            ps.Runspace.SessionStateProxy.SetVariable("ScriptLog", (Action<Level, string>)ScriptLog);


   //add following row:
   ps.Runspace.SessionStateProxy.SetVariable("DebugPreference", "Continue");



        ps.AddCommand(System.IO.Path.Combine(pathScripts, testSkripte[i].ToString()));
        ps.Streams.Debug.DataAdded += new EventHandler<DataAddedEventArgs>(Debug_DataAdded);
        ps.Streams.Warning.DataAdded += new EventHandler<DataAddedEventArgs>(Warning_DataAdded);
        ps.Streams.Error.DataAdded += new EventHandler<DataAddedEventArgs>(Error_DataAdded);   
        ps.Invoke();                        
     }

и это для записи-отладки:

Powershell-Code:

    usings ... 

    #set variable
    $DebugPreference

    #Now Write (-Debug) without Error
                    Write-Debug "Write-Debug"
                    Write-Warning "Write-Warning"
                    Write-Error "Ende --> Write-Error"
...