The content of this blog is archived. No comments may be made, and no further content will be published. Thank you for your ongoing readership! -Ryan
| « Photos from the Freezepop Boston Journey | Real Time Photo: The nicest-looking cloud I've seen in awhile » |
Asterisk and FreePBX under Ubuntu 9.04 and Lighttpd on a Linode VPS
Are you looking for tips on doing this with Ubuntu 9.10 (Karmic)? The procedure is different! See the updated blog post here.
FreePBX is a popular front end for the Asterisk PBX system written in PHP. It adapts the complex yet very flexible Asterisk configuration system into something easier to use (yet still very extensible). When I worked for a business-class VoIP provider back in the day, we used FreePBX (and its predecessor, AMP) for most of our customer-premise PBX servers. I do like using FreePBX to configure my Asterisk system. However, I can't justify an entire server for Asterisk, so I need it to coexist with a number of other applications. What I can justify is a VPS with relatively little memory, so some tuning is required.
Rationale
The usual installation instructions assume the use of CentOS, Apache and mod_php for the stack. There are a few downsides to this configuration....
Since mod_php runs the PHP interpreter "within" Apache, it is restricted to running PHP code with Apache's permissions. For the purposes of FreePBX, which needs to edit configuration files owned by the "asterisk" user, this means setting Apache to run as "asterisk." Not an ideal configuration from a security standpoint, especially when the server is not dedicated to Asterisk. The PHP folks strongly recommend that Apache use the prefork MPM with mod_php due to threading concerns. This is not a big deal for a dedicated Asterisk/FreePBX server, but if you're sharing it with a web server that might have popularity and limited memory, this can be a problem under high load. For this reason, I use lighttpd and PHP via FastCGI to service dynamic PHP content. This allows the web server to run threaded while PHP does its own thing, running under more specific uids. I've also found the availability of software for CentOS to be lacking, so I've standardized on Ubuntu to avoid straying from the repositories as much as possible. As of this writing, I'm using Ubuntu 8.04 LTS on servers and Ubuntu 9.04 on desktops, although I am using 9.04 for this example. So, time to get FreePBX operating properly in an entirely foreign environment!The setup
The following was used as a base for this installation:- Server: Linode 360 Xen-based virtual private server
- Distribution: Ubuntu 9.04, 32-bit
The steps
I'm starting from the beginning, as I am doing this in a testbed. You can probably skip some steps if you already have a working system. Additionally, you might want to browse http://library.linode.com/ for more general advice on deploying, securing, and configuring a general purpose server.Prepare the system
I used Linode's Distribution Wizard to deploy a barebones Ubuntu 9.04 image using the defaults. First, I log in and do my normal Linux prep:Code:
# vi /etc/apt/sources.list | |
[uncomment to enable the universe repositories] | |
# apt-get update | |
[output deleted] | |
Fetched 2025kB in 2s (680kB/s) | |
Reading package lists... Done | |
# apt-get install language-pack-en | |
[to clear locales errors] | |
# apt-get upgrade | |
# adduser rtucker | |
Adding user `rtucker' ... | |
[dialogue deleted] | |
# echo "rtucker ALL=(ALL) ALL" >> /etc/sudoers | |
| |
(log back in as rtucker) | |
| |
$ sudo vi /etc/ssh/sshd_config | |
[edit to set PermitRootLogin no | |
$ sudo /etc/init.d/ssh restart | |
$ mkdir -m 700 .ssh | |
$ cat > .ssh/authorized_keys | |
[paste ssh public key here, followed by ctrl-D] | |
| |
(log back in and make sure it uses the key!) |
OPTIONAL: Configure the system to use Ubuntu's stock kernel
To make Asterisk's MeetMe subsystem happy, one needs the ztdummy kernel module to provide timing. This is optional, and can be done with the stock Linode kernels, but you can run your distribution's stock kernel via PV-GRUB and thus "do what needs doing" without compiling.Code:
$ sudo apt-get install linux-image-server grub | |
[output deleted] | |
$ sudo mkdir /boot/grub | |
$ sudo update-grub | |
[dialogue deleted... yes, you want it to generate menu.lst for you] | |
[yeah, it'll complain about a non-Xen kernel. See below.] |
exec /sbin/getty 38400 tty1to:
exec /sbin/getty 38400 hvc0In Linode's dashboard, click on your configuration profile and change the kernel to pv-grub-x86_32. Save it, send a reboot, and watch the fireworks via the lish console. Getting an error on boot like "close blk: backend at ..."? See comment #3 from Quinn Ebert, below.
Installing Asterisk
You can download and install Asterisk from source, but if you're a wimp like me, Ubuntu's packages work just fine:Code:
$ sudo apt-get install asterisk asterisk-config asterisk-doc asterisk-mp3 asterisk-mysql asterisk-sounds-main asterisk-sounds-extra |
Code:
$ sudo apt-get install zaptel zaptel-source | |
$ sudo module-assistant update | |
$ sudo module-assistant auto-install zaptel | |
$ sudo modprobe ztdummy |
Code:
ztdummy.c: In function 'ztdummy_hr_int': | |
ztdummy.c:203: error: 'struct hrtimer' has no member named 'expires' |
Code:
$ sudo apt-get install wget | |
$ wget https://launchpad.net/... | |
$ sudo dpkg -i zaptel*dajhorn*.deb | |
$ sudo module-assistant auto-install zaptel | |
$ sudo modprobe ztdummy | |
$ lsmod | |
[holy crap, there's ztdummy] |
Time for a Courtesy Reboot
Alrighty, you've installed Asterisk and Zaptel, it's probably time to do a reboot to make sure everything comes up right.Code:
$ sudo reboot |
Installing lighttpd, PHP, MySQL, and FreePBX
It's time to install our web server, lighttpd, as well as the necessary muffins to execute PHP code. As mentioned above, we're using the FastCGI method to handle PHP requests. We'll also grab MySQL, and the necessary libraries to tie it all together. MySQL will want you to set a root password; remember what this is, for you will need it later on.Code:
$ sudo apt-get install lighttpd php5-cgi php-pear php-db php5-mysql mysql-server mysql-client |
Code:
$ sudo cp /etc/asterisk/modules.conf /etc/asterisk/modules.conf.original |
Code:
$ cd /usr/src | |
/usr/src$ sudo wget http://mirror.freepbx.org/freepbx-2.5.1.tar.gz | |
/usr/src$ sudo tar -zxf freepbx-2.5.1.tar.gz | |
/usr/src$ cd freepbx-2.5.1 |
Code:
/usr/src/freepbx-2.5.1$ sudo mysqladmin -p create asterisk | |
/usr/src/freepbx-2.5.1$ sudo mysqladmin -p create asteriskcdrdb | |
/usr/src/freepbx-2.5.1$ sudo mysql -p asterisk < SQL/newinstall.sql | |
/usr/src/freepbx-2.5.1$ sudo mysql -p asteriskcdrdb < SQL/cdr_mysql_table.sql | |
/usr/src/freepbx-2.5.1$ sudo mysql -p | |
mysql> GRANT ALL PRIVILEGES ON asteriskcdrdb.* TO asteriskuser@localhost IDENTIFIED BY 'secret'; | |
mysql> GRANT ALL PRIVILEGES ON asterisk.* TO asteriskuser@localhost IDENTIFIED BY 'secret'; | |
mysql> flush privileges; | |
mysql> \q |
Code:
/usr/src/freepbx-2.5.1$ sudo ./install_amp --username=asteriskuser --password=secret | |
[...] | |
Enter your USERNAME to connect to the 'asterisk' database: | |
[asteriskuser] (press enter here) | |
Enter your PASSWORD to connect to the 'asterisk' database: | |
[secret] (press enter here) | |
Enter the hostname of the 'asterisk' database: | |
[localhost] (press enter here) | |
Enter a USERNAME to connect to the Asterisk Manager interface: | |
[admin] (press enter here) | |
Enter a PASSWORD to connect to the Asterisk Manager interface: | |
[amp111] (set something for this password!) | |
Enter the path to use for your AMP web root: | |
[/var/www/html] /var/www/freepbx (a reasonable path) | |
Created /var/www/freepbx | |
Enter the IP ADDRESS or hostname used to access the AMP web-admin: | |
[x.xx.xx.xx] (put your real hostname/IP here) | |
Enter a PASSWORD to perform call transfers with the Flash Operator Panel: | |
[passw0rd] (press enter here) | |
Use simple Extensions [extensions] admin or separate Devices and Users [deviceanduser]? | |
[extensions] (press enter here) | |
Enter directory in which to store AMP executable scripts: | |
[/var/lib/asterisk/bin] (press enter here) | |
Created /var/lib/asterisk/bin | |
Enter directory in which to store super-user scripts: | |
[/usr/local/sbin] (press enter here) | |
| |
/etc/amportal.conf writtenAssuming new install, --install-moh | |
added to command line | |
OK | |
[... and away it goes!] | |
| |
Please update your modules and reload Asterisk by visiting http://... | |
| |
********************************************** | |
* Some Warning That Isn't Relevant Right Now * | |
********************************************** |
Code:
$ sudo apt-get install postfix | |
[Choose "Internet Site" unless you know you need something else.] | |
[Also go with the default for System Mail Name, usually.] |
Making it all work
Right now, FreePBX is installed and in control of Asterisk, Asterisk is installed and should be working, and lighttpd is there. However, we do need to do some more work to get the lighttpd/PHP/FreePBX chain working. Using the current version of lighttpd in its default configuration, it will spawn its own PHP handlers (see /etc/lighttpd/conf-available/10-fastcgi.conf to see what I mean). Unfortunately, it can only spawn children as www-data, its own username. This makes privilege separation difficult. To fix this, we're going to start our own php-cgi handlers with asterisk's username, and tell lighttpd to use them when requests come in for FreePBX. We'll do this by adding a line to rc.local and by creating a configuration module for lighttpd. To /etc/rc.local, I added (before the exit 0):Code:
echo -n "Starting FCGI handler for FreePBX... " | |
/usr/bin/spawn-fcgi -f /usr/bin/php-cgi -a 127.0.0.1 -p 4001 -C 2 -u asterisk -g asterisk | |
echo "done." |
Code:
server.modules += ( "mod_fastcgi", "mod_access" ) | |
| |
$HTTP["host"] == "your.http.hostname.here" { | |
# deny access to scary places | |
$HTTP["url"] =~ "^/freepbx/admin/modules/" { | |
url.access-deny = ("") | |
} | |
else $HTTP["url"] =~ "^/freepbx/" { | |
dir-listing.activate = "disable" | |
alias.url += ( "/freepbx/" => "/var/www/freepbx/" ) | |
fastcgi.server = ( | |
".php" => | |
( "freepbx" => ( | |
"host" => "127.0.0.1", | |
"port" => 4001 | |
))) | |
} | |
} |
Code:
$ cd /var/www/freepbx | |
/var/www/freepbx$ sudo find . -type d | sudo xargs chmod 755 | |
$ cd /usr/share/asterisk | |
/usr/share/asterisk$ sudo chgrp -R asterisk agi-bin | |
/usr/share/asterisk$ sudo chmod -R 770 agi-bin |
Code:
$ sudo lighty-enable-mod freepbx | |
Available modules: auth cgi fastcgi freepbx proxy rrdtool simple-vhost ssi ssl status userdir | |
Already enabled modules: | |
Enabling freepbx: ok | |
Run /etc/init.d/lighttpd force-reload to enable changes | |
$ sudo /etc/init.d/lighttpd force-reload | |
Syntax OK | |
* Stopping web server lighttpd [ OK ] | |
Syntax OK | |
* Starting web server lighttpd [ OK ] |
Code:
$ sudo cp /etc/asterisk/modules.conf /etc/asterisk/modules.conf.freepbx | |
$ sudo cp /etc/asterisk/modules.conf.original /etc/asterisk/modules.conf |
15 comments
In trying to "run through" your guide here, I've run into a bit of a problem (I am running on Linode, BTW)...
Once I get around to booting pvGrub with the Ubuntu-Server kernel, after taking a goodly amount of time to boot, things seem to "panic/hang" with the following output:
--LISH OUTPUT BELOW--
Press `ESC' to enter the menu... 0
Booting 'Ubuntu 9.04, kernel 2.6.28-14-server'
root (hd0)
Filesystem type is ext2fs, using whole disk
kernel /boot/vmlinuz-2.6.28-14-server root=/dev/xvda ro
initrd /boot/initrd.img-2.6.28-14-server
close blk: backend at [path erased]
close blk: backend at [path erased]
--LISH OUTPUT ABOVE--
...I'd like to admit right-off-the-bat that it's very possible I missed something in your instructions here (and on the various LinodeLibrary pages as-well), but, I'd love to get your input on what might be causing this one (also, bear in mind that I've obviously already googled around a bit on this one).
BTW, in closing, just like to say this is a great post -- For those of us who choose to do things a "bit differently" (I, for example, am running another FreePBX on CentOS, but not having a "great" experience with it), this kind of top-notch documentation is greatly enjoyed and appreciated, at least by me. ;)
Thanks for your Great Work!
--Quinn
I might recommend opening a ticket or stopping by #linode on irc.oftc.net to make sure there's not an obvious impediment... barring that, I could take a look at your menu.lst or post my (1.3GB) "known good" image somewhere.
Thanks for the kudos! I did use FreePBX+CentOS+Apache for awhile, but did a rebuild this spring and got the FreePBX+Ubuntu+Lighttpd combo going. The pv-grub part is new to me this week (I'm not even using it in production yet), but I'm amazed at how simple it turned out to be. The usual approach to getting ztdummy going involves grabbing the kernel source, half-compiling it, then compiling ztdummy against that, which is probably a little more difficult than it needs to be (especially when kernel upgrades occur).
I seem to have figured this out... Oddly enough, it appears that, of all things, using pvGRUB "hiddenmenu" seems to cause Lish to "hitch" and lock like this. I happened to realize this after I tried to hand-compile my own kernel, and it refused to boot (and thus gave me the opportunity to press ESC to return to the GRUB menu -- After pressing ENTER (on a bit of a "hunch") to try booting the "generic" kernel (which is 28-14-server, as-of-this-morning), it booted "just fine"... Seeing this behavior, I removed "hiddenmenu" from the GRUB menu.lst (again, on the same hunch from earlier), and voila, it now comes up "like it should."
...Just figured I'd pass along that bit of "oddness" ... Maybe if it's not the "Irish Luck" kicking-in in my case, it may help somebody else who might come upon the same behaviour in the future...
Again, thanks for the wonderful article, and for taking the time to reply to me on this. ;)
Thanks Again!
--Quinn
On Jul 29, Quinn Ebert wrote "Several BIG Issues with O&O’s New Defrag V11?".
Seem to have hit another ("last minute") bug in following your guide here:
After running through all of your instructions here, and doing what you so cleverly call the "courtesy reboot" (I love that, BTW, great term for it), seems /freepbx/admin gives a 403 error... A bit more delving into this issue (after enabling request-trace-debugging, and all that nice stuff) seems to indicate that this setup does *not* actually wind up using the asterisk user/group for the spawned FastCGI server (even when the "-u" and "-g" options are specified -- also, I even went to the extent of using the actual numerical id's for this user on my node, and still saw the same behavior...Other than that, though, looks like everything else (after I figured out the pvGrub issue) works just perfectly.
Any insight you could provide into this last "nagging issue" here? I'll be more than happy to provide any logs/etc that you may find useful.
Thanks Again!
--Quinn
On Jul 29, Quinn Ebert wrote "Several BIG Issues with O&O’s New Defrag V11?".
Curious on the -u and -g thing... it only works if the spawn-fcgi is called as root (I was a little unclear about that, so just making sure). What user is it being spawned as?
Thanks!
Not sure, but, if you can tell me how to find that out, I can tell you...
But, to give a bit more detail, I enabled the request-tracing feature for lighthttpd, and a bit of digging through error.log wasn't incredibly helpful, but, it seems you forgot to add in the lines for showing users how to enable mod_fastcgi (which is why 403's were appearing)... However, once I enabled fastcgi, and the PHP scripts started being rendered correctly, the admin pages would error-out (Fatal-error-style) with permissions-related errors trying to access the files under /etc/asterisk -- This leads me to the belief that fastcgi (either it, or lighthttpd itself) isn't switching users properly, as a few quick peeks at the permissions under /etc/asterisk reveals that all of the users and permissions are properly assigned (e.g. all of the files *are* assigned to user/group ownership of the "asterisk" user and group).
Any further ideas?
Thanks!
--Quinn
On Jul 29, Quinn Ebert wrote "Several BIG Issues with O&O’s New Defrag V11?".
Sorry for the "extra noise," but, a quick look at the "ps" man page gave me the "tip" I needed; Seems php-cgi after the "courtesy" reboot starts spawning under the "Debian-ish" standard "www-data" user. Any idea of why it might be "resorting" to this?
Thanks!
--Quinn
On Jul 29, Quinn Ebert wrote "Several BIG Issues with O&O’s New Defrag V11?".
In short, you need to:
1) Use spawn-fcgi as root to start the php-cgi handlers, and
2) Tell lighttpd to use it for FreePBX.
The first two bits in that section should do it... note that you might have to tweak the HTTP line (the third one in the 10-freepbx.conf) a little bit to match the URL you're accessing FreePBX with.
OK, my apologies, but, I'm obviously misunderstanding your verbiage here... As far as I can tell, I've already handled these (I have both the stuff for the custom "freepbx" module for lighthttpd, and the 3 lines I added to rc.local)... Something I missed, then?
Thanks,
Quinn
On Jul 29, Quinn Ebert wrote "Several BIG Issues with O&O’s New Defrag V11?".
OK...I figured out what I missed here... Just a bit of a "suggestion" for you here based on an observation... Regarding the portion to your users about editing line 3 of 10-freepbx.conf, I misread into how to edit it -- I'd entered the "linode-given" hostname there (which is what I understood I was supposed to do), but, me just being "the way I am," I somehow found it perplexing when I went through my "usual practice" of accessing a newly-provisioned server directly by IP (and, of course, the way things work with this config setup, that doesn't give *quite* the expected result through the "socketed" fastCGI setup)... So, that one just can be chalked up to "user error" -- not *really* an issue on the part of your guide (although, it could be beneficial to maybe note for your readers that line 3 should be edited "to include the hostname you'll be browsing to later for freePBX admin" or something like that.
Sorry again for the added trouble on your part, and, keep up the good work here...I know I (for one) certainly do appreciate it. ;)
Thanks Again!
--Quinn
On Jul 29, Quinn Ebert wrote "Several BIG Issues with O&O’s New Defrag V11?".
sudo mysql -p asterisk <SQL/cdr_mysql_table.sql
should be:
sudo mysql -p asteriskcdrdb <SQL/cdr_mysql_table.sql
That's what I used anyway. Thanks for your clear, well thought out, no BS instructions.
Thanks for the props... my goal was to go as far off the beaten path as I could, with the hope that individual pieces could be used in other, less-insane situations :-) Glad it worked for you with Apache!
Comments are closed for this post.