Take the 2-minute tour ×
Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

I want to launch a CI server (TeamCity 8.1) on startup on a Mac OS X Server running Mavericks. I don't want the CI server to be launched by the root user but by another user on the system.
The user I want to start the server with is server1:staff. I installed TeamCity in /Applications/TeamCity. The TeamCity folder is owned by server1:staff.
Then I created 2 plists in /Library/LaunchDaemons owned by root:wheel but specifying that I want this process to be started by the server1:staff user.

Here are the plists. This one starts the server:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>WorkingDirectory</key>
    <string>/Applications/TeamCity</string>
    <key>Debug</key>
    <false/>
    <key>Label</key>
    <string>jetbrains.teamcity.server</string>
    <key>OnDemand</key>
    <false/>
    <key>KeepAlive</key>
    <true/>
    <key>ProgramArguments</key>
    <array>
        <string>bin/teamcity-server.sh</string>
        <string>run</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>StandardErrorPath</key>
    <string>logs/launchd.err.log</string>
    <key>StandardOutPath</key>
    <string>logs/launchd.out.log</string>
    <key>UserName</key>
    <string>server1</string>
</dict>
</plist>

This one starts the build agent that runs the builds:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>Debug</key>
    <false/>
    <key>KeepAlive</key>
    <true/>
    <key>Label</key>
    <string>jetbrains.teamcity.BuildAgent</string>
    <key>OnDemand</key>
    <false/>
    <key>ProgramArguments</key>
    <array>
        <string>launcher/bin/TeamCityAgentService-macosx-universal-32</string>
        <string>-c</string>
        <string>../conf/wrapper.conf</string>
    </array>
    <key>RunAtLoad</key>
    <true/>
    <key>SessionCreate</key>
    <true/>
    <key>StandardErrorPath</key>
    <string>logs/launchd.err.log</string>
    <key>StandardOutPath</key>
    <string>logs/launchd.out.log</string>
    <key>WorkingDirectory</key>
    <string>/Applications/TeamCity/buildAgent</string>
    <key>UserName</key>
    <string>server1</string>
</dict>
</plist>

With this configuration the server does not launch on startup.
The only way to have the server launch on startup with my configuration is without specifying the UserName/UserGroup in the plist. But with this the server launches with the root user.
I already tried to change the ownership of the plist to match the server1:staff user but with no success.
I'm kind of stuck with this configuration and I don't know what is wrong with it.
Any tips are welcome.

[EDIT]
I have nothing wrong in Console.app concerning TeamCity.
To be sure I reinstalled TeamCity from scratch etc.
There is nothing in launchd.err.log. Though I found this in launchd.out.log but I don't know when it happened (currently rebooting after deleting all log files)

BuildId=null, AgentOwnAddress='null', AlternativeAddresses=[10.175.11.48, 192.168.2.92], Port=9090, Version='29939', PluginsVersion='29939-md5-51785f46b7e643a588892acce02b9333', AvailableRunners=[Ant, Duplicator, gradle-runner, Inspection, Ipr, JPS, Maven2, rake-runner, simpleRunner, Xcode], AvailableVcs=[perforce, mercurial, jetbrains.git, svn, cvs], AuthorizationToken='afccc2fae65d1c580e34d4aed4cc55df', PingCode='DX5fzIvbgFCvVghhwuvARdEU33XOfzCW'} 
jvm 1    | Call http://localhost:8111/RPC2 buildServer.registerAgent3: java.net.ConnectException: Connection refused 
jvm 1    | Registering on server http://localhost:8111, AgentDetails{Name='Default Agent', AgentId=null, BuildId=null, AgentOwnAddress='null', AlternativeAddresses=[10.175.11.48, 192.168.2.92], Port=9090, Version='29939', PluginsVersion='29939-md5-51785f46b7e643a588892acce02b9333', AvailableRunners=[Ant, Duplicator, gradle-runner, Inspection, Ipr, JPS, Maven2, rake-runner, simpleRunner, Xcode], AvailableVcs=[perforce, mercurial, jetbrains.git, svn, cvs], AuthorizationToken='afccc2fae65d1c580e34d4aed4cc55df', PingCode='DX5fzIvbgFCvVghhwuvARdEU33XOfzCW'} 
jvm 1    | Call http://localhost:8111/RPC2 buildServer.registerAgent3: java.net.ConnectException: Connection refused 
wrapper  | TERM trapped.  Shutting down.
jvm 1    | Processing shutdown hook. 
jvm 1    | Sending agent force shutdown command to: http://localhost:9090 
jvm 1    | Shutdown command successfully sent. Agent is exiting. 
jvm 1    | Stop command called 
jvm 1    | Agent process finished 
jvm 1    | Agent has exited with code: 30 
jvm 1    | Launcher is exiting 
wrapper  | <-- Wrapper Stopped  

[EDIT2] After restarting I have nothing in the server logs and Console.app (the server does not start so I think it is expected behavior).

share|improve this question
    
Anything interesting in the Console.app logs after it fails to start? –  Daniel Beck Mar 18 at 13:45

1 Answer 1

The use of all these relative paths is a bit sketchy. I think you're not thinking through your current working directory and relative paths correctly.

For example, the build agent plist specifies that its working directory is…

/Applications/TeamCity/buildAgent

…but one of the program arguments that you pass to the launcher binary is…

../conf/wrapper.conf.

I'm pretty sure this would be interpreted as relative to the working directory of…

/Applications/TeamCity/buildAgent

…not the binary's directory of…

/Applications/TeamCity/buildAgent/launcher/bin.

So you're actually telling it to look in the main…

/Applications/TeamCity/conf

…which doesn't typically have a wrapper.conf, but I think maybe you thought you were telling it to look in…

/Applications/TeamCity/buildAgent/launcher/conf

…which is where wrapper.conf typically lives.

I think you may have some other working directory / relative path mistakes in your plists as well. For example, it looks like you have two separate logs directories, so you have two separate sets of launchd stdout/stderr files. Buy maybe that's what you wanted.

I think you should probably straighten out these path problems first. This may be your whole problem, not a launchd problem at all. But even if it isn't, you need to get this cleared up so it doesn't get in the way of further launchd troubleshooting.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.