PHP 5.6 – looking forward

Having taken a look in the past, now it’s time to look into the future, namely 5.6 (PHP 7 is the future future, we’ll get there eventually). So I’d like to make some predictions of what would work well and not so well and then see if it would make sense in two years or turn out completely wrong.

High impact

I expect those things to be really helpful for people going to PHP 5.6:

Constant expressions – the fact that you could not define const FOO = BAR + 1; was annoying for some for a long time. Now that this is allowed I expect people to start using it with gusto.

Variadics – while one can argue variadics are not strictly necessary, as PHP can already accept variable number of args for every function, if you’re going to 5.6 the added value would be enough so you’d probably end up using them instead of func_get_args and friends.

Operator overloading for extensions – the fact that you can sum GMP numbers with + is great, and I think more extensions like this would show up. E.g., for business apps dealing with money ability to work with fractions without precision loss is a must, and right now one has to invent elaborate wrappers to handle it. Having an extension for this would be very nice. Finding a way to transition from integer to GMP when number becomes too big would be a great thing too.
Still not convinced having it in userspace is a great idea, what C++ did to it is kind of scary.

phpdbg – not having gdb for PHP was for a long time one of the major annoyances. I expect to use it a lot.

Low impact

Function and constant importing – this was asked for a long time, but I still have hard time believing a lot of people would do it, since people who need imports usually are doing it in OO way anyway.

Hurdles

OpenSSL becoming strict with regard to peer verification by default may be a problem, especially for intranet apps running on self-signed certs. While this problem is easily fixable and the argument can be made that it should have been like this from the start – too many migrations go on very different paths depending on if it requires changing code/configs or not.

Adoption – again, with 5.5 adoption being still in single digits, I foresee a very slow adoption for 5.6. I don’t know a cure for “good enough” problem and I can understand people that do not want to move from something that already works, but look at the features! Look at the performance! I really hope people would move forward on this quicker.

While 5.4 will always have a special place in my heart, I hope people now staying on 5.2 and 5.3 would jump directly to 5.6 or at least 5.5. The BC delta in 5.5 and 5.6 is much smaller – I think 5.3->5.4 was the highest hurdle recently, and 5.4 to 5.5 or 5.6 should go much smoother.

Anything you like in PHP 5.6 and I forgot to mention? Anything that you foresee may be a problem for migration? Please add in comments. 

Advertisements

hiphop for php

By now probably everybody that is connected to PHP world knows about Facebook’s HipHop.
So here are my thoughts about it.

1. This is a very cool and exciting technology. There were multiple attempts to do this in various ways, and from what it looks, HipHop is the most successful and appealing. I know doing these things is not easy – I tried something like that myself somewhere back in 2006 but was unable to go past very basic examples (I also made a mistake of choosing C instead of C++ as target, which I now think was not a smart decision). And the progress and support for almost all of the PHP magic is definitely great. There still are unsupported areas, but mostly are dark corners into which not many people venture (or should venture, at least ūüôā

2. I do not see it as a replacement for php.net code or Zend Engine. The mainstream of PHP development still happens in the community around php.net and I do not think it is going to change anytime soon. I also see the fact that HipHop engine basically re-implements all the extensions as a serious disadvantage, for which the solution should be sought, even though I completely understand the technical reasons for doing so. I do not know which kind of the solution but while for the company like Facebook it might be OK to “freeze” certain set of extensions and features and maybe catch up periodically, I think it is obvious how such model can be a problem for the wider adoption.

3. If we talk about broader adoption of this technology in a wider PHP world, there are some serious challenges to consider:

  • Plugins: right now, you must compile your whole application. However, many real-life applications have extensive plugin models, which consist of their main competitive advantage – take WordPress, Drupal, Magento, any Zend Framework app – all of these allow to write custom plugins and run them alongside the main code base. The model in which you have to rebuild whole application each time you add/change a line of code is not acceptable in these circumstances.
  • Modularity: this is connected to the above, but is a bit different. PHP right now runs on Apache, IIS, Lighty, nginx, and tons of other servers in different environments. For the use of the technology in the wide variety of environments PHP is used in, one must be able to modularize¬† and separate the application PHP code from the runtime and the environment.
  • Portability: I tried to run a bunch of my scripts through the demo that the HipHop team was very kind to give me – and most of them experiences unsupported functions or some function didn’t work exactly as their PHP counterparts (random example: PHP’s fopen() would error out given empty first argument, while HPHP implementation would open the current directory as file. There are more such things…). Now, I admit, it would be very easy to fix them, to use different functions and they would work, but again I think it’s obvious how it can be a problem for a PHP programmer, if you are not coding targeting HipHop specifically – and especially of you use 3rd-party code. Having different implementations always presents portability challenges.
  • Thread-safety: A huge problem with PHP thread-safety is third-party libraries. Many of them are not thread safe either explicitly, or, even worse, implicitly – i.e. they just have either bugs or information leaks between threads (like changing some setting in one thread and feeling its effect in another – imagine chdir() leaking through the thread boundaries – see how it can be a problem?) HipHop team’s answer to this question was “we had fixed all those extensions” – which, without diminishing the capabilities of this excellent team, I think is not a satisfactory answer. It very well may be that they indeed fixed all the problems they could see in the code they run – but let us not forget they run one (albeit huge) application. I have hard time believing they have fixed every threading problem with every C library in existence that has interface to PHP and will continue to do so as long as C libraries exist. This of course goes back to modularity question, since here we have coupling between compiling and runtime model.
  • Debugging: obviously, debugging C++ code is orders of magnitude harder than PHP code. So you either need ninja debugging skills, or a very good set of tools to allow you to identify a problem in a live server running non-source PHP.

4. I also see certain danger potential in the success of this project. The danger primary being that the performance is very important in the web world, and it can give an incentive to the PHP community to change PHP in ways that may be better for performance, but would make PHP into being an entirely different language. The obvious example of this is strict typing – strict typing, of course, would help the compiler a lot in figuring out what’s going on with the code. However, I am not convinced at all that it would make the life of a PHP programmer easier. I know there are a number of proponents of this but I am still not convinced it’s the way for PHP to go. And there might be other incentives like this – i.e. to add or drop features to PHP, or avoid using certain constructs and features, for the sole reason of making it more compile-able. Now, there’s nothing wrong with being compiler-friendly, but I don’t think for a language like PHP it should be the primary motivation.

Re-reading these notes I realized some of it might give an impression that I dislike the technology. It is absolutely not so – on the contrary, I think it is a great addition to the PHP world and I want again to congratulate the HipHop team on a huge achievement and thank them for making the PHP world better and more exciting. It would be very interesting to see how this develops and how and if the problems can be overcome and how this technology changes the PHP world and is changed by it.

Ruby-like iterators in PHP

I’ve started playing with Ruby recently, and one of the things that got my attention in Ruby were iterators. They are different inside from regular loops but work in a similar way, and looks like people (at least ones that write tutorials and code examples ūüėČ ) like to use them. For example, you can have:

arr = {"one" => 1, "two" => 2, "three" => 3}
arr.each do |key, val|
print "#{key}: is #{val}\n"
end

which iterates over a Ruby hash and prints:

three: is 3
two: is 2
one: is 1

So it got me thinking – suppose I wanted to do something like this in PHP (suppose I don’t like regular loop-y iterators for some weird reason). Naturally, I wouldn’t get it in the same concise form as Ruby does, since I can’t change the syntax. But I could get the essence. Let’s try it. First, the main iterator:

class RubyIterator {
  protected $_body;

  public function __construct($body) {
    if(!is_callable($body)) {
      throw new Exception("Iterator body should be a callable");
    }
    $this->_body = $body;
  }
  public function yield()
  {
    $args = func_get_args();
    call_user_func_array($this->_body, $args);
  }
}

Next, less try to make some class that uses it:

class RubyArray {
    protected $_arr;
    public function __construct(array $a)
    {
        $this->_arr = $a;
    }

    public function each($body) {
        $iter = new RubyIterator($body);
        foreach($this->_arr as $k => $v) {
            $iter->yield($k, $v);
        }
    }
}

and then:

/*
arr = {"one" => 1, "two" => 2, "three" => 3}
arr.each do |key, val|
    print "#{key}: is #{val}\n"
end
*/
    
$arr = new RubyArray(array("one" => 1, "two" => 2, "three" => 3));
$arr->each(function($key, $val) { echo "$key: is $val\n"; });

and the result the same, of course. Or, let’s try with ranges:

class RubyRange {
    protected $_from$_to;
    public function __construct($from$to) {
        $this->_from $from;
        $this->_to $to;
    }
    public function each($body) {
        $iter = new RubyIterator($body);
        for($i=$this->_from$i<=$this->_to$i++) {
            $iter->yield($i);
        }
    }
    
}

and use it:

/*
r = 1..10;
r.each do |i|
    print "#{i*i}\n"
end
*/

$rr = new RubyRange(110);
$rr->each(function($i) { echo $i*$i."\n"; });

which indeed produces:

1
4
9
16
25
36
49
64
81
100

And so on – if one wanted, whole set of iterator methods could be implemented (I’m of course too lazy to do that ūüôā ). I wonder if there are use cases that we can’t do there.

syntax I miss in PHP

Here are some syntax additions I’d like to see in PHP:

1. a()()
When a() returns a callable object (such as a closure) the second set of brackets would call it. That would allow to write some neat code. I am working on a patch for that but it’s a bit harder than I thought.

2. a()[$x]
This is kind of obvious, I wonder why don’t we have it? Should also be able to be an lvalue, though unless a() returns by-ref or return value is an object it may not do what one wanted.

3. foo(1,2,,4)
Syntax to skip a parameter in a call, which then will be substituted with the default as defined by the function. Would come handy if you have function with many defaults, and you only want to change the last one but leave the rest alone – now you don’t have to look up the actual default’s values.

4. foo(“a” => 1, “c” => 2, “d” => 4)
Named parameters call, which allows you to specify parameters in arbitrary order by name. Would allow to build nice APIs which could accept wider ranges of parameters without resorting to using arrays. That’d also imply call_user_func_array() would accept named arguments.
The problem here might be what to do with unknown arguments – i.e. ones that the function did not expect. I guess the function could just ignore them.

5. $a = [“a”, “b” => “c”];
I’d really like to have short array syntax. Yes, I know it was rejected so many times already, but I still like it.