Categories
- Databases (12)
- MySQL (8)
- Oracle (4)
- PostgreSQL (3)
- SQL Server (3)
- SQLite (1)
- General Info (8)
- Hardware (7)
- Hosted 64-bit Software (22)
- Lightning Plug-In (3)
- Xine RPMs (20)
- Linux (22)
- Audio / Video (3)
- Internet Apps (11)
- Office Productivity (4)
- Printing (1)
- Red Hat / Fedora (3)
- Samba (1)
- White Box (3)
- Wine (5)
- Wireless Support (8)
- Programming (26)
- C# / .NET (4)
- Mono (2)
- C++ (1)
- JavaScript (1)
- PHP (9)
- SQL (3)
- PL/SQL (1)
- Web Services (1)
- WordPress (13)
- Plug-Ins (7)
- C# / .NET (4)
- Projects (1)
- Security (3)
- Web Servers (6)
- Windows Open Source (1)
- Databases (12)
Archives
- January 2012 (1)
- November 2011 (1)
- October 2011 (2)
- September 2011 (1)
- August 2011 (1)
- May 2011 (1)
- September 2010 (2)
- August 2010 (3)
- March 2010 (1)
- April 2009 (1)
- February 2009 (1)
- January 2009 (1)
- October 2008 (2)
- June 2008 (3)
- May 2008 (1)
- March 2008 (4)
- January 2008 (2)
- December 2007 (2)
- November 2007 (1)
- October 2007 (1)
- September 2007 (2)
- August 2007 (5)
- July 2007 (2)
- June 2007 (2)
- May 2007 (3)
- November 2005 (1)
- August 2005 (2)
- June 2005 (3)
- September 2004 (7)
- August 2004 (2)
- July 2004 (8)
- June 2004 (10)
Category Archive: Mono
Subcategories: No categories
Tech Blog 3.0 (aka “You win, PHP…”)
After a little over a year running on Tech Blog 2.0, you are now viewing version 3.0. Â For this version, we’ve returned to WordPress from BlogEngine. Â There are several issues that colluded to drive this change, most of which surrounded PHP and its crazy behavior. Â (Geeky details follow – skip to the paragraph starting with “Bottom line:” if you don’t want the geek stuff. Â I bolded it so it would be easy to spot.)
PHP’s recommended configuration is to run under Apache using the pre-fork multi-processing module (MPM). Â The advantage to this is that Apache does not have to spin off another process to handle each request; it handles it in the same thread. Â However, this means that each instance of the server must have all enabled modules loaded. Â This means that each instance of the server (AKA “thread”) is very large, so the number of threads run is lower (typically 5-15 in a server the size we’re on). Â Also, this means that each thread can only handle one request at a time; if you have 7 threads configured, each serving one of 7 requests, and an 8th request comes it, it has to wait for one to finish. Â If the requests are served quickly, this may not be a problem; however, the avalanche of request that follow the typical front-page mention on mega-blogs can easily overwhelm it.
To fix this problem, there is another MPM, this one called worker. Â In this scenario, there are spare thread waiting to fill requests, and these can spawn other threads to do further work if required. Â So, the Apache threads would realize that a request needs to be handled by PHP, and pass it off to that process to be completed. Â The Apache memory footprint is much smaller; it serves the images, scripts, and other static files, and passes off the requests that require heavy lifting. Â PHP, then, has a (FastCGI) process where it receives these requests, processes them, and returns the response to the caller. Â Because each of these threads only has to load the PHP requirements, they are smaller too, so you can have more threads processing at the same time; you just might survive that front-page mention! Â (This is the same technique applied by LightTPD and Nginx, two other servers I tried at various times.)
It is in this scenario where PHP fails to live up to its expectations. Â These PHP processes would simply stop responding, but the controller thinks they’re still there. Â The end result to the user is a site that just sits and waits for output that will never come. Â Eventually, they may receive a Gateway Timeout or Bad Gateway error. Â The problem is worse on slower sites, but even popular sites seemed to fall victim to this from time to time. Â This was also a problem whether PHP controlled its threads, or Apache controlled them.
The one thing that really perturbs me is instability. Â If something is broken, I can fix it; if it works, I can fix it ’til it’s broke. Â Â But something that works sometimes, and other times doesn’t, simply won’t fly. Â I was able to introduce some stability by restarting the server 4 times a day, but that’s a band-aid, not a long term solution. Â I was tired of fighting.
Bottom line: the configuration required for a stable server is in opposition to a lean-and-mean configuration. Â So, I installed the required Apache modules, and will continue to run my PHP-serving server at a configuration twice as large as it needs to be. Â I’ll eventually move the Mono (.NET) processes to another machine, where the fast configuration won’t stability problems.
But, PHP isn’t all. Â While I would still heartily recommend BlogEngine.NET to someone who was going to serve the blog from a Windows machine, but I had some issues getting upgrades to go smoothly under Mono. Â It also is optimized for fast serving, at the expense of RAM. Â At this point, that’s not the tradeoff we need.
Finally, with this update, the blog has received its first new theme. Â It’s a clean, clear theme that should serve the content well. Â Plus, the social media icons up in the corner are just too cool, IMO. Â I’ve also applied tags to all posts except the “My Linux Adventure” series, and this theme displays them. Â (Comments are not here now, but will be migrated shortly.)
So, there you have it. Â Enjoy!
Mono / FastCGI Startup Script
We’ve begun running Mono on some DJS Consulting servers to enable us to support the .NET environment, in addition to the PHP environment most of our other applications use. Â While Ubuntu has nice packages (and Badgerports even brings them up to the latest release), one thing that we were missing was a “conf.d”-type of configuration; my “/applications=” clause of the command was getting really, really long. Â We decided to see if we could create something similar to Apache / Nginx’s sites-available/sites-enabled paradigm, and we have succeeded!
To begin, you’ll need to create the directories /etc/mono/fcgi/apps-available and /etc/mono/fcgi/apps-enabled. Â These directories will hold files that will be used define applications. Â The intent of these directories is to put the actual files in apps-available, then symlink the ones that are enabled from apps-enabled. Â These files have no name restrictions, but do not put an extra newline character in them. Â The script will concatenate the contents of that file to create the MONO_FCGI_APPLICATIONS environment variable, which tells the server what applications exist. Â (The syntax is the same as that for the “/applications=” clause – [domain]:[URL path]:[filesystem path].) Â Here’s how the site you’re reading now is configured (from the file djs-consulting.com.techblog.conf)…
techblog.djs-consulting.com:/:/path/to/install/base/for/this/site
Finally, what brings it all together is a shell script. Â This should be named “monoserve” and placed in /etc/init.d. Â (This borrows heavily from this script, which we used until we wrote this one.) Â Note the group of variables surrounded by the “make changes here” notes – these are the values that are used in starting the server. Â They are at the top so that you can easily modify this for your own needs.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 | #!/bin/bash ### BEGIN INIT INFO # Provides: monoserve.sh # Required-Start: $local_fs $syslog $remote_fs # Required-Stop: $local_fs $syslog $remote_fs # Default-Start: 2 3 4 5 # Default-Stop: 0 1 6 # Short-Description: Start FastCGI Mono server with hosts ### END INIT INFO PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin DAEMON=/usr/bin/mono NAME=monoserver DESC=monoserver ## Begin -- MAKE CHANGES HERE -- PROGRAM=fastcgi-mono-server2 # The program which will be started ADDRESS=127.0.0.1 # The address on which the server will listen PORT=9001 # The port on which the server will listen USER=www-data # The user under which the process will run GROUP=$USER # The group under which the process will run ## End -- MAKE CHANGES HERE -- # Determine the environment MONOSERVER=$(which $PROGRAM) MONOSERVER_PID="" FCGI_CONFIG_DIR=/etc/mono/fcgi/apps-enabled # Start up the Mono server start_up() { get_pid if [ -z "$MONOSERVER_PID" ]; then echo "Configured Applications" echo "-----------------------" # Construct the application list if the configuration directory exists if [ -d $FCGI_CONFIG_DIR ]; then MONO_FCGI_APPLICATIONS="" for file in $( ls $FCGI_CONFIG_DIR ); do if [ "$MONO_FCGI_APPLICATIONS" != "" ]; then MONO_FCGI_APPLICATIONS=$MONO_FCGI_APPLICATIONS, fi MONO_FCGI_APPLICATIONS=$MONO_FCGI_APPLICATIONS`cat $FCGI_CONFIG_DIR/$file` done export MONO_FCGI_APPLICATIONS echo -e ${MONO_FCGI_APPLICATIONS//,/"\n"} else echo "None (config directory $FCGI_CONFIG_DIR not found)" fi echo # Start the server start-stop-daemon -S -c $USER:$GROUP -x $MONOSERVER -- /socket=tcp:$ADDRESS:$PORT & echo "Mono FastCGI Server $PROGRAM started as $USER on $ADDRESS:$PORT" else echo "Mono FastCGI Server is already running - PID $MONOSERVER_PID" fi } # Shut down the Mono server shut_down() { get_pid if [ -n "$MONOSERVER_PID" ]; then kill $MONOSERVER_PID echo "Mono FastCGI Server stopped" else echo "Mono FastCGI Server is not running" fi } # Refresh the PID get_pid() { MONOSERVER_PID=$(ps auxf | grep $PROGRAM.exe | grep -v grep | awk '{print $2}') } case "$1" in start) start_up ;; stop) shut_down ;; restart|force-reload) shut_down start_up ;; status) get_pid if [ -z "$MONOSERVER_PID" ]; then echo "Mono FastCGI Server is not running" else echo "Mono FastCGI Server is running - PID $MONOSERVER_PID" fi ;; *) echo "Usage: monoserve (start|stop|restart|force-reload|status)" ;; esac exit 0 |
This needs to be owned by root and be executable (“chmod +x monoserve”). Â You can use “update-rc.d monoserve defaults” to set this to start at boot.
Tagged badgerports, config, fastcgi, mono, script