Executing script on a remote server - vb.net

The following code works when the script is executed on the current machine
(Currently, the script is a simple messagebox displaying the argument passed)
Arguments:
UserName = Nothing
Password = Nothing
RemoteMachineName = "CurrentMachineName"
PathBashFile = "Path/To/My/Local/Script.ps1"
Params = "parameter1"
However, when I want to run a local script on a remote computer, the script is never actually executed. The code doesn't throw any exception.
Arguments:
UserName = "MyUsername"
Password = "MyPassword"
RemoteMachineName = "RemoteMachineName"
PathBashFile = "Path/To/My/Local/Script.ps1"
Params = "parameter1"
All I have as a result is :
outParams("processId") = Nothing
outParams("returnValue") = 8
What's going on? Why isn't my script running as expected on the remote machine? (No message box pops up on either machine. I have tried other cmdlets, but none ever work)
Here is the code:
Try
connOptions = New ConnectionOptions()
connOptions.Username = UserName
connOptions.Password = Password
connOptions.Impersonation = ImpersonationLevel.Impersonate
connOptions.Authentication = Management.AuthenticationLevel.PacketPrivacy
managementPath = New ManagementPath("\\" & RemoteMachineName & "\root\cimv2:Win32_Process")
Scope = New ManagementScope(managementPath, connOptions)
Scope.Connect()
objectGetOptions = New ObjectGetOptions()
processClass = New ManagementClass(Scope, New ManagementPath("root\cimv2:Win32_Process"), objectGetOptions)
inParams = processClass.GetMethodParameters("Create")
inParams("CommandLine") = "cmd.exe /c powershell """ & PathBashFile & """ " & params
inParams("CurrentDirectory") = workingDirectoryPath
outParams = processClass.InvokeMethod("Create", inParams, Nothing)
MsgBox(outParams("processId") & " " & outParams("returnValue"))
Catch ex As Exception
Throw New Exception("[ExecuteRemoteBashFile] " & ex.Message)
End Try
If someone could point out any mistakes in my code, it would be greatly appreciated!

I solved my problem by putting the complete path to powershell.exe, instead of assuming that the console knows where to look for that...
inParams("CommandLine") = "cmd.exe /c C:\Windows\System32\WindowsPowerShell\v2.0\powershell.exe """ & PathBashFile & """ " & params

Related

VB.Net shell output sometimes not returning

for 99% of all my Shell commands this code works fine, but for just one command I don't get the returned text, which is normally visible in the Shell window. Here is the code I use to execute commands and read back the results:
Function RunCommandCom(command As String, arguments As String) As String()
Dim p As Process = New Process()
Dim pi As ProcessStartInfo = New ProcessStartInfo()
Dim output As String
pi.Arguments = " " + "/c" + " " + command + " " + arguments
pi.FileName = "cmd.exe"
pi.RedirectStandardOutput = True 'pi.CreateNoWindow = True
pi.WindowStyle = ProcessWindowStyle.Normal
pi.UseShellExecute = False
p.StartInfo = pi
p.Start()
output = p.StandardOutput.ReadToEnd()
p.WaitForExit()
p.Close()
If output Is ""
Then
Return Nothing
Else
Return output.Replace(Chr(13), "").Split(Chr(10))
End If
End Function
The command making Problems is executed fine. It shall create a entry in a database, which defintly is existing after calling my funciton. Executing the command directly in a Shell generates the same entry and I can see the returned text.
Does anyone has an idea why the streamreader does not read/contain anything for exactly this one special command?
Arg. I found the problem. These two commands send their output to the StandardError stream. I don't know why, as no error occured.

Console App - "Procedure or function has too many arguments specified" on 2nd run

I have written a console application to process, read and sort jpeg images from an input folder. The app uses a third party dll to read barcodes on proof of delivery documents, before giving a relevant file name, copying the file and uploading the path of said file to an SQL database. Everything works ok for a single file, but once I have multiple files in the directory and call the insert procedure for the second time, I get the error "Procedure or function has too many arguments specified". I output the parameters to the console and can see no issue, but command fails at the point of execution. Any ideas what's going on here. Thanks. Steve.
For Each File As String In Files
FileName = System.IO.Path.GetFileName(File)
SourceFile = System.IO.Path.Combine(SourcePath, FileName)
Console.WriteLine("Got File " + SourceFile)
Results = Reader.DecodeFile(SourceFile)
If Not Results Is Nothing Then
For Each item As BarcodeResult In Results
StrInfo = item.BarcodeText
Next
DestFileName = StrInfo & Format(Now, "ddMMyyyy-hhmmss") & ".jpg"
DestFile = System.IO.Path.Combine(SuccessPath, DestFileName)
'System.IO.File.Copy(File, DestFile, True)
Console.WriteLine("File " & DestFile & " Created...")
sqlCon.Open()
sqlCmd.CommandType = CommandType.StoredProcedure
sqlCmd.Parameters.Add("#Consignment_id", SqlDbType.Decimal)
sqlCmd.Parameters("#Consignment_id").Direction = ParameterDirection.Input
sqlCmd.Parameters("#Consignment_id").Value = StrInfo
sqlCmd.Parameters.Add("#Path", SqlDbType.VarChar)
sqlCmd.Parameters("#Path").Direction = ParameterDirection.Input
sqlCmd.Parameters("#Path").Value = DestFile
sqlCmd.Parameters.Add("#Doc", SqlDbType.VarChar)
sqlCmd.Parameters("#Doc").Direction = ParameterDirection.Input
sqlCmd.Parameters("#Doc").Value = "POD"
sqlCmd.Parameters.Add("#UploadedBy", SqlDbType.VarChar)
sqlCmd.Parameters("#UploadedBy").Direction = ParameterDirection.Input
sqlCmd.Parameters("#UploadedBy").Value = "SYSTEM"
Console.WriteLine(sqlCmd.Parameters("#Consignment_id").Value.ToString)
Console.WriteLine(sqlCmd.Parameters("#Path").Value.ToString)
Console.WriteLine(sqlCmd.Parameters("#Doc").Value.ToString)
Console.WriteLine(sqlCmd.Parameters("#UploadedBy").Value.ToString)
sqlCmd.ExecuteNonQuery()
sqlCon.Close()
Console.WriteLine(StrInfo & " Uploaded...")
'System.IO.File.Delete(SourceFile)
Threading.Thread.Sleep(1000)
Else
'DestFileName = FileName
'DestFile = System.IO.Path.Combine(FailPath, DestFileName)
'System.IO.File.Copy(File, DestFile, True)
'System.IO.File.Delete(SourceFile)
'Console.WriteLine("Failed, moved to 'Bad' folder...")
End If
Next
Console.WriteLine("Finished, press any key to exit...")
Console.ReadKey()

Displaying the output of Process.Start

I have a Process.Start command that I would like to see the output of, but the new window is opening and closing too quickly for me to see anything. Here is the code I have so far that I'm working with:
System.Diagnostics.Process.Start(Environment.GetEnvironmentVariable("VS110COMNTOOLS") & "..\Ide\MSTEST.EXE", "/Testsettings: """ & rwSettings & "" & " /Testcontainer: """ & rwContainer & "" & " /Resultsfile: """ & rwResults & "")
Unfortunately as I try to debug this if I allow this to run it flashes up the window but doesn't let me see what the error is, or if it's running successfully at all. I'm using VS2012 so I might just not be looking at the right view when I'm debugging.
Here is some code taen out of the middle of some logic, so it is not standalone. You can use ProcessStartInfo() and Process() to have more control:
Dim start_info As New ProcessStartInfo("sqlcmd", cmd)
start_info.UseShellExecute = False
start_info.CreateNoWindow = True
start_info.RedirectStandardOutput = True
start_info.RedirectStandardError = True
' Make the process and set its start information.
Dim proc As New Process()
proc.StartInfo = start_info
Dim dt As Date = Now()
' Start the process.
proc.Start()
' Attach to stdout and stderr.
Dim std_out As StreamReader = proc.StandardOutput() ' will not continue until process stops
Dim std_err As StreamReader = proc.StandardError()
' Retrive the results.
Dim sOut As String = std_out.ReadToEnd()
Dim sErr As String = std_err.ReadToEnd()

cmd process not exiting

I was running the following code to execute commands from vb.net app.
Dim CMDServer As Diagnostics.ProcessStartInfo
Dim CMDReply As Diagnostics.Process
CMDServer = New Diagnostics.ProcessStartInfo
CMDServer.WorkingDirectory = "C:/"
CMDServer.FileName = "cmd.exe"
CMDServer.UseShellExecute = False
CMDServer.RedirectStandardOutput = True
CMDServer.RedirectStandardError = True
CMDServer.CreateNoWindow = True
CMDServer.Arguments = "/C " + command
CMDReply = Process.Start(CMDServer)
MsgBox("START")
Dim Reply As String = ""
If Not CMDReply.HasExited Then
CMDReply.WaitForExit()
End If
MsgBox("EXIT")
Try
Dim ext = CMDReply.ExitCode
Reply = CMDReply.StandardOutput.ReadToEnd()
MsgBox(ext.ToString + " " + Reply)
Catch ex As Exception
MsgBox(ex.ToString)
End Try
it works fine for almost all commands, but when the command="help" the program stucks on CMDReply.WaitForExit(). Can anyone explain what may be the problem here?
Standard deadlock. Read the output first and then wait for exit. The
program cannot exit until you've read all of its output. The code you
have can only work if there's little output that fits the buffer.
From Hans Passant's comment

starting a process in cmd window

I have to start a process in a cmd window.
But in cases like shown because of some error cmd window just flashes and I can't see what happens. It would be the best if cmd window stay opened until some keypress or similar.
Dim q As String = Chr(34)
Dim p As New Process
With p.StartInfo
.FileName = q & whereis7z & "\7z.exe" & q
.Arguments = " e " & q & tempArch & fNameStr & q & " -y"
.WindowStyle = ProcessWindowStyle.Normal
.CreateNoWindow = False
.WorkingDirectory = tempArch
Debug.Print(.FileName & .Arguments)
End With
p.Start()
If p.ExitCode <> 0 Then
MsgBox(p.ExitCode, MsgBoxStyle.Critical)
End If
Is here any way to keep cmd window opened until keypress to see what's wrong with my 'StartInfo' because 'ExitCode' is not enough.
Alternatively, you could redirect the standard output of the window in order to capture the program output.
p.StartInfo.RedirectStandardOutput = True
Then just read in what the program has output so you can display it yourself,
Dim Output as String = p.StandardOutput.ReadToEnd
you should execute the cmd.com application instead of your program directly.
If you try from the start menu "cmd /k dir", you will receive the directory listing and the window will remain open.
I think you must pass your application in parameters (arguments)
Hope this helps
Serge