how can I remove XPCService by script - objective-c

I create project for os x application with xpcservices that run by loginItems. that's mean the service is founded in the app in the path:{APP_NAME}.app/Contents/Library/LoginItems and who is responsible for run the service is the the main app:
NSXPCConnection *connection = [[NSXPCConnection alloc] initWithLoginItemName:#"{SERVICE_NAME}.app" error:&error];
I builded uninstaller, for deleting all the files that I installed. and I need to remove the service.
the command I used for it :
launchctl remove SERVICE_NAME
this is works fine if I run it from the terminal,
but if i run it from script it's remove the service from the "Activity Monitor" but the service still in launchctl list with status -5.
so if I install new version its take the previous version that installed.
I run the script from xcode by NSTask. there is no error. it's does what the script should do.
I even set the administrator privileges:
/usr/bin/osascript -e 'do shell script \"SCRIPT_NAME args 2>&1 etc\" with administrator privileges'
Why it's not remove like I did it in the terminal ?
p.s:
its works when run it from Xcode (even the app is in release mode)

To remove correctly the login item you should do it in the code :
pass false in SMLoginItemSetEnabled:
SMLoginItemSetEnabled((__bridge CFStringRef)loginItemBundleId, false)

Related

How to create a Linux GUI app short cut for WSL2 on Windows10?

I have properly installed and setup WSL2. It works fine.
I also setup X11 forwarding and X server (VcXsrv). I can launch GUI apps such like konsole or gvim or even google-chrome from a bash shell.
Now I want to launch konsole by simply double clicking a short cut on the desktop without launching the bash command mode terminal. How should I do it?
I tried running this in cmd:
> wsl /usr/bin/konsole
and it reports:
qt.qpa.xcb: could not connect to display
qt.qpa.plugin: Could not load the Qt platform plugin "xcb" in "" even though it was found.
This application failed to start because no Qt platform plugin could be initialized. Reinstalling the application may fix this problem.
Available platform plugins are: eglfs, linuxfb, minimal, minimalegl, offscreen, vnc, wayland-egl, wayland, wayland-xcomposite-egl, wayland-xcomposite-glx, xcb.
I'm guessing it is because some X11 forwarding configurations were not properly setup, so I created a k.sh as follows:
#!/usr/bin/bash
export DISPLAY=$(cat /etc/resolv.conf | grep nameserver | awk '{print $2; exit;}'):0.0
export LIBGL_ALWAYS_INDIRECT=1
/usr/bin/konsole &
The first two lines were the X11 settings in my .bashrc, the last line launches konsole.
It works fine under bash environment; but when I ran
wsl k.sh
from windows cmd environment, it silently quitted without launching the konsole.
I'm out of ideas. What should I do to directly launch konsole or other Linux GUI apps under windows without having to getting into bash?
Thanks in advance.
You are asking about two different command-lines, and while the failures in running them via the wsl command have the same root-cause, the underlying failures are likely slightly different.
In both cases, the wsl <command> invocation results in a non-login, non-interactive shell where the command simply "runs and exits".
Since the shell is non-login/non-interactive, your startup files (such as ~/.bashrc and ~/.bash_profile, among others) are not being processed.
When you run:
wsl /usr/bin/konsole
... the DISPLAY variable is not set, since, as you said, you normally set it in your ~/.bashrc.
Try using:
wsl -e bash -lic "/usr/bin/konsole"
That will force bash to run as a login (-l), interactive (-i) shell. The DISPLAY should be set correctly, and it should run konsole.
Note that the quotes probably aren't necessary in this case, but are useful for delineating the commands you are passing to bash. More complicated command-lines can be passed in via the quotes.
As for:
wsl k.sh
That's likely a similar problem. You are doing the right thing by setting DISPLAY in your script, but I notice that you aren't using a fully-qualified path it. This would normally work, of course, if your script is in a directory on the $PATH.
But I'm guessing that you might add that directory to the $PATH in your startup config, which means (again) that it isn't being set in this non-login, non-interactive shell.
As before, try:
wsl -e bash -lic "k.sh"`
You could also use a fully-qualified path, of course.
And, I'm fairly sure you are going to run into an issue with trying to put konsole in the background via the script. When WSL exits, and the bash shell process ends, the child konsole process will terminate as well.
You could get around this with a nohup in the script, but then you also need to redirect the stderr. It's probably easiest just to move the & from the script itself to the command-line. Change your k.sh to:
#!/usr/bin/bash
export DISPLAY=$(cat /etc/resolv.conf | grep nameserver | awk '{print $2; exit;}'):0.0
export LIBGL_ALWAYS_INDIRECT=1
/usr/bin/konsole
Then run it with:
wsl -e bash -lic "k.sh &"`
Finally, a side note that when and if you can upgrade to Windows 11, it will automatically create Windows Start Menu entries for any Linux GUI app you install that creates a .desktop file. You can manually create .desktop files to have WSL create Start menu items for most applications.
For reference, in Windows 11 it's easier. To run a GUI application without a terminal window popping up, you just need to call wslg.exe instead of wsl.exe.
So, for example:
target: C:\Windows\System32\wslg.exe konsole
start in: C:\WINDOWS\system32
shortcut key: None
comment: Konsole
This tutorial shows how to install VcXsrv and and edit .bashrc to ensure that the "DISPLAY env var is updated on every restart".
DISPLAY env var needs to be dynamic setting.
I've used it successfully with WSL2 on Windows10 Version 21H2 (OS build 19044.2130) to run Chrome, Edge, and thunar. I'm using the Ubuntu 20.04 Linux distro.
To edit .bashrc follow these instructions.

Kestrel server doesn't work when run in background, why?

I have a project made and tested with Visual Studio. It works.
Then I uploaded it into Ubuntu server.
Then ran it with dotnet run. Works, remote machines see it (via nginx proxy).
Then I tried dotnet run &. The process seems like started, but nothing listens on port specified. Then, according to the example, I tried sudo nohup dotnet run kestrel > /dev/null 2>&1 &. This time it listened for a while, then died with:
Application started. Press Ctrl+C to shut down.
fail:
Microsoft.AspNetCore.Diagnostics.ExceptionHandlerMiddleware[0]
An unhandled exception has occurred: Can not find compilation library location for package 'google.protobuf'
System.InvalidOperationException: Can not find compilation library
location for package 'google.protobuf' at
Microsoft.Extensions.DependencyModel.CompilationLibrary.ResolveReferencePaths()
(A fragment of output from nohup.out, first linens, I skipped project details as irrelevant and private).
Any clues what's happening? I still get no errors when running it in foreground.
Here's what I found out: I can't run it (it gives same error messages) when I run it as root. On my test server I have a special user account named "dotnet". When I log in as dotnet I can run the app. As root I can't.
I don't want to run my app with root privileges.
Next try: I run dotnet restore as root. Then I go with nohup dotnet run kestrel > /dev/null 2>&1 & and it works.
Nice. Now is there a way to start my app with limited privileges?
I found the answer myself, so I'll share.
First: do not run .NET core projects on Linux as root if you don't intend to give them full root privileges. I think web applications with root privileges are bad idea and sort of asking for troubles.
But well, when something doesn't work, it's tempting to use sudo from time to time. And it turns out it was the cause of the problem:
dotnet restore and dotnet run must be executed with the same privileges, by the same user. When I issued dotnet restore as root, it worked. It's even harder the other way, when you want to run the project as user with lower privileges. You have to remove all temporary files before issuing dontet restore. So, generally nohup dotnet run kestrel > /dev/null 2>&1 & works as charm, no sudo is needed here, running this as root can be harmful.
Now I always create special dotnet user to run dotnet apps on servers. It's safer this way. The user cannot sudo. When I need to perform administrative tasks I just start separate root session. I use the same approach with database access. The app has only rights to execute procedures, not even select allowed.

Jenkins SSH remote process is getting killed as soon as the Jenkins SSH plugin returns back

Jenkins version: 1.574
I created a simple job which performs the following:
Using "Execute shell script on remote host using SSH" as one of the BUILD steps, I'm just calling a shell script. This shell script performs stop and start operations on Tomcat to restart an application on the target machine.
I have a valid username, password, port defined for the target SSH server in Jenkins Global settings.
I saw this behavior that when I run a Jenkins job and call the restart script (which gets the application name as parameter $1), it works fine, but as soon as "Execute shell script on remote host using SSH" step completes, I see the new process dies on the remote/target application server.
If I run the script from the target/remote server itself, everything works fine and the new process/PID remains live forever, but running the same script from Jenkins, though I don't see any errors and everything works as expected, the new process dies as soon as the above mentioned SSH step is complete and control comes back to the next BUILD step in Jenkins job OR the Jenkins job is complete.
I saw a few posts/blogs and tried setting: BUILD_ID=dontKillMe in the Jenkins job (in various places i.e. Prepare Environment variables and also using Inject Environment variables...). When the job's particular build# is complete, I can see Environment Variables for that build# does say BUILD_ID=dontKillMe as its value (instead of the default Timestamp tag value).
I tried putting nohup before calling the restart script, i.e.,
nohup restart_tomcat.sh "${app}"
I also tried:
BUILD_ID=dontKillMe nohup restart_tomcat.sh "${app}"
This doesn't give any error and creates a nohup.out file on the remote server (but I'm not worried about it as the restart_tomcat.sh script itself creates its own LOG file which I'm "cat"ing after the restart_tomcat.sh script is complete. cat'ing on the log file is performed using another "Execute shell script on remote host using SSH" build step, and it successfully shows the log file created by the restart script).
I don't know what I'm missing at this point, but as soon as the restart_tomcat.sh step is complete, the new PID/process on the remote/target server dies.
How can I fix this?
I've been through this myself.
On my first iteration, before I knew about Jenkins ProcessTreeKiller, I ended up just daemonizing Tomcat. The Apache Tomcat documentation includes a section on running as a daemon.
You can also try disabling the ProcessTreeKiller for your whole Jenkins instance, if it's relatively small (read the first link for information).
The BUILD_ID=dontKillMe should be passed to the shell, and therefore it should be in your command line, not in Jenkins global configuration or job parameters.
BUILD_ID=dontKillMe restart_tomcat.sh "${app}" should have worked without problems.
You can also try nohup restart_tomcat.sh "${app}" & with the & at the end.
My solution (it worked after trying everything else) in Ubuntu 14.04 (Trusty Tahr) (Amazon AWS - Amazon EC2), Jenkins 1.601:
Exec command: (setsid COMMAND < /dev/null > /dev/null 2>&1 &);
Exec in PTY: DISABLED
// Example COMMAND=socat TCP4-LISTEN:1337,fork TCP4:127.0.0.1:1338
I created this Transfer as my last one.
#!/bin/ksh
export BUILD_ID=dontKillMe
I added the above line to the start of my script and the issue was resolved.

How to run a CruiseControl task as an administrator in Windows Server 2008

I'm currently using CruiseControl.NET to automate my build. We have two different ways to build a solution in my build environment - one is through the Keil uVision4 IDE, the other is through Visual Studio 2008.
I've successfully gotten the Visual Studio solution to build properly using CruiseControl.NET and have created a batch file which properly uses Keil's uVision command line interface to compile my uvproj Project (compilation details here).
Problem Description
1) I can successfully execute the build script on my Windows 2008 server and build the project if I create a command prompt with administrator privileges (I'm doing this manually - start -> run -> cmd with ctrl-shift-enter to run as admin).
2) However, if I create a command prompt without administrator privileges, and attempt to execute the batch file, the batch file won't work unless I accept the prompt asking me to confirm admin rights are required to run the batch script.
How do I automatically execute a batch file as an administrator through CruiseControl?
Is this something that could be automated using the RunAs command?
Technical details
1) The batch file being executed is pretty simple - it deletes the old output and re-makes the output, creating a build log file in the location below.
set BuildLogLocation=BuildLog\BuildLog.txt
echo on
cd ../..
cd PTM
rmdir /s /q output
mkdir output
mkdir BuildLog
C:\Keil\UV4\UV4.exe -r myProj.uvproj -o %BuildLogLocation%
echo ErrorLevel of build is %ERRORLEVEL%
echo build complete, see %BuildLogLocation%
2) Currently I'm looking to use the Exec functionality to run the Keil build script above:
<Exec>
<Command>C:\myProject\Build\KeilBuild\BuildScript.bat<Command/>
<buildTimeoutSeconds>600<buildTimeoutSeconds/>
<!-- Details about error codes can be found here:
http://www.keil.com/support/man/docs/uv4/uv4_commandline.htm -->
<successExitCodes>0,1</successExitCodes>
<Exec/>
Related questions:
How can I use a build server with Keil uVision4 (MDK-ARM), script a build, use a makefile? (Electrical Engineering)
Execute a command-line command from CruiseControl.NET (Stack Overflow)
Can you run CCService, the CruiseControl.NET Windows Service, as a user who has administrative permissions? I'd try that first.
If that doesn't work, I would use runas to run your script. You'll have to embed the administrative user's password in the script calling runas.
I know this is old but, Did you get an offical way to do it Via Cruise Control?
Normally I create this and call it to call other processes "As Admin".
Make a ".VBS" script with This in the contents:
Dim strBatchPath
strBatchPath = "PATH-TO-FILE.EXE"
Set runBatch = CreateObject("shell.application")
runBatch.shellexecute strBatchPath,,,"runas",1
That could be an option to people that can't find an official way
You could try psExec from sysinternals. If you don't need to run as a nt-authority account you should be able to use this in the same way as runas.
It allows you to pass in the username/password as a switch (if memory serves)
I have Discovered that when using PSEXEC and using the -h switch, it then "runs as admin" on destination
e.g.
psexec -h \ServerToRunOn /accepteula -u DOMAIN\USER -p PASSWORD "PATH-TO-FILE"
I am Using CC.Net to call a batch file with the above in. This will run that file as Admin

RestartManager fails to restart application during update

I'm using c#, .net 4, WIX 3.5, Windows Vista.
I have made my application compatible with RestartManager by p/invoking the RegisterApplicationRestart method and by handling the WM_QUERYENDSESSION and WM_ENDSESSION window messages (I return new IntPtr(1);).
If I try to update my application manually, then everything works as it should:
Launch application;
Launch msi file containing new app version;
During the installation/update, I'm prompted to close the running application;
Upon continuing the running app is closed, install completes, and the app is restarted;
If I try to update my application from the application itself, then I run into problems:
1) Launch application;
2) Download the new msi file;
3) Launch msi file with:
using (System.Diagnostics.Process p = new System.Diagnostics.Process())
{
p.StartInfo.UseShellExecute = false;
p.StartInfo.FileName = "msiexec";
p.StartInfo.Arguments = "/i \"" + downloadPath + "\" /passive";
p.StartInfo.UserName = "Administrator";
p.StartInfo.Password = securePassword;
p.Start();
}
4) Because I'm using passive mode, the application is closed automatically;
5) After the installation, my application is not restarted and under Event Viewer I have an
Event 10007 - Application or service 'MyApp' could not be restarted.
I have tried:
Not to use passive mode for msiexec;
Launch msiexec via cmd.exe (cmd.exe /C "msiexec /i ....") - in the hopes that launching msiexec from another process would solve the problem;
Wait for 60+ seconds before launching the msi update (shouldn't be relevant in my scenario, but MSDN documentation has something about it...)
But none of the above has worked (always the same result).
Having to launch the setup with elevated permissions might have something to do with the issue, because during the manual update I get a warning in the Event Viewer - Application MyApp (pid 3220) cannot be restarted - Application SID does not match Conductor SID.
Despite this, restarting the app still works. Googleing the warning yields no good/specific results, only that this warning is probably caused by running the msi in an elevated prompt.
How do I fix (or workaround) this issue, so that I can update my application from the application itself and restart my application afterwards?
Edit - extra testing:
There doesn't seem to be a need to respond to WM_QUERYENDSESSION and WM_ENDSESSION messages, because application restart during a manual upgrade works without them, so we can rule them out;
If I don't provide administrator credentials to the application initiated upgrade and instead I type them in during the upgrade, then app restarting works;
If I run an elevated command prompt and initiate an application upgrade from there (manually), then app restarting still works;
In order for application upgrade to work at all under Standard user accounts (so far I tested under an Administrator account with UAC), then I also have to set p.StartInfo.LoadUserProfile = true;. Otherwise nothing happens. (application restart still doesn't work though);
I tried all other process StartInfo parameters that I could set - WorkingDirectory, Redirect, Verb
(= "runas") - no change in results;
I installed Vista SP2 onto the virtual machine that I have been testing on (so far ran SP1), but no change;
I performed an "automatic" application upgrade with verbose logging. In the end there was an error message - RESTART MANAGER: Failed while restarting applications. Error: 352. That error code is very generic (http://msdn.microsoft.com/cs-cz/library/aa373665), inorder to get more detailed info I would have to write my own installer that would call RmGetList after the error, then I might get more details (this though is something I'm not willing to do);
Edit 2 - msi log file:
http://mommi.planet.ee/muu/log.txt
Assuming that the manual process indeed works without any problem it seems that your need for Administrator privileges in combination with the "updating itself" leads to these problems. I see the following options:
create a batch file to execute the update
When you want to update call this batch file (with elevated privileges), make the app close itself... the batch file should wait some seconds, then check whether the app is still running (and close it in case) and then run the commandline you need to run msiexec - don't restart the app from within msiexec but after a successfull run of msiexec from the batch file.
create a batch file which is always used to start the app
When the time comes to update you just end the app. Either the batch file check for an available update and applies it, starting the app after successfull update OR the app set some environment variable which is then accordingly processed by the rest of the batch file.