Проблема с приложением .net под Linux, не работает из сценария оболочки

Я работаю над обработкой пост-фиксации .net для передачи данных в OnTime через их Soap SDK. Моя ловушка работает в Windows нормально, но на нашем производственном сервере подрывной деятельности RHEL4 она не будет работать при вызове из сценария оболочки.

#!/bin/sh
/usr/bin/mono /hooks/post-commit.exe "$@"

Когда я выполняю его с параметрами из командной строки, он работает правильно. При выполнении через сценарий оболочки я получаю следующую ошибку: (похоже, есть проблема с выполнением процесса SVN, который я использую для получения данных журнала для ревизии):


Unhandled Exception: System.InvalidOperationException: The process must exit before getting the requested information.
  at System.Diagnostics.Process.get_ExitCode () [0x0003f] in /tmp/monobuild/build/BUILD/mono-1.9.1/mcs/class/System/System.Diagnostics/Process.cs:149
  at (wrapper remoting-invoke-with-check) System.Diagnostics.Process:get_ExitCode ()
  at SVNLib.SVN.Execute (System.String sCMD, System.String sParams, System.String sComment, System.String sUserPwd, SVNLib.SVNCallback callback) [0x00000]
  at SVNLib.SVN.Log (System.String sUrl, Int32 nRevLow, Int32 nRevHigh, SVNLib.SVNCallback callback) [0x00000]
  at SVNLib.SVN.LogAsString (System.String sUrl, Int32 nRevLow, Int32 nRevHigh) [0x00000]
  at SVNCommit2OnTime.Program.Main (System.String[] args) [0x00000]

Я пробовал использовать mkbundle и mkbundle2 для создания автономной системы с именем post-commit, но получаю другое сообщение об ошибке:

Unhandled Exception: System.ArgumentNullException: Argument cannot be null.
Parameter name: Value cannot be null.
  at System.Guid.CheckNull (System.Object o) [0x00000]
  at System.Guid..ctor (System.String g) [0x00000]
  at SVNCommit2OnTime.Program.Main (System.String[] args) [0x00000]

Есть идеи, почему он может не работать из сценария оболочки или что может быть не так с прилагаемой версией?

Редактировать:@Herms, с эхом уже пробовал, выглядит нормально. Что касается /hooks/post-commit.exe, я пробовал сценарий с полным путем к сборке .net и без него с теми же результатами.

Редактировать:@Леон, Я пробовал как , так и "$@" с одинаковыми результатами. Это хук фиксации пост-фиксации Subversion, и он принимает два параметра, поэтому их необходимо передать сборке .net. "$@" был тем, что рекомендовалось на моно-сайте для вызова сборки .net из сценария оболочки. Сценарий оболочки является выполняет сборку .net и с правильными параметрами, но генерирует исключение, которое не генерируется при запуске непосредственно из командной строки.

Редактировать:@Vinko, я не вижу отличий в окружении, кроме BASH_LINENO и BASH_SOURCE

Редактировать:@ Люк, надоело, но это тоже без разницы. Я впервые заметил проблему при тестировании из TortoiseSVN на моем компьютере (когда он работает как подпроцесс демона подрывной деятельности), но также обнаружил, что получаю те же результаты при выполнении сценария из каталога хуков (т.е. ./post-commit REPOS REV, где post-commit - это приведенный выше сценарий sh. Выполнение mono post-commit.exe REPOS REV работает нормально. Основная проблема заключается в том, что для выполнения мне нужно иметь что-то от имени post-commit, чтобы он был вызван. Но он не работает из сценария оболочки, и, как указано выше, mkbundle не работает с другой проблемой.

Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
1
0
1 471
6
Перейти к ответу Данный вопрос помечен как решенный

Ответы 6

Просто случайная мысль, которая может помочь с отладкой. Попробуйте изменить сценарий оболочки на:

#!/bin/sh
echo /usr/bin/mono /hooks/post-commit.exe "$@"

Проверьте, соответствует ли выводимая строка команде, которую вы ожидаете запустить. Возможно, ваша обработка аргументов командной строки в сценарии оболочки не выполняет то, что вы хотите.

Я не знаю, каким должен быть ваш ввод в сценарий, но $ 1 перед путем мне кажется немного неуместным.

Вы уверены, что хотите сделать

/usr/bin/mono /hooks/post-commit.exe "$@"

$ @ расширяется до ВСЕХ аргументов. «$ @» заменяется на все аргументы, соединенные пробелами. Я подозреваю, что ваш сценарий оболочки неверен. Вы не указали, что именно должен делать сценарий, так что это ограничивает наши возможности вносить предложения.

Сравните переменные среды в вашей оболочке и в сценарии.

Попробуйте поставить "cd $ 1 / hooks /" перед строкой, которая запускает моно. В этой папке могут быть сборки, которые обнаруживаются при запуске моно из этой папки в оболочке, но не обнаруживаются при запуске сценария.

Убедившись, что мой код сделал работает из командной строки, я обнаружил, что он больше не работает! Я заглянул в свой код .net, чтобы увидеть, есть ли что-нибудь в этом смысл.

Вот что у меня было:

        static public int Execute(string sCMD, string sParams, string sComment,
                                  string sUserPwd, SVNCallback callback)
        {
            System.Diagnostics.Process proc = new System.Diagnostics.Process();
            proc.EnableRaisingEvents = false;
            proc.StartInfo.RedirectStandardOutput = true;
            proc.StartInfo.CreateNoWindow = true;
            proc.StartInfo.UseShellExecute = false;
            proc.StartInfo.Verb = "open";
            proc.StartInfo.FileName = "svn";
            proc.StartInfo.Arguments = Cmd(sCMD, sParams, sComment, UserPass());
            proc.Start();
            int nLine = 0;
            string sLine = "";
            while ((sLine = proc.StandardOutput.ReadLine()) != null)
            {
                ++nLine;
                if (callback != null)
                {
                    callback.Invoke(nLine, sLine);
                }
            }
            int errorCode = proc.ExitCode;
            proc.Close();
            return errorCode;
        }

Я изменил это:

            while (!proc.HasExited)
            {
                sLine = proc.StandardOutput.ReadLine();
                if (sLine != null)
                {
                    ++nLine;
                    if (callback != null)
                    {
                        callback.Invoke(nLine, sLine);
                    }
                }
            }
            int errorCode = proc.ExitCode;

Похоже, что процесс задерживается немного дольше, чем я получаю вывод, и поэтому proc.ExitCode выдает ошибку.

Ответ принят как подходящий

Некоторые процессы могут оставаться в стороне некоторое время после закрытия своего стандартного вывода (т. Е. Вы получаете от них сообщение о конце файла). Вам необходимо вызвать proc.WaitForExit() после прочтения всех данных, но до проверки ExitCode.

Другие вопросы по теме