Hi! ... Thanx for such a great (and at least secure ;-) ) thing! I just wanted to ask if you are working on lighttpd-support, because lighttpd is very fast and good configurable... If you haven't started such a thing yet, I did it (only poorly, but effective...) It's quite easy but effective: - I made a PHP-Script to query my ispconfig-vhosts from mysql and return lighttpd configuration directives - I added the script to my lighty-config (include_shell "/root/ispconfig/patchwork/lighttpd_vhosts.php") And adapted the config to run under my webserver-user (www-data:www-data) ... Basically, that's it... I currently leave ispconfig and it's components untouched, but i would need to write some stuff that makes makes me .htaccess-files out of the "custom apache parameter" option... But that's not my no1 priority right now... It would be pretty nice if you would offer something like this built-in, because it is unbeleavable easy, and ispconfig would then support a living alternative to the big big apache... ;-)
That sounds interesting. Maybe you can provide my with you code by email to dev [at] ispconfig [dot] org and I will have a look how we can integrate it in the ISPConfig dev branch.
Nice! ... I'll make a prototype-setup (because my testserver is currently very wasted) and cleanup the code a bit... You'll get the code tonight (CET ;-) ) via mail...
Soooo... This is, how to do it: You need the following Script, the location doesn't matter... Currently it is not very advanced but it longs to run ispconfig with lighttpd: //////// BEGIN /root/ispconfig/custom/lighttpd.conf.php Code: #!/usr/bin/php -q <? $go_info["server"]["db_host"] = "localhost"; $go_info["server"]["db_name"] = "db_ispconfig"; $go_info["server"]["db_user"] = "root"; $go_info["server"]["db_password"] = "12345"; $go_info["server"]["db_type"] = "mysql"; mysql_pconnect($go_info["server"]["db_host"],$go_info["server"]["db_user"],$go_info["server"]["db_password"]); mysql_select_db($go_info["server"]["db_name"]); list($shost,$sdomain,$docroot,$user,$group,$log,$sname)=mysql_fetch_array(mysql_query("select server_host,server_domain,server_path_httpd_root,server_httpd_user,server_httpd_group,server_path_httpd_log,dist_httpd_daemon from isp_server limit 1")); if($shost)$sdomain="$shost.$sdomain"; echo "server.name=\"$sdomain\"\n"; echo "server.tag=\"ispconfig/lighttpd@$sdomain\"\n"; echo "server.username=\"$user\"\n"; echo "server.groupname=\"$group\"\n"; echo "server.document-root=\"$docroot/sharedip\"\n"; echo "accesslog.filename=\"$log\"\n"; $db_res=mysql_query("select doc_id,web_host,web_domain,web_cgi,optionen_directory_index from isp_isp_web"); $yr=date("Y"); $mn=date("m"); echo "\n\n########## VHOSTS ########\n\n"; /* I should assign the additional domains from isp_isp_domain here as well, but right now I don't know how they are assigned... ;-) */ while(list($id,$host,$domain,$cgi,$dirindex)=mysql_fetch_array($db_res)) { $vhlist[$domain]=array("id"=>$id,"dirlist"=>true,"cgi"=>$cgi); if($host) $vhlist["$host.$domain"]=array("id"=>$id,"dirlist"=>true,"cgi"=>$cgi); } reset($vhlist); while(list($host,$parm)=each($vhlist)) { echo "\$HTTP[\"host\"]==\"$host\" {\n"; echo "\tserver.name=\"$host\"\n"; echo "\tserver.document-root=\"$docroot/web$parm[id]/web\"\n"; echo "\t#accesslog.filename=\"/var/log/lighttpd/web$parm[id]-access.log\"\n"; echo "\taccesslog.filename=\"$docroot/web$parm[id]/log/$yr/$mn/web.log\"\n"; echo "\tserver.dir-listing=\"".(($parm["dirlist"])?"enable":"disable")."\"\n"; if($parm["cgi"]) echo "\tcgi.assign=(\n\t\t\".pl\"=>\"/usr/bin/perl\",\n\t\t\".py\"=>\"/usr/bin/python\",\n\t)\n"; echo "}\n\n"; } ?> //////// END /root/ispconfig/custom/lighttpd.conf.php You can run it directly and see it's output - these are standard lighttpd configuration directives. Now create a corresponding lighttpd configuration: //////// BEGIN /etc/lighttpd/lighttpd.conf Code: ############## Module Prefs ################ server.modules=("mod_access","mod_cgi","mod_accesslog","mod_fastcgi") ############### Generic Preferences ############# server.errorlog="/var/log/lighttpd/error.log" server.pid-file="/var/run/lighttpd.pid" #accesslog.filename="/var/log/lighttpd/access.log" index-file.names=("index.html","index.htm") url.access-deny=("~",".inc") server.event-handler="linux-sysepoll" #You can set this to port 9999 to run lighttpd besides apache2 #server.port=9999 server.port=80 include_shell "/usr/share/lighttpd/create-mime.assign.pl" ############# Basic Dirlist-Settings ################ server.dir-listing="enable" dir-listing.encoding="iso-8859-15" dir-listing.hide-dotfiles="enable" #dir-listing.external-css="/dir.css" ############# PHP-Fastcgi-Stuff ################ index-file.names+=("index.php") fastcgi.server=( ".php"=>( "localhost"=>( "bin-path"=>"/usr/bin/php5-cgi", "socket"=>"/tmp/php5-socket", "max-procs"=>2, "bin-environment"=>( "PHP_FCGI_CHILDREN"=>"1", "PHP_FCGI_MAX_REQUESTS"=>"10000", ), "bin-copy-environment"=>( "PATH", "SHELL", "USER", ), "broken-scriptfilename"=>"enable" ) ) ) ############# And now, our VHOST-Handling ################ include_shell "/root/ispconfig/custom/lighttpd.conf.php" //////// END /etc/lighttpd/lighttpd.conf This expects debian/ubuntu style lighttpd-package, where there is a mime-script at /usr/share/lighttpd/create-mime.assign.pl ... you can comment the line and put the mime-handling from the example-config in it if you don't want this. Maybe you have to adapt the fastcgi-configuration to your needs, for example if your php-cgi fastcgi enabled binary is not at /usr/bin/php5-cgi ... Also, this is my lightweight configuration example (only a few fcgi-processes) You can create the entire lighttpd-config this way from MySQL-Informations, they will refresh every time you reload lighty... So it is quite easy to switch from apache2 to lighty without making major changes to existing apache2-configs... As you can see, while I don't know much about ISPCONFIG-Internals, my script is poorly using it's features, I guess you can make one much better in five minutes or so ;-) Have Fun! Martin
WOW... It is possible to put the fastcgi.server stuff into the "virtual hosts", using lighty's execwrap to gain maximum security!! At least I can have the suexec-effect for php-scripts... I know this is possible with apache2-fastcgi+suexec as well, but I never got this running well... I think this is a nice solution... Maybe we can make a stable implementation out of this, that could be really usefull (espacially thinking of the latest php, ... bugs and possible security breaches by insecure user scripts)
Update I overworked it a bit... And got it now running on one of my smaller servers (runs pretty stable ) lighttpd.conf: Code: include_shell "/usr/share/lighttpd/create-mime.assign.pl" include_shell "/root/ispconfig/scripts/lighttpd.conf.php" /root/ispconfig/scripts/lighttpd.conf.php: Code: #!/root/ispconfig/php/php -q <? $go_info["server"]["db_host"] = "localhost"; $go_info["server"]["db_name"] = "db_ispconfig"; $go_info["server"]["db_user"] = "ispconfig_root"; $go_info["server"]["db_password"] = "12345"; $go_info["server"]["db_type"] = "mysql"; mysql_connect($go_info["server"]["db_host"], $go_info["server"]["db_user"], $go_info["server"]["db_password"]) or die("Could not connect to MySQL server!"); mysql_select_db($go_info["server"]["db_name"]); $year=date("Y"); $month=date("m"); $prefix_web="web"; $db_res=mysql_query("select isp_isp_web.doc_id,isp_isp_domain.domain_host,isp_isp_domain.domain_domain from isp_isp_domain,isp_isp_web,isp_dep where isp_dep.parent_doc_id=isp_isp_web.doc_id and isp_dep.child_doc_id=isp_isp_domain.doc_id and isp_dep.parent_doctype_id=isp_isp_web.doctype_id and isp_dep.child_doctype_id=isp_isp_domain.doctype_id"); while(list($id,$hs,$dm)=mysql_fetch_array($db_res))$ahosts[$id][]=array($hs,$dm); list($shost,$sdomain,$docroot,$user,$group,$log,$sname)=mysql_fetch_array(mysql_query("select server_host,server_domain,server_path_httpd_root,server_httpd_user,server_httpd_group,server_path_httpd_log,dist_httpd_daemon from isp_server limit 1")); if($shost)$sdomain="$shost.$sdomain"; echo "\n\n## Static Preferences ##\n\n"; echo "server.modules=(\"mod_access\",\"mod_cgi\",\"mod_accesslog\",\"mod_fastcgi\",\"mod_ssi\",\"mod_alias\")\n"; echo "server.errorlog=\"/var/log/lighttpd/error.log\"\n"; echo "server.pid-file=\"/var/run/lighttpd.pid\"\n"; echo "index-file.names=(\"index.html\",\"index.htm\")\n"; echo "url.access-deny=(\"~\",\".inc\")\n"; echo "server.event-handler=\"linux-sysepoll\"\n"; echo "\n\n## Dynamic Preferences ##\n\n"; echo "server.name=\"$sdomain\"\n"; echo "server.tag=\"ispconfig/lighttpd@$sdomain\"\n"; echo "server.username=\"$user\"\n"; echo "server.groupname=\"$group\"\n"; echo "server.document-root=\"$docroot/sharedip\"\n"; echo "accesslog.filename=\"$log\"\n"; //echo "#accesslog.filename=\"/var/log/lighttpd/access.log\"\n"; system("chown $user:$group $log"); echo "\n\n## Global Dirlist-Settings ##\n\n"; echo "server.dir-listing=\"enable\"\n"; echo "dir-listing.encoding=\"iso-8859-15\"\n"; echo "dir-listing.hide-dotfiles=\"enable\"\n"; echo "#dir-listing.external-css=\"/dir.css\"\n"; $db_res=mysql_query("select * from isp_isp_web"); echo "\n\n## Dynamic VHOSTS ##\n\n"; while($qline=mysql_fetch_array($db_res)) { $parlist=array ( "id"=>$qline["doc_id"], "dirlist"=>true, "cgi"=>$qline["web_cgi"], "php"=>$qline["web_php"], "safemode"=>$qline["web_php_safe_mode"], "ssi"=>$qline["web_ssi"], "error"=>$qline["web_individual_error_pages"], ); $vhlist[$qline["web_domain"]]=$parlist; if($qline["web_host"]&&$qline["web_host"]!="NULL") $vhlist[$qline["web_host"].".".$qline["web_domain"]]=$parlist; if(is_array($ahosts[$qline["doc_id"]])) { reset($ahosts[$qline["doc_id"]]); while(list(,list($hs,$dm))=each($ahosts[$qline["doc_id"]])) { if(!$vhlist[$dm])$vhlist[$dm]=$parlist; if($hs&&$hs!="NULL"&&!$vhlist["$hs.$dm"])$vhlist["$hs.$dm"]=$parlist; } } } reset($vhlist); while(list($host,$parm)=each($vhlist)) { if(!is_dir("$docroot/$prefix_web$parm[id]/log/$year/$month"))system("mkdir -p $docroot/$prefix_web$parm[id]/log/$year/$month"); touch("$docroot/$prefix_web$parm[id]/log/$year/$month/web.log"); system("chown -R $user:$group $docroot/$prefix_web$parm[id]/log"); echo "\$HTTP[\"host\"]==\"$host\" {\n"; echo "\tserver.name=\"$host\"\n"; echo "\tserver.document-root=\"$docroot/$prefix_web$parm[id]/web\"\n"; echo "\taccesslog.filename=\"$docroot/$prefix_web$parm[id]/log/$year/$month/web.log\"\n"; echo "\tserver.errorlog=\"$docroot/$prefix_web$parm[id]/log/error.log\"\n"; echo "\tserver.dir-listing=\"".(($parm["dirlist"])?"enable":"disable")."\"\n"; if($parm["cgi"]) echo "\n\t## CGI-Settings ##\n\tcgi.assign=(\n\t\t\".pl\"=>\"/usr/bin/perl\",\n\t\t\".py\"=>\"/usr/bin/python\",\n\t)\n"; if($parm["php"]) { echo "\n\t## FastCGI-PHP-Settings ##\n"; echo "\tindex-file.names+=(\"index.php\")\n\n"; echo "\tfastcgi.server=(\n"; echo "\t \".php\"=>(\n"; echo "\t \"localhost\"=>(\n"; echo "\t \"bin-path\"=>\"/usr/bin/php5-cgi -c /etc/php5/cgi/php".(($parm["safemode"])?"_safe":"").".ini\",\n"; echo "\t \"socket\"=>\"/tmp/php5-".(($parm["safemode"])?"safe-":"")."socket\",\n"; echo "\t \"max-procs\"=>4,\n"; echo "\t \"bin-environment\"=>( \n"; echo "\t \"PHP_FCGI_CHILDREN\"=>\"4\",\n"; echo "\t \"PHP_FCGI_MAX_REQUESTS\"=>\"10000\",\n"; echo "\t \"TMP\"=>\"$docroot/tmp\",\n"; echo "\t \"TEMP\"=>\"$docroot/tmp\",\n"; echo "\t ),\n"; echo "\t \"bin-copy-environment\"=>(\n"; echo "\t \"PATH\",\n"; echo "\t \"SHELL\",\n"; echo "\t \"USER\",\n"; echo "\t ),\n"; echo "\t \"broken-scriptfilename\"=>\"enable\"\n"; echo "\t )\n"; echo "\t )\n"; echo "\t)\n"; } if($parm["ssi"]) { echo "\n\t## SSI-Settings ##\n\tssi.extension=(\".shtml\")\n"; } echo "\n\t## Error-Handling ##\n"; echo "\talias.url=(\"/error/\"=>\"$docroot/$prefix_web$parm[id]/web/error/\")\n"; if($parm["error"]) { /* ErrorDocument 400 /error/invalidSyntax.html ErrorDocument 401 /error/authorizationRequired.html ErrorDocument 403 /error/forbidden.html ErrorDocument 404 /error/fileNotFound.html ErrorDocument 405 /error/methodNotAllowed.html ErrorDocument 500 /error/internalServerError.html ErrorDocument 503 /error/overloaded.html AliasMatch ^/~([^/]+)(/(.*))? /var/www/web12/user/$1/web/$3 AliasMatch ^/users/([^/]+)(/(.*))? /var/www/web12/user/$1/web/$3 */ } echo "}\n\n"; } ?> It works pretty well and even sets the permissions on startup However, someday I should use the config.inc stuff to connect to mysql... And: You should update the apache_reload-function to restart lighttpd instead of apache, I've done it, but I forgot where... But this solution is VERY stable... You can adapt the settings below "Static Preferences" with values from ispconfig... Yes, and I made php a bit more secure by creating php_safe.ini für safemode, set open_basedir to /var/www there and as tempdir /var/www/tmp ... However, it would be absolutely easy to use the suexec-stuff and improve this even more, maybe I'll do this someday ;-) Have Fun!
Gentleman, It would be great if ISP would fully support lighty. Can anyone provide me with a complete walk-through please a bit confusing... on PSIplus's post, btw, great post man Hope someone can help
Step-by-Step-instruction Okay... My step-by-step instruction... But one thing: I use Debian/Ubuntu-Style Lighty (ready to use with the mime-type-scripts), and I don't know how SuSE/Fedora/etc. packages look like... However Install ISPconfig with Apache2 (this is nessasary, while ISPconfig doesn't support lighttpd by itself)... After the installation, stop apache2 and disable it (Ubuntu/Debian: Edit /etc/default/apache2, there is an option) Install LighttpD, in debian/ubuntu: apt-get install lighttpd ... You can build it from source, but you'll need the mime-script at /usr/share/lighttpd/create-mime.assign.pl or replace the include-line in lighty-config later by a default mime-handling ... After the installation, make sure lighty is stopped: /etc/init.d/lighttpd stop Make sure PHP5 with fastcgi is installed and at /usr/bin/php5-cgi ... in debian/ubuntu you can usually do this by apt-get install php5-cgi ... Then generate a safe-mode config for php at /etc/php5/cgi ... just copy the php.ini there to php_safe.ini, and enable the safemode-option in there. But for now this is not elementary ;-) ... Make sure there is a tmp-directory for your webscripts... It's usually at /var/www/ ... so make: mkdir /var/www/tmp ... then chown it for the webserver: chown www-data:www-data /var/www/tmp ... I usually change then the session-directory in php.ini to this location as well, but this is non-vital. Use my files from the last posting. Put lighttpd.conf to /etc/lighttpd and the script (lighttpd.conf.php) to /root/ispconfig/scripts/ ... Make the script executeable: chmod 755 /root/ispconfig/scripts/lighttpd.conf.php Then, you can fine-tune the lighty-config if you want... Some of the options are in the php-script as well, but for now you can leave it as-is... Modify the lighttpd.conf.php to fit your database-configuration (username/password/database) ... For now this is nessasary ;-) Then, create some website in ispconfig, so that we can test the configfile-generation Run the config-script, and check it's output: /root/ispconfig/scripts/lighttpd.conf.php ... No error-Messages? Good... That means, that the config-generater works well. Then you can test lighty by running as root: lighttpd -D -f /etc/lighttpd/lighttpd.conf ... It should start without errormessages and you should now reach the prevously created host. Done. This way you can easily upgrade existing installations. You can stop the lighty with [CTRL]+[C] and then start it normally by /etc/init.d/lighttpd start Now you have to modify the ispconfig-script for apache-reboot... Edit /root/ispconfig/scripts/lib/config.lib.php ... Arround line 2374 (near the end) is the function: "function apache_reload(){" ... Rename the function, so that the line looks like: "function apache_reload_off(){" ... Over the function, put this: Code: function apache_reload() { exec("/etc/init.d/lighttpd stop"); exec("/etc/init.d/lighttpd start"); } ... It's dirty, but it works well ;-) ... Don't use "restart" or "reload", while this doesn't work well in most distributions... I'll send a better version of the script to the ubuntu people soon, but for now this is one good way... Now, everything should work well, even if ispconfig still "believes" that it's erving for apache2 ;-) That's the way I did it, and how it's running at my testserver, wich currently hosts for example this page: pb.exw.at ... Works stable, but needs much more integration into ispconfig... Please tell me your results ;-) Have Fun!
Thx a million man, unfortunately, I'm focusing on CentOS maybe it requires a little tweaking. Will try it on my VM image first
yes. yes Please register as ISPConfig developer to get SVN write access to the latest ISPConfig dev releases. http://server1.howtoforge.com/forums/showthread.php?t=135
Lighttpd Config Parser A while ago I started writing a config parser for Lighttpd in PHP. It's been a while since I've worked on it, and is read-only. But it could be a good base if you need a full parser. http://svn.jeremyh.net/r/LighttpdParser
Well, I am totally new to ISPConfig. I managed to install it, and also use your instructions for using lighttpd instead of apache. Everything seems ok so far, however I need to test things a lot more. Thanks for the useful info PSIplus!
wow. I'd love to see this in a more stable version, but I have to wait until edge comes out, make that upgrade and then I'll check back to see how far this project has proceeded...
@PSIplus can you give me a hand with a similar problem? I would like to manually compile and install lighttpd on my debian box, have it lsitening on a different port i.e. 88 and import the vhosts from apache. I plan on using mod_proxy on my apache2 so apache2 will stay the default webserver BUT have it forward static content to lighttpd (I have figured out the forwarding part, but need help with the compilation on debian (running 3.1) If this works out I'd like to also use lighttpd for ruby on rails can you help? I could open another thread? or you could send me a pm or whatever
Thanks for the guide.. but can someone please convert it to an easier-to-read format? It's really hard to read what the guide says, muchless properly do it. Thanks.
I'd love to see this too... Hey guys I'd love to see ISPConfig have built in handling for lighttpd. I would be willing to donate some money towards making this a reality. I also know of one other person that would do the same. If there are others here using Lighty perhaps we can all chip in?
PSIplus, thanks for the great script As lighttp does not recognize .htaccess files I ran into problems migrating to lighttp. I extended your script so it now has a (very) rudimentary support for htaccess. first I changed the modules section to include mod_auth and mod_rewrite Code: echo "server.modules=(\"mod_auth\",\"mod_access\",\"mod_cgi\",\"mod_accesslog\",\"mod_fastcgi\",\"mod_ssi\",\"mod_alias\",\"mod_rewrite\")\n"; then I added function calls to the end of the script Code: ... echo "\n\t## Error-Handling ##\n"; echo "\talias.url=(\"/error/\"=>\"$docroot/$prefix_web$parm[id]/web/error/\")\n"; if($parm["error"]) { /* ErrorDocument 400 /error/invalidSyntax.html ErrorDocument 401 /error/authorizationRequired.html ErrorDocument 403 /error/forbidden.html ErrorDocument 404 /error/fileNotFound.html ErrorDocument 405 /error/methodNotAllowed.html ErrorDocument 500 /error/internalServerError.html ErrorDocument 503 /error/overloaded.html AliasMatch ^/~([^/]+)(/(.*))? /var/www/web12/user/$1/web/$3 AliasMatch ^/users/([^/]+)(/(.*))? /var/www/web12/user/$1/web/$3 */ } // search for .htaccess files and prevent direct access echo "\n\turl.access-deny = ( \".htaccess\", \".htpasswd\")\n"; list($data, $rewdata) = recurse_htaccess("", "$docroot/$prefix_web$parm[id]/web"); echo $data; echo $rewdata; echo "}\n\n"; ... finally I added my new functions to the end of the script Code: function recurse_htaccess($curdir, $basedir) { $dir = opendir($basedir . $curdir); $data = ""; $rewdata = ""; while (false !== ($file = readdir($dir))) { if ($file != "." && $file != "..") { if(is_dir($basedir . $curdir . "/" . $file)) { list($ndata, $rdata) = recurse_htaccess($curdir . "/" . $file, $basedir); $data .= $ndata; $rewdata .= $rdata; } elseif($file == ".htaccess") { list($ndata, $rdata) = get_htaccess($curdir . "/" . $file, $basedir); $data .= $ndata; $rewdata .= $rdata; } } } return array($data, $rewdata); } function get_htaccess($file, $basedir) { $data = ""; $rewexp = array(); $fpath = $basedir . $file; $file = str_replace(".htaccess", "", $file); $fp = fopen($fpath, "r"); if(!$fp) return ""; if(!file_exists($fpath)) return ""; $lines = file($fpath); if(!is_array($lines) || count($lines) < 1) return ""; $match = false; $data = ""; $data .= "\t\$HTTP[\"url\"] =~ \"^$file\" {\n"; $data .= "\t\tauth.backend = \"htpasswd\"\n"; $rewbase = ""; $reqdata = "\"$file\" => (\n"; // method / realm / require... $first = true; foreach($lines as $line) { if(preg_match("'authtype\s+(\w+)'is", $line, $matches)) { $match = true; if(!$first) $reqdata .= ",\n"; $reqdata .= "\t\t\t\"method\" => \"" . strtolower(trim($matches[1])) . "\""; } elseif(preg_match("'authname\s+\"?([^\"]+)\"?'is", $line, $matches)) { $match = true; if(!$first) $reqdata .= ",\n"; $reqdata .= "\t\t\t\"realm\" => \"" . trim($matches[1]) . "\""; } elseif(preg_match("'require\s+\"?([^\"]+)\"?'is", $line, $matches)) { $match = true; if(!$first) $reqdata .= ",\n"; $reqdata .= "\t\t\t\"require\" => \"" . trim($matches[1]) . "\""; } elseif(preg_match("'authuserfile\s+\"?([^\"]+)\"?'is", $line, $matches)) { $match = true; if(trim($matches[1]) != "") $data .= "\t\tauth.backend.htpasswd.userfile = \"" . trim($matches[1]) . "\"\n"; } elseif(preg_match("'rewritebase\s+(\S+)'is", $line, $matches)) { $rewbase = trim($matches[1]); } elseif(preg_match("'rewriterule\s+(\S+)\s+(\S+)'is", $line, $matches)) { $srch = trim($matches[1]); $rewexp["$srch"] = trim($matches[2]); } $first = false; } $data .= "\t\tauth.require = ( "; $data .= $reqdata . ")\n\t\t)\n"; $data .= "\t}\n"; if($match == false) $data = ""; // reset it $rewdata = ""; if(count($rewexp) > 0) { $rewdata = "\n\turl.rewrite-once = ( "; $first = true; foreach($rewexp as $search => $replace) { if($first == false) $rewdata .= ","; if($rewbase != "") { $search = preg_replace("'^\^'", "^$rewbase", $search); } $rewdata .= "\n\t\t\"$search\" => \"$replace\""; $first = false; } $rewdata .= ")\n"; } return array($data, $rewdata); } Sorry for the missing code comments... But I had no time for these. As I said this is VERY basic .htaccess support... I managed to get all my .htaccess directory access limits running. My basic rewrite rules are working, too (no rewrite conditions). Host-based or file-based access limit in .htacess files does not yet work, maybe I'll get this to work later
I just started using this script, and discoverd two flaws: - it doesn't support wildcard domains, something I frequently use - the .htaccess patch is to slow on big sites (and i mean BIG, over 100k folder really kills the perfornance) Below is a patched version that adds wildcard support. The .htaccess patch is included but disabled I also added a few extra lighttpd options; especially a port parameter, so you can run lighttpt next to your apache2 to test the performance/validy of this script. (had to rename file to .txt for the forum to accept it)