Installing Redmine as a Service
This can be a tricky thing to get working if you have no knowledge of Ruby or assume that all the scripts you come across actually work. I have found a lot of information about getting Redmine to run as a windows service is quite old and ruby ahs changed a lot since they were written. This article hold all my research from googling around the internet which includes those key niggets of information to help me get the scripts working.
As ever you have come across another article saying how things should work but never just give you the code so you can get Redmine working and worry about other things. This article is diffrerent, i have included all my research so if there are any problems i have not seen or issues that come along later you will be able to fix them withou pulling your hair out and lastly this article has the working scripts. If you just want the scripts so you can get running please scroll to 'The Scripts' and follow the installations instructions and you will be running very quickly.
Notes
General
There are currently a few methods that I have found to create a service:
- Mongrel server – seems old way of doing it
- Creating a registry entry via a script and then a payload script with the service code
- Create the service utilising the windows resource kit by having another program run as a wrapper
- Simple – create the service by the command line pointing to your script
- Read this article on how to install redmine as a service. It is really easy to follow
http://www.redmine.org/projects/redmine/wiki/HowTo_run_Redmine_as_a_Windows_service_%28win32-service_+_taskill_approach%29 - Your Redmine directory is - D:\Documents\Developer\RubyRoot\redmine
- Your ruby directory - D:\Documents\Developer\RailsInstaller\Ruby2.1.0
- The command to create the service is:
sc create redmine binPath= "D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw -C D:\Documents\Developer\RubyRoot\redmine\ service.rb"Notes
- You might need to run this as administrator
- This creates a service called redmine
- When created it is set as Manual, you need to change this to automatic - I think!
- sc delete redmine will delete the service
- creates a log file in {REDMIN_DIR}\log
- my code - sc create redmine binPath= "D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw -C D:\Documents\Developer\RubyRoot\redmine\ service.rb"
- should there be a space at …..redmine\ service.rb
- these instructions will only set Redmine as a service not all the rails
- The script of stack overflow don’t forget to change the CONFIG statement, see thread
- Irb / IRb= iteractive ruby winapi - Ruby: gem win32-service: Create a service with Admin privileges - Stack Overflow
- notes for the win32-service.gem is in its gem folder under docs which ill give the syntax for using the gem
- most commands seem to want to run from the project directory - check steps and add reminders where needed.
- i think where you run the 'rails server' command denotes the root folder of the ruby server
- unless specified the current directory will be 'c:\windows\system32\'
- Ruby.exe is the base binary and rubyw.exe is a version that does not present a console which is better because it can run silently.
- task kill method works if you do not stop the service to early and i need to add the addition of server.pid delete statement
- unless you change it the default directoy is c:\windows\system32, you can change it on the service command line prompt with the -C option or in the script with the :chdir or Dir.chdir
- remember running scripts and things from the command prompt will give you more information
When happens when you run the Redmine service
When you start the service it can take up to 60 seconds to properly start and if you look in task manager it is normal to see to instances of ruby either ruby.exe or rubyw.exe
This is what happens:
- when you start the windows service this spawns 1 instance of rubyw.exe in windows
- the windows service loads the ruby script service.rb and executes it, this the causes antoher instance of rubyw.exe to appear in the windows service list
- the webrick server starts creates and populate the /tmp/pid/server.pid with its process id
- redmine starts it then replaces the number in server.pid with its own number
- servider.pid is created with redmines PID inside (server.pid is the default)
- you can see the rubyw.exe is running at about 5% CPU
- when the rubyw.exe (with no usage on redmine) drops to 0% the server is running and it is safe to stop the redmine server if required
Errors
When trying to configure redmine to run as a service you might come across some of the issues I am going to outline below but the good thing is I am going to tell you why they occur which will make fixing them stress free.
Error 1053
Windows could not start the redmine service on Local Computer. Error 1053: The service did not respond to the start or control request in a timely fashion.
- This occurs when there are issues in the script or in particular the binary path definition in the windows service (ie the one you create with the 'sc create' command)
- When you start the service and it immediately fails it is most likely the binary path statement.
- If it fails a little way in it is most likely the spawn.process file path is wrong.
- not pointing to the ruby/rubyw binary correctly (ie full location)
- not pointing to the script correctely (ie full location)
- not changing to the script directory (ie -C or :chdir)
- faulty script, ie written wrong
- a previously run script has left a server.pid file in the /tmp/pid/ folder which prevents the daemon spawning
- possibly incompatible builds of win32-services gem
Error 1067
Windows could not stop the redmine service on Local Computer. Error 1067: The process terminated unexpectedly.
- This can be caused by trying to close the service too quickly after starting it.
- If you get this message after the service has started correctely and been running for a while and then you stop it the error occurs this is most likely to be you exit code is in correct, perhaps not terminating the correct pid.
Links
Normal Script
- how to configure a rails app (redmine) to run as a service on windows? - Stack Overflow - this is the DemoDaemon script and the basis of my script (and the task kill script from redmine.org)
- Create a Windows Service with Ruby - Part 1 - this is a very clear article on how to install a ruby app as a service (written 23/07/13). You can download his code from github. Even thought it is for a ruby app it is the same code for redmine (almost). This code has a main script code and some smaller ones for registering and unregistering the service. The service is configured to run under the 'network' user for running without a logged in user.
It mentions the use of:- run as 'network' user - to allow the service to run without a user being logged in
- chomp - The chomp method simply removes any leading or trailing whitespace
- 'echo %cd%' - displays the current directory
- -C - This option specifies that Ruby should set the working directory of the script to the directory where the script is located.
- win32 daemon error - Service_Main thread exited abnormally · Issue #4 · djberg96/win32-service · GitHub - this is the 1 file version of the DemoDaemon script
- Sinatra deployed as a windows service [updated] | tech.maynurd.com - a bit old and for something called Sinatra but gives some useful context
- Running a Ruby Program as a Windows Service? - Stack Overflow - this uses code from 'Create a Windows Service with Ruby - Part 1'
- winapi - Ruby: gem win32-service: Create a service with Admin privileges - Stack Overflow
- Win32::Daemon#mainloop method - win32-service (0.8.6) ruby gem documentation - Omniref - this shows you information about win32-service.gem
- winapi - Daemon creation not working using Win32Utils ruby gem - Stack Overflow - usesful insight into error 1053
- Rails Deployment Environment on Windows - Stack Overflow - also covers setting up running rails app/redmine through apache
- ubuntu - How to stop a Daemon Server in Rails? - Stack Overflow
- Stop and Restart Easily a Rails Server - Waiting for dev...
- Ruby on Windows: FAQ: "script.rb" versus "script.rbw" - whatr is the difference between ".rb" and ".rbw" files, (ruby.exe vs rubyw.exe)
- Kill process by name using Ruby on Windows | Nat On Testing - taskkill
- ruby - require 'rubygems' - Stack Overflow - why we need or dont need it
- how to configure a rails app (redmine) to run as a service on windows? - Stack Overflow - mentions DemoDaemon script
- File: README - Documentation for win32-service (0.8.6) - docs for the win32-service
- win32-service | RubyGems.org | your community gem host - the official gem page for win32-service
- Ruby's File.open gives "No such file or directory - text.txt (Errno::ENOENT)" error - Stack Overflow - useful insight into the error and how to output the current directory in ruby
Using Windows Resource Kit
- how to configure a rails app (redmine) to run as a service on windows? | Zachman Answers
- Running Redmine as a Windows Service | Learn First
- Running Any Executable As A Windows Service (Ruby / Sinatra) - Everything is a Ghetto
Mongrel
- Muhammad Naeem: How To Install Redmine on Windows with Apache - this article covers installing redmine from scratch on windows using the mogrel service
- How to install Ruby on Rails alongside WampServer? - Stack Overflow - also covers setting up redmine through apache
- Step-by-step quick installation of Redmine + SVN on Windows | Rahul Vaidya's Blog
Misc Relevant
- Method: File.expand_path - Documentation for core (1.9.2)Method: File.expand_path - Documentation for core (1.9.2)
- Files & Directories (Read Ruby 1.9)
- The Rails Command Line — Ruby on Rails Guides
- How to start rails server? - Stack Overflow
- Run console command in ruby, get PID of child process and kill it in some seconds - Stack Overflow
- Module: Process (Ruby 1.9.3) - covers process.spawn and process.wait commands
- ruby on rails 3 - ROR + A server is already running. Check .../tmp/pids/server.pid. Exiting - Stack Overflow - has examples of how to set a different server.pid file and set a different port
- How to run any Ruby Script as a Windows 7/2008/Vista/2003/XP Service Daemon | AlwaysUp | Start Ruby at boot/on schedule - this is a 3rd party Service software to allow the running of any Ruby Script
- File.expand_path() - the ctl file sends error messages to windows, the daemon file sends error message to the log file
The Scripts
Simple Script
The simple script is the absolute basic version of the script but does work as expected.
These are my notes on using the script found on redmine.org, HowTo run Redmine as a Windows service (win32-service + taskill approach) - Redmine. This script has issues with it so i have listed them below and then you will find my corrected version which does work.
- This script will only run once and then you will get an error (1053) everytime you try an run it afterwards - This is because when thescript finishes it does not delete {redmine_dir}/tmp/pids/servere.pid which prevents it from running when ruby does a check for running processes. To fix this i added a line of code at the end to remove the server.
- when running after correctely setting the details in the script i was still getting a 1053 error. - This is caused because the file location for the spawn.process event needs to be a full address
- it will give a 1063 error when exiting - This can be caused by the exit! command, so i commented it out
Instructions
- Install the win32-service Gem. This is done by opening a command prompt (possibly with admin privileges and the internet) and typing: ruby gem install win32-service
- create a file called redmine-service.rb putting in the script code below.
- Place this script the root folder of your redmine installation D:\Documents\Developer\RubyRoot\redmine\
- In the script update REDMINE_DIR path to fit your Redmine installation
- open up a command prompt with administrator priviledges and run the following command that will create the Windows Service. Edit the command where needed, D:\Documents\Developer\RubyRoot\redmine\ is the path of the directory where the service.rb file is located and D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw your Ruby binary.
sc create redmine binPath= "D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw -C D:\Documents\Developer\RubyRoot\redmine\ redmine-service.rb"
When you fill in the command make sure you leave the space inbetween ...\redmine\ redmine-service.rb , the reason for this is that ...\redmine\ beongs with the -C switch which is telling the code to change to the redmine directory before running the script. you can actually add a full path to redmine-service.rb if you wanted to make it easier to read.
- You can now start and stop the Redmine Service through services.msc or these should work sc start redmine and sc stop redmine
- If you want to delete the service you can use sc delete redmine
The Script
REDMINE_DIR = 'D:\Documents\Developer\RubyRoot\redmine' LOG_FILE = "#{REDMINE_DIR}\\log\\redmine-service.log" begin require 'win32/daemon' include Win32 class RedmineService < Daemon def service_init File.open(LOG_FILE, 'a'){ |f| f.puts "Initializing service #{Time.now}" } @server_pid = Process.spawn 'D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw script/rails s -e production', :chdir => REDMINE_DIR, :err => [LOG_FILE, 'a'] end def service_main File.open(LOG_FILE, 'a'){ |f| f.puts "Service is running #{Time.now} with pid #{@server_pid}" } while running? sleep 10 end end def service_stop File.open(LOG_FILE, 'a'){ |f| f.puts "Stopping server thread #{Time.now} with pid #{@server_pid}" } system "taskkill /PID #{@server_pid} /T /F" Process.waitall File.open(LOG_FILE, 'a'){ |f| f.puts "Service stopped #{Time.now}" } pid_file = 'tmp/pids/server.pid' File.file?(pid_file) && File.delete(pid_file) #exit! # can cause a bad exit end end RedmineService.mainloop rescue Exception => e File.open(LOG_FILE,'a+'){ |f| f.puts " ***Daemon failure #{Time.now} exception=#{e.inspect}\n#{e.backtrace.join($/)}" } raise end
My Complex Script
This is my script that i have made from several scripts. This is a modern daemon code with logging and a controller file to make install/running/deleting the script as a service. The script will also populate most of the variables if your Ruby path is set and you run the redmine_service_ctl.rb from the root of your redmine installation.
My script might not handle paths with spaces in them correctely. This should be easily fixed by using quotes (") where needed. I might update the scripts if there is any interest.
Instructions
The script configures itself automatically.
- Install the win32-service Gem. This is done by opening a command prompt (possibly with admin privileges and the internet) and typing: ruby gem install win32-service
- redmine_service_ctl.rb file
- create a file called redmine_service_ctl.rb putting the in the Controller Script code below.
- Place this script the root folder of your redmine installation (eg: D:\Documents\Developer\RubyRoot\redmine\)
- Edit the file as required
- redmine_service.rb file
- create a file called redmine_service.rb putting the in the Daemon / Service Script code below.
- Place this script the root folder of your redmine installation (eg D:\Documents\Developer\RubyRoot\redmine\)
- Edit the file as required
- Install the service - Open up a command prompt with administrator priviledges and run the following command that will create the windows service.
ruby redmine_service_ctl.rb install
If the installation does not work as expected you might need to
- check your ruby path exists
- that you have run this script from your redmine root folder
- the script might automatically run only if your configured MySQL service is already running but this will not affect installtion of the service.
- Edit the Scripts to insert manuall variables instead of relying on the auto variable code.
Controller Script
This script should be called redmine_service_ctl.rb and this is the service management script, it is used to install/stop/start/delete the service from the command line.
############################################################################ # # redmine_service_ctl.rb # # This is a command line script for installing and/or running a small # Ruby program as a service, in this case it is Redmine. # # The service will run Redmine and will record certain events to a log file. # If enabled, the service can also write a small bit of text # to the log file every 20 seconds to show it is running. # Some text will bve written to the log file during the initialization (service_init) step. # # It should take about 10 seconds to start, which is intentional - it's a test # of the service_init hook, so don't be surprised if you see "one moment, # start pending" about 10 times on the command line. # # The Log File is {redmine_dir}/log/test.log. Feel free to delete it when finished. # # To run the service, you must install it first. # # Usage: ruby redmine_service_ctl.rb <option> # # Note that you *must* pass this program an option # # Options: # install - Installs the service. The service name is "RedmineService" # and the display name is "Redmine Windows Service". # start - Starts the service. Make sure you stop it at some point or # you will eventually fill up your filesystem!. # stop - Stops the service. # pause - Pauses the service. # resume - Resumes the service. # uninstall - Uninstalls the service. # delete - Same as uninstall. # # You can also used the Windows Services GUI to start and stop the service. # # To get to the Windows Services GUI just follow: # Start -> Control Panel -> Administrative Tools -> Services # # by shoulders @ QuantumWarp.com # used code from # http://stackoverflow.com/questions/877943/how-to-configure-a-rails-app-redmine-to-run-as-a-service-on-windows # ############################################################################ #--------------------------------------------------------------------------- # Includes #--------------------------------------------------------------------------- # require 'rubygems' # only for < ruby 1.9 require 'win32/service' require 'rbconfig' include Win32 include RbConfig # Make sure you're using the version you think you're using. puts 'VERSION: ' + Service::VERSION SERVICE_NAME = 'RedmineService' SERVICE_DISPLAY_NAME = 'Redmine Windows Service' SERVICE_DESCRIPTION = 'This is my Windows Redmine Service' #--------------------------------------------------------------------------- # Automatically Create Windows Service Binary Path #--------------------------------------------------------------------------- RUBY_BINARY = File.join(CONFIG['bindir'], 'rubyw').tr('/', '\\') PATH = ' -C ' + File.dirname(File.expand_path($0)).tr('/', '\\') + '\\ ' + 'redmine_service.rb' CMD = RUBY_BINARY + PATH # MANUAL OVERIDE # This builds the windows binaryPath ="" in the format: # CMD = 'D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw -C D:\Documents\Developer\RubyRoot\redmine\ redmine_service.rb' # CMD = 'D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw -C D:\Documents\Developer\RubyRoot\redmine\ D:\Documents\Developer\RubyRoot\redmine\redmine_service.rb' # if you want to uses spaces in your path you need to enclose in each path in quotes ("") # possibly # CMD = '"D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw" -C "D:\Documents\Developer\RubyRoot\redmine\ " "redmine_service.rb"' # CMD = '"D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw" -C "D:\Documents\Developer\RubyRoot\redmine\" "D:\Documents\Developer\RubyRoot\redmine\redmine_service.rb"' #--------------------------------------------------------------------------- # Perform Service Action Based on Argument supplied #--------------------------------------------------------------------------- # You must provide at least one argument. raise ArgumentError, 'No argument provided' unless ARGV[0] # These are the actions performed for the various windows service tasks/functions case ARGV[0].downcase when 'install' Service.new( # These are the service configuration settings that are written to the registry # will run automatically without a user being logged in :service_name => SERVICE_NAME, :display_name => SERVICE_DISPLAY_NAME, :description => SERVICE_DESCRIPTION, :start_type => Service::AUTO_START, :service_type => Service::WIN32_OWN_PROCESS, :load_order_group => 'Network', :dependencies => nil, #:dependencies => ['Developer-Apache2.4','Developer-MySQL'], #:error_control => Service::ERROR_NORMAL, #:service_start_name => 'SomeDomain\\User', #:password => 'XXXXXXX', :binary_path_name => CMD, ) puts CMD puts 'Service ' + SERVICE_NAME + ' installed' # One of following code sections, which all match to their corresponding 'Windows Service Function' is # triggered depending on what argument is supplied in the oommand line. when 'start' if Service.status(SERVICE_NAME).current_state != 'running' Service.start(SERVICE_NAME, nil, 'hello', 'world') while Service.status(SERVICE_NAME).current_state != 'running' puts 'One moment...' + Service.status(SERVICE_NAME).current_state sleep 1 end puts 'Service ' + SERVICE_NAME + ' started' else puts 'Already running' end when 'stop' if Service.status(SERVICE_NAME).current_state != 'stopped' Service.stop(SERVICE_NAME) while Service.status(SERVICE_NAME).current_state != 'stopped' puts 'One moment...' + Service.status(SERVICE_NAME).current_state sleep 1 end puts 'Service ' + SERVICE_NAME + ' stopped' else puts 'Already stopped' end when 'uninstall', 'delete' if Service.status(SERVICE_NAME).current_state != 'stopped' Service.stop(SERVICE_NAME) end while Service.status(SERVICE_NAME).current_state != 'stopped' puts 'One moment...' + Service.status(SERVICE_NAME).current_state sleep 1 end Service.delete(SERVICE_NAME) puts 'Service ' + SERVICE_NAME + ' deleted' when 'pause' if Service.status(SERVICE_NAME).current_state != 'paused' Service.pause(SERVICE_NAME) while Service.status(SERVICE_NAME).current_state != 'paused' puts 'One moment...' + Service.status(SERVICE_NAME).current_state sleep 1 end puts 'Service ' + SERVICE_NAME + ' paused' else puts 'Already paused' end when 'resume' if Service.status(SERVICE_NAME).current_state != 'running' Service.resume(SERVICE_NAME) while Service.status(SERVICE_NAME).current_state != 'running' puts 'One moment...' + Service.status(SERVICE_NAME).current_state sleep 1 end puts 'Service ' + SERVICE_NAME + ' resumed' else puts 'Already running' end else raise ArgumentError, 'unknown option: ' + ARGV[0] end
Daemon / Service Script (the actual service)
This should be called redmine_service.rb
############################################################################ # # redmine_service.rb # # This script should automatically configure itself. # # The only thing you might need to alter are the RUBY_BINARY_ARGUMENTS. # -e is the enviroment and the options are development/production # -p is the port number to run Redmine on # # by shoulders @ QuantumWarp.com # used code from # http://stackoverflow.com/questions/877943/how-to-configure-a-rails-app-redmine-to-run-as-a-service-on-windows # ############################################################################ #--------------------------------------------------------------------------- # Includes #--------------------------------------------------------------------------- include RbConfig #--------------------------------------------------------------------------- # Automatically Create File Paths #--------------------------------------------------------------------------- RUBY_BINARY = File.join(CONFIG['bindir'], 'rubyw').tr('/', '\\') #RUBY_BINARY = 'D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw' # Redmine 2.x #RUBY_BINARY_ARGUMENTS = ' ' + 'script/rails s -e production -p 3000' #RUBY_BINARY_ARGUMENTS = ' script/rails s -e production -p 3000' # Redmine 3.x RUBY_BINARY_ARGUMENTS = ' ' + 'bin/rails s -e production -p 3000' #RUBY_BINARY_ARGUMENTS = ' bin/rails s -e production -p 3000' REDMINE_DIR = File.dirname(File.expand_path($0)).tr('/', '\\') #REDMINE_DIR = 'D:\Documents\Developer\RubyRoot\redmine' LOG_FILE = "#{REDMINE_DIR}\\log\\redmine-service.log" #LOG_FILE = 'D:\Documents\Developer\RubyRoot\redmine\log\redmine-service.log' #--------------------------------------------------------------------------- # The Actual Service #--------------------------------------------------------------------------- begin require 'win32/daemon' include Win32 class RedmineDaemon < Daemon # This method fires off before the +service_main+ mainloop is entered. # Any pre-setup code you need to run before your service's mainloop # starts should be put here. Otherwise the service might fail with a # timeout error when you try to start it. # def service_init File.open(LOG_FILE, 'a'){ |f| f.puts "Initializing service #{Time.now.to_s}" } @server_pid = Process.spawn RUBY_BINARY + RUBY_BINARY_ARGUMENTS, :chdir => REDMINE_DIR, :err => [LOG_FILE, 'a'] # MANUAL COMMANDS # Redmine 2.x #@server_pid = Process.spawn 'D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw script/rails s -e production -p 3000', :chdir => REDMINE_DIR, :err => [LOG_FILE, 'a'] # Redmine 3.0 #@server_pid = Process.spawn 'D:\Documents\Developer\RailsInstaller\Ruby2.1.0\bin\rubyw bin/rails s -e production -p 3000', :chdir => REDMINE_DIR, :err => [LOG_FILE, 'a'] end # This is the daemon's mainloop. In other words, whatever runs here # is the code that runs while your service is running. Note that the # loop is not implicit. # # You must setup a loop as I've done here with the 'while running?' # code, or setup your own loop. Otherwise your service will exit and # won't be especially useful. # # In this particular case, I've setup a loop to append a short message # and timestamp to the log file every 20 seconds. Remove the logging # when you are using this as a real service otherwise you logfile will # become large quickly. # # not sure what the (*args) means def service_main(*args) File.open(LOG_FILE, 'a'){ |f| f.puts "Service is running #{Time.now} with pid #{@server_pid}" } msg = 'application started at: ' + Time.now.to_s File.open(LOG_FILE, 'a'){ |f| f.puts msg f.puts "Args: " + args.join(',') } # While the daemon is running while running? if state == RUNNING sleep 20 # write constantly to log file while running for diagnostics only #msg = 'Service is running as of: ' + Time.now.to_s #File.open(LOG_FILE, 'a'){ |f| f.puts msg } else # PAUSED or IDLE sleep 0.5 end end # We've left the loop, the daemon is about to exit. File.open(LOG_FILE, 'a'){ |f| f.puts "STATE: #{state}" } msg = 'service_main left at: ' + Time.now.to_s File.open(LOG_FILE, 'a'){ |f| f.puts msg } end # This event triggers when the service receives a signal to stop. I've # added an explicit "exit!" here to ensure that the Ruby interpreter exits # properly. I use 'exit!' instead of 'exit' because otherwise Ruby will # raise a SystemExitError, which I don't want. # def service_stop msg = 'Received stop signal at: ' + Time.now.to_s File.open(LOG_FILE, 'a'){ |f| f.puts msg } pid_file = 'tmp/pids/server.pid' File.open(LOG_FILE, 'a'){ |f| f.puts "Stopping server thread #{Time.now.to_s} with pid #{@server_pid}" } system "taskkill /PID #{@server_pid} /T /F" Process.waitall File.open(LOG_FILE, 'a'){ |f| f.puts "Service stopped #{Time.now.to_s}" } File.file?(pid_file) && File.delete(pid_file) # exit! - what is this exit for? there was a reason, this seems to cause a bad exit with redmine but might be needed for other scripts end # This event triggers when the service receives a signal to pause. # def service_pause msg = 'Received pause signal at: ' + Time.now.to_s File.open(LOG_FILE, 'a'){ |f| f.puts msg } end # This event triggers when the service receives a signal to resume # from a paused state. # def service_resume msg = 'Received resume signal at: ' + Time.now.to_s File.open(LOG_FILE, 'a'){ |f| f.puts msg } end end # Create an instance of the Daemon and put it into a loop. I borrowed the # method name 'mainloop' from Tk, btw. # RedmineDaemon.mainloop #--------------------------------------------------------------------------- # Service Failure Logging #--------------------------------------------------------------------------- rescue Exception => err File.open(LOG_FILE, 'a'){ |fh| fh.puts 'Daemon failure: ' + err + '\n'} # this one line is from the 1 page script based on demo File.open(LOG_FILE,'a+'){ |f| f.puts " ***Daemon failure #{Time.now.to_s} exception=#{err.inspect}\n#{err.backtrace.join($/)}" } raise end
Notes
- the ctl file, once run has nothing to do with the daemon. It is just a configurator., the daemon is how indows interacts with ruby
- this script is written for Redmine 2.x but needs to be slightly amended to run Redmine 3.x . If you dont make the following change, the redmine service will fail to run and you will get the following error in the redmine-service.log file.
script/rails no longer exists, please use bin/rails instead.
To fix this you basically need to make the change as told in this error. You will see in the redmine-service.rb i have added Redmine 3.x versions, the lines you need to change from Redmine 2.x to 3.x are line 30 - line 36, the rest should be obvious.
Making Xampp a Dependency for the Redmine Service
If you are using xampp as the donour for the MySQL service you must make sure that this is running when the Redmine service is started otherwise it will fail and not start. To fix this you can make the xampp MySQL (and Apache if required) service as a dependency which means that when you start your redmine service it will start these dependant services first to make sur ethey are running.
Currently the scripts above are not enabled to call Xampp Apache and MySQL services as dependants, the code is there though. There are a couple of steps required to get this working if you want, otherwise you must manually start at least the MySQL service or already have it runnign before you start the redmine service
This feature requires 2 things to be done
- Change Xampp Apache and MySQL Service names (Optional)
- Edit the Redmine Service Script (we will be using 'My Complex Script')
NB:
- When the redmine service starts either the Xampp Apache or MySQL then you cannot stop and start these services through the xampp control panel, it just doesnt work and perhaps will get fixed in later versions. These reason is that windows knows that redmine started these services and it should be the redmine service that should stop them which it does when you stop and start it.
- If you go into windows and stop and start the Apache or MySQL service via services.msc windows is intelligent and knows the redmine service started these services so propmpt you that it will also stop the redmine service if you continue which it will close correctely.
- If the Apache and MySQL services are already started when you start the redmine service, they will not be classed as dependendant services and can be stoppped and started throught the xampp control panel
- I find it useful just to run only the MySQL service as a dependant when playing with the httpd.conf file so i can easily stop and start the apache server in xampp.
- Redmine only require the requires the MySQL service to be running.
Change Xampp Service Names
If you want to run more than 1 Xampp installation, or even if you dont, i recommend that you should change the default service name for the Xampp Apache and MySQL services on you Developer Xampp instance. The reason for this is that if like me you use Xampp for developing websites on your Windows PC, the Xampp installationscheck by service name, to see if the Apache and MySQL services are running. This means that if you setup your Developer site with the default service names, when you then open up another instance of Xampp it will think that it is running as a service even if you have not installed that instance as a service.
So by giving different names to these services we will be using for the redmine development xampp it can function independantly to any other xampp instances. This how most people would expect this to work. I also want this seperate installation of xampp because when i am poking around with code or messing databases for my regular web development i do not risk my development enviroment.
Changing the service names is optionals for those budding coders but i definately still recommend it for the reasons outlined above)
Instructions
To change the service names of Apache and MySQL is very easy and requires you to use the xampp control panel.
Apache Service
- Open Xampp control panel as an administrator
- Make sure the service is not running
- If the service has already been installed, uninstall the service
- click config (top right)
- click 'Service and Port Settings'
- click 'Apache' Tab
- change the service name
Apache2.4 ----> Developer-Apache2.4 - Install the service
- Done
MySQL Service
- Open Xampp control panel as an administrator
- Make sure the service is not running
- If the service has already been installed, uninstall the service
- Click config (top right)
- Click 'Service and Port Settings'
- Click 'MySQL' tab
- Change the service name
mysql ----> Developer-MySQL - Install the service
- Done
Edit the Redmine Service Script
This stage is also an easy one and involves editing the redmine_service_ctl.rb from 'My Complex Script' .
- Open up a command prompt as an administrator
- Navigate to you redmine root directory (should be D:\Documents\developer\RubyRoot\redmine )
- If you have installed 'My Complex Script' you need to uninstalled it, run the following command
ruby redmine_service_ctl.rb uninstall - If you have not installed 'My Complex Script' you need to create the 2 files redmine_service_ctl.rb and redmine_service.rb in your redmine root folder using the appropriate code from above
- Open the file redmine_service_ctl.rb in a text editor
- Look at line 88 - 89 and edit the file as follows:
:dependencies => nil, #:dependencies => ['Developer-Apache2.4','Developer-MySQL'],
You can see that there is a declaration of no dependencies. The line below it defines some depnedecies but is remmed out. Change the lines around so the service has dependencies. The new code should look like the code below, basically you have just changed the poistion of the Hash '#'
#:dependencies => nil, :dependencies => ['Developer-Apache2.4','Developer-MySQL'],
As you can see the service names match those i set earler but can be anything as long as they match the appropriate service.
- Save the file
- Install the redmine service via the command line now that it has dependencies configured. You should still have the command line open in your redmine root directory and running as an administrator
ruby redmine_service_ctl.rb install - Done
Now start the redmine service and you will find it will start the Xampp apache and MySQL Services automatically.
Redmine as a Windows Service Final Thoughts
This is a robust way of having redmine running on your Windows PC and once configured you can practically forget about it and just use Redmine for what you wanted to use it for in the first place, software development. There are no more settings to do, you are ready to rock and roll.