Monday, 11 August 2014

Compile Lighttpd with LibreSSL

As LibreSSL is gaining popularity you might want to switch your compiled Lighttpd version with one that uses LibreSSL for your https.

Tested on Debian Squeeze, but should work on Wheezy/Ubuntu in a similar way.

Prerequisites

$ sudo apt-get install make gcc libev-dev libpcre3-dev zlib1g-dev libbz2-dev gamin libgamin-dev liblua5.1-0-dev
$ wget \
http://download.lighttpd.net/lighttpd/releases-1.4.x/lighttpd-1.4.35.tar.gz \
http://ftp.openbsd.org/pub/OpenBSD/LibreSSL/libressl-2.0.5.tar.gz
$ tar xvfz libressl-2.0.5.tar.gz && tar xvfz lighttpd-1.4.35.tar.gz

Compile & Install LibreSSL

We are installing it in a non-standard path so it won't interfer with your existing openssl/libssl(-dev)

$ cd libressl-2.0.5
$ ./configure --prefix=/opt/libressl
$ make 
$ sudo make install

Verify the LibreSSL Installation

$ /opt/libressl/bin/openssl version
LibreSSL 2.0

Compile Lighttpd with LibreSSL

$ cd ../lighttpd-1.4.35
$ wget https://gist.github.com/lifeofguenter/7ef3fe9e089fcb24baed/raw/316108a350f69d622c17d0801cc429388cf36cef/lighttpd-libressl.patch
$ patch -p1 < lighttpd-libressl.patch 
$ ./configure \
--prefix=/usr \
--sysconfdir=/etc \
--localstatedir=/var \
--with-libev \
--with-pcre \
--with-zlib \
--with-bzip2 \
--with-fam \
--with-lua \
--with-openssl=/opt/libressl
$ make
$ sudo make install

Verify the Lighttpd Installation

$ lighttpd -v
lighttpd/1.4.35 (ssl) - a light and fast webserver
Build-Date: Aug 11 2014 12:54:04

Please have a look at the following URLs for further Documentation on configuring Lighttpd + SSL:

Wednesday, 6 August 2014

Parallel/Asynchronous DNS resolving in PHP

In PHP one key for a scalable and performant web application is parallelism, whenever and wherever possible, even if you use queues. The most popular usage of parallelism in PHP is probably curl_multi_*.
In this post I will show you how to do multiple DNS requests lightning fast with two different approaches / PHP extensions.

In both cases the DNS requests are done asynchronously, meaning even with multiple requests the whole process will only take as long as the longest request takes (in theory).

PHP's internal DNS functions rely on resolv.conf and in most cases it is not heavily optimized, defaulting to a rather long timeout of 5 seconds.
So even if you are only needing single DNS lookups both extensions might still be interesting as you can dynamically change the behavior of that, which what PHP is all about, or?


pecl-ares


pecl-ares offers PHP bindings for the c-ares library (affiliated with cURL).
I was happy that Michael Wallner (you might know him for pecl-http) offered help to revive the code, as it has not had a release since 4 years. So to get it running with the current c-ares version and a modern system, you should have a look at its git.
pecl-ares also allows the usage of callbacks which might be useful for certain scenarios.

Installation (assuming php-fpm)

$ sudo apt-get install libc-ares-dev php5-dev
$ git clone https://git.php.net/repository/pecl/networking/ares.git php-ares
$ cd php-ares
$ phpize
$ ./configure
$ make
$ sudo make install
$ sudo echo "extension=ares.so" > /etc/php5/mods-available/ares.ini
$ sudo php5enmod ares

Usage


It does not offer yet any documentation, but the source code is easy to understand, so anyways here is an example:

<?php

$ares = ares_init([
    'timeoutms' => 2000,
    'tries'     => 1,
    //'udp_port'  => 53,
    //'tcp_port'  => 53,
    'servers'   => ['8.8.8.8'],
    'flags'     => ARES_FLAG_NOALIASES|ARES_FLAG_NOSEARCH,
]);

$q = [];
$q[] = ares_query($ares, null, 'www.lifeofguenter.de', ARES_T_A);
$q[] = ares_query($ares, null, 'lifeofguenter.de', ARES_T_A);

do {
    $n = ares_fds($ares, $r, $w);
    ares_select($r, $w, 100);
    ares_process($ares, $r, $w);
} while ($n);

foreach ($q as $query) {
    var_dump(ares_result($query, $errno, $errstr));
}

ares_destroy($ares);
unset($ares);


php-rdns


php-rdns offers OOP PHP bindings for librdns (same guy behind rspamd) and uses libev for event looping. "We" recently developed it for a client of ours and released it as open source. It is highly simplified and some things might not yet be implemented or working correctly, but if you are interested we are always happy to see a pull request. Initial development was done by Alexander Solovets and later bug-fixing by Eduardo Silva (lead dev/founder of monkey webserver).

Installation (assuming php-fpm)


$ sudo apt-get install libev-dev php5-dev
$ wget https://github.com/weheartwebsites/php-rdns/releases/download/v0.1.1/rdns-0.1.1.tgz
$ tar xvfz rdns-0.1.1.tgz
$ cd rdns-0.1.1/
$ phpize
$ ./configure
$ make
$ sudo make install
$ sudo echo "extension=rdns.so" >> /etc/php5/mods-available/rdns.ini
$ sudo php5enmod rdns
$ /etc/init.d/php-fpm restart

Usage

(full  documentation on GitHub)

<?php

$rdns = new RDNS;
$rdns->addServer('8.8.8.8');

$rdns->addRequest('www.lifeofguenter.de', RDNS_A, 2);
$rdns->addRequest('lifeofguenter.de', RDNS_A, 2);
$replies = $rdns->getReplies();
ksort($replies);

var_dump($replies);
unset($rdns);

You might also be interested in ReactPHP or swoole, which are event-driven solutions to this problem.

Monday, 4 August 2014

The Rise and Fall of PHPclasses

I started playing around with PHP somewhere between 1999 and 2000 which does not necessarily make me a good PHP developer, but I have seen a lot of PHP History. One of them is PHPclasses, which existed way before GitHub, Packagist and all the Fanboying in the PHP community.

It was my go to destination for PHP libraries as I had a early dislike for PEAR (for no real reason) and there was no real alternative (except maybe SF). I even "contributed" a shitty class (SOCKS5 Client) in 2008 (did a modernization on GitHub), but even though PHPclasses was in my bookmarks (and I occasionally stumbled on it via Google) it was always very annoying to use:

  • forced registration to view source code
  • some great talented developers, but also a lot of low quality "libraries" (usually mixed up with hardcoded HTML)
  • nothing against advertisement, but the placement combined with the "layout" did not make it fun to browse
  • shitty layout was shitty back then (even then it felt like from the 80s), the recent relaunch still feels like from the 80s, but with more graphics
  • no repository
  • mainly something like "one author = one library" as opposed to "collaboration" which you will often find on GitHub
Today Phil Sturgeon, whom I had the pleasure to meet at the PHP mini conference in Cape Town this year (no idea who he was before that, but funny outgoing guy, and seems to know more about PHP programming than I do) started a wave that many of us developers were not saying out loud:

PHPclasses.org sucks!

The response on Twitter is huge, and you can most probably guess which answer was voted most.

Funny enough Manuel Lemos decided to chip in, turns out he sucks* as well. Very stubborn and failing to acknowledge feedback, he still insists that forcing user registration for viewing source code is the right thing to do.
Sites like GitHub actually give a perfect example that you can perfectly have guests view source code and only force registration for "ratings" or "subscribtions". And there is not less "fame" for the developers.

Anyhow, the same reason why PHP: The Right Way should be preferred over old sites like tizag or tutorialspoint, if you are new to PHP, please do not go to PHPclasses.org but use Packagist (you do not even need to use composer) or GitHub to find useful PHP libraries that will help you accelerate development on your next project.

I do hope PHPclasses.org will get a grip and do a massive relaunch, but I doubt someone as stubborn as Manuel can pull it off. The decline of his Alexa Ranking should indicate that "the-PHPclasses-Way" will not last forever.



*Update: Matthias Noback noted in the comments that it sounded mean. I just wanted to clarify: this should not be a personal attack on ML, as I do not know him personally. So "he sucks" is my professionally (and simplified) opinion about him. "Annoying" is what I would consider him personally (after some twitter chats).

Monday, 10 February 2014

Cleaning up PHP short-open-tags with Eclipse

One major problem of old/legacy or unmaintained PHP scripts is, that they usually use short-open-tags to enclose PHP code:

<? echo "foobar"; ?>

This used to be common in the old days, but trying to run those scripts on a modern LAMP stack will most likely result in 500-code errors.

Sure you could just enable short_open_tag in the php.ini and it would solve the problem. But even though there are no official hints that it might get deprecated or removed, it is still a bad practice. The Basic Coding Standard by the PHP Framework Interop Group clearly states:

Files MUST use only <?php and <?= tags.

So why should you hold on to bad practices, if you can just easily mass replace them to normal open-tags? Eclipse offers a feature where you can do a project based search & replace, and even use Regular Expression with group matching. Follow the steps below to refactor your (or someones else) code.

Steps to fix under Eclipse (PDT):


1) Select via the "File Navigator" your root project folder

Eclipse File Navigator

2) Go to the menu: "Search" -> "File..."

3) Configure as seen in the screenshot below, type into "Containing text:" the following: <\?($|\s+)


Eclipse Search & Replace in Files



4) Click on the button "Replace..."

5) Again, configure as seen in the screenshot. Type into "With:" the following: <?php$1

Eclipse Regular Expresion Text Matches



6) Click on "OK" -> Done! :)


Basically with that regular expression we just used, you are searching for all "<?" occurrences that are followed by either a newline or white space (tabs, spaces). It will then replace it by "<?php" including the same amount of white spaces (or newline) after. This will ensure we are not breaking the code or changing anything else except the PHP short-open tag.

Wednesday, 29 May 2013

Compile tinyproxy as anonymous proxy

Tinyproxy is a small light-weight proxy daemon for Linux environments. Espescially usefull if you have some spare dedicated/virtual servers running with multiple IPs. In this tutorial I will show you how to compile it from source on a Debian server - as the current official .deb package does not allow running it in complete anonymous mode.

Additionally if you don't want to install asciidoc (1GB!!!) you can use the modified patch from my compile steps (original). My version of the patch works with the current stable (1.8.3) version of tinyproxy. Not using the patch might give you following error:

checking for a2x... no
configure: error: Test for asciidoc failed. See the file 'INSTALL' for help.

 

Compile

# cd /usr/src
# wget --no-check-certificate https://banu.com/pub/tinyproxy/1.8/tinyproxy-1.8.3.tar.bz2
# wget --no-check-certificate

https://github.com/lifeofguenter/patches/raw/master/tinyproxy/tinyproxy-1.8.3-no-asciidoc.patch
# tar xvfj tinyproxy-1.8.3.tar.bz2
# cd tinyproxy-1.8.3/
# patch -p1 < ../tinyproxy-1.8.3-no-asciidoc.patch

# ./configure \
--prefix=/usr \
--sysconfdir=/etc \
--localstatedir=/var \
--disable-xtinyproxy \
--disable-filter \
--disable-upstream \
--disable-reverse \
--enable-transparent

# make && make install

Config

# nano /etc/tinyproxy.conf
User nobody
Group nogroup

Port 8888
BindSame yes

Timeout 600

DefaultErrorFile "/usr/share/tinyproxy/default.html"
StatFile "/usr/share/tinyproxy/stats.html"
Syslog On
LogLevel Error
PidFile "/var/run/tinyproxy/tinyproxy.pid"

MaxClients 100
MinSpareServers 5
MaxSpareServers 20
StartServers 10
MaxRequestsPerChild 10000

Allow 127.0.0.1
Allow 144.76.18.34
Allow 41.134.22.26

DisableViaHeader Yes

ConnectPort 443
ConnectPort 563

Run

# mkdir /var/run/tinyproxy
# chown nobody:nogroup /var/run/tinyproxy/
# tinyproxy