PHP needs its own ES6
Juha-Matti Santala

Juha-Matti Santala @hamatti

About: I'm a developer community builder and full-stack web developer from Finland. I blog occasionally here and weekly at my own blog at hamatti.org

Location:
Turku, FIN
Joined:
Jan 15, 2017

PHP needs its own ES6

Publish Date: Feb 7 '19
91 57

I have a love-hate relationship with PHP. I have written PHP in many forms from website templating and Wordpress to full MVC and SPA backend solutions in the past 15+ years.

I was reading through Bronson Dunbar's post "Using and learning ReactJS for 2 years, what have I learnt, and I stopped at this:

As we mentioned earlier, JavaScript has been around for some time, and in order to stay relevant a few people decided it was time to give it an update and that is when ES6 was born.

Both Javascript and PHP have similarities in their journey. Neither one was built for what they are used now: Brendan Eich wrote the Javascript as a prototype in 10 days back in 1995 to provide Netscape interaction into browser and Rasmus Lerdorf wrote PHP to be a templating engine in 1994. Due to the popularity of both, they have evolved into something completely different.

For the past few years (after getting over the Python 2->3 pain), I've been thinking and speaking about how I want PHP to break backwards compatibility. I know it's not gonna happen because such a big part of Internet runs on PHP and it would break everything.

So Bronson's post gave me something to think about: maybe we don't need a "new PHP", maybe we need ES6-for-PHP — a layer on top of PHP that would allow us to tackle the issues and write different PHP while still being compatible under the hood.

Background

I'm no language designer nor someone who finds joy (nor has skills) in building new programming languages. But I'm a dreamer and I can dream.

One of the big annoyances in PHP is the inconsistent standard library. Which is actually a feature, not a bug. When Rasmus Lerdorf was creating the language, he used different kind of naming schemes to balance the function hashing.

Well, there were other factors in play there. htmlspecialchars was a very early function. Back when PHP had less than 100 functions and the function hashing mechanism was strlen(). In order to get a nice hash distribution of function names across the various function name lengths names were picked specifically to make them fit into a specific length bucket. This was circa late 1994 when PHP was a tool just for my own personal use and I wasn't too worried about not being able to remember the few function names.

But it's 2019 and a lot of PHP is still being written. What if we could make it more enjoyable? (I love writing Ruby and Ruby on Rails and DHH's The Rails Doctrine is an inspiration to me. Especially the part about developer happiness.)

So what should we work on?

Consistency-layer on standard library naming

As you can see from the quote above, PHP's functions were named for specific purpose: to balance the hashing function. It means that as the standard library has grown, it's impossible to remember how to write function names because there's no consistency.

There's strpos but str_rot13. There's php_uname but phpversion. There's strtolower but bin2hex. And there's str_shuffle but recode_string. You can probably see the point.

So first plan of action: creating a consistent and predictable naming scheme

Turning array functions into methods of arrays

Let's take a look. Let's say we have an array of values that we want to first filter and then map. In vanilla PHP, we would do this:

array_map(
  function(number) {
    return number * 2;
  },
  array_filter(
    [1,2,3,4,5,6,7,8,9,10],
    function(number) {
      return number % 2 == 0;
    })
);

Notice how array_map has parameters as callback, array and array_filter has parameters array, callback. I have no clue why they are the exact opposite of each other but more often than not, I don't remember which is which and I have to resort back to docs. Also it's difficult to follow because of heavy nesting.

Let's see how we could make it nicer.

array(1,2,3,4,5,6,7,8,9,10)
  ->filter(num -> num % 2 == 0)
  ->map(num -> num * 2)

Making array functions into methods of array itself, we could chain things. Even if we don't want to adopt ES6-style arrow functions for anonymous functions, it would make this code much easier to follow and ready.

Second plan of action: make array_ functions into methods of arrays and make then chainable

One sort to rule them all

How about sorting then? Currently PHP's sort is a huge mess. Back in 2015, I wrote a blog post about my pain with them. Quoting myself:

There’s of course sort. Instead of giving a flag or parameter to sort to reverse the order, you have rsort. Then if you want to keep the key=>value pairs intact, there’s asort (which has caused me most confusions ever since I accidentally used that one instead of sort) and arsort. Then you can sort with keys ksort and reverse krsort. For natural sorting there’s natsort and case insensitive natcasesort. And when all this is not enough, you can use custom defined comparing function with usort, uasort and uksort. And the inconsistently named array_multisort for multidimensional arrays.

What if instead, we would have just sort() function and that would work with either flags, keys or custom callbacks. And please have an option for sort that returns array, not just sort as a side-effect. One of the first custom functions I create in most PHP projects is a sorted function (name borrowed from Python) that enables me to be more functional.

Third plan of action: unify sorts

Separating sequential array and associative array

Did you know that PHP only has associative arrays? It works quite okay while you're in PHP land but when you start converting it to JSON, you start to see issues. Another one of my blog posts from last year highlights this issue.

If you sort an array with numeric, sequential and unordered keys, you turn from object to an array. If you sort an array with numeric, sequential and ordered keys, it remains an array. Whatever you do for non-numeric or non-sequential array, it will stay an object.

When I'm reading through code or writing it, I should be able to figure out more consistently what the outcome will be. Using array_values to reset a "once a sequential array that got turned into associative array" is horrible.

Fourth plan of action: separate array types

Conclusion

There are probably other parts of the standard library that could benefit from a "ES6 Treatment" but the biggest pain points of my life regarding developing with PHP are these.

Let's recap:

  1. Consistent naming
  2. Array functions into chain-able methods of array
  3. One sort, no more
  4. Two arrays are better than one

Which parts of PHP would you like to see enhanced with ES6-for-PHP type of solution?

EDIT Feb 9th
If you like the idea, check out php-next project by Khalyomede

Comments 57 total

  • Anwar
    AnwarFeb 7, 2019

    I love the idea, and I think with the EcmaScript idea we could use a meta language. See all the new coming stuff like typed properties from PHP 7.4? What if we could use them now, and downgrade gracefully to PHP versions that do not support it by targeting a version like Typescript or Babel does for Javascript?

    • Robin
      RobinFeb 7, 2019

      You might be interested in preprocess.io (@assertchris work, not mine :) )

      • Juha-Matti Santala
        Juha-Matti SantalaFeb 7, 2019

        Oh wow, that's really nice and seems to be quite in line with my thinking. A layer of new syntax on top of old functionality.

        • Anwar
          AnwarFeb 9, 2019

          Could not help myself but start a research project. github.com/khalyomede/php-next. You will be able to transpile modern PHP code into valid PHP using build tools like Gulp.

          • Juha-Matti Santala
            Juha-Matti SantalaFeb 9, 2019

            This is so cool Khalyomede! I'll have to take a look and see if I could contribute also.

      • Anwar
        AnwarFeb 8, 2019

        This is truly a gem! Thousands thank you!!! @Juha-Matti, if you plan on making an ES for PHP with this library, I am in too 😉

  • Ben Halpern
    Ben HalpernFeb 7, 2019

    This is very well put. As an outsider, my understanding of the last decade or so of PHP, there has been a lot of performance tuning but less done to ameliorate things about the interface?

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 7, 2019

      Yeah, there's been a lot of talk and work on the performance and it's become way better with PHP7. From 5.4 on there has been small but super valuable improvements in the core syntax as well but since nothing breaks backwards compatibility and there's not much overlap with existing, the basics have not evolved as much as I'd like to see.

    • Matthieu Cneude
      Matthieu CneudeNov 13, 2019

      PHP introduced the possibility of strong typing with PHP 7 too (scalar and return typing) which is really cool I think. It's not perfect, but way better than PHP 5 or the ugliest versions before.

  • Bruno Paz
    Bruno PazFeb 7, 2019

    Great article about something I have been thinking for a while.

    And its a thing that can done incrementally. (Ex: Array functions, File functions etc) without breaking any "old" code.

    I like your array example. ;)

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 7, 2019

      Totally!

      I have had so many headaches because of all the things related to arrays :D

  • Chad Windham
    Chad WindhamFeb 8, 2019

    Javascript wasn't "redone from the ground up". They simply added a bunch of new/nice features. I would also have to completely disagree with "most developers aren't even using it". That is a completely untrue statement. You claim people are using CoffeeScript. Well, I'm sorry, but if you look at statistics CoffeeScript has had a sharp decline for a while now. ES6 is in fact the current standard of the the javascript language and it is in use. A LOT...

    Your statements basically come off as an offense that somebody would say javascript is better than php. (Which the author didn't do, nor did he compare them.) The author is saying that the upgrade of the ecmascript standards was very good for the language. Then he said that an upgrade to the features of php would be good for the language.

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      I agree with Chad here.

      I think PHP would benefit from a start from zero but that's never gonna happen. Too much will break if they do. So I started to think about alternatives.

      I think it's great that in Javascript, not everyone has to use ES6. I see it as an enhancement rather than requirement and I think the "ES6-for-PHP" idea could follow that. A layer on top that people can use if they want but the code that gets actually run is still plain old PHP.

      And I'm not saying that we have to take a Javascript route in PHP world. ES6 just happened to be a nice model that people who've done Javascript understand as a notion. It's not removing anything from Javascript, it's not forcing anyone to upgrade, but if you want to use it, it makes writing Javascript so much nicer.

      • Juha-Matti Santala
        Juha-Matti SantalaFeb 8, 2019

        And to reply your original question Jorge:

        So, do you think PHP need to start from zero or redone some stuff like the guys of JavaScript are doing?. Why?

        Yes. Not necessary "like the guys of Javascript are doing" but in some way. Do you not agree on the problems I've laid out in the blog post? With the wildly inconsistent naming and function parameters, wonky array functions and functionality and other problems?

  • Cabloo
    CablooFeb 8, 2019

    Have you tried Hack PHP from Facebook? It's basically what you're recommending here plus a lot more (strong typing and generics, for example).

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      I actually haven't. I've heard about it but never actually gave it a spin. Is it "backwards" compatible with PHP in a way that I could just start running my existing PHP app as a Hack app and slowly start using its better features?

      • Cabloo
        CablooFeb 8, 2019

        Yes - I have had the pleasure of developing on Hack and I like to describe it as a blend of PHP, JavaScript, and Java, since it takes some of the best features from each (and adds more). It was built to be fully compatible with PHP so that Facebook could slowly migrate its giant code base without breaking any existing functionality.

        That being said, I've never had to setup Hack on a server. The major difference is that Hack is a compiled language, so it requires significantly different server software to build & run (HHVM last time I checked). Depending on how your current PHP app is setup, this may turn out to be a simple or complex task.

        • Juha-Matti Santala
          Juha-Matti SantalaFeb 8, 2019

          Great, I'll have to put Hack on my list-to-learn and take a look at it in some point.

          ES6 needs transpiling as well so needing to have a few extra steps with Hack is not really an issue.

  • Fred Ross
    Fred RossFeb 8, 2019

    This is exactly what Facebook did with Hack. It also adds a decent type system, the vec, dict, and set primitives which replace all the ridiculous associative arrays, and gives you a high performance JIT to boot.

  • Tim Kilian
    Tim KilianFeb 8, 2019

    Turning php into JavaScript.

    • Anwar
      AnwarFeb 8, 2019

      Transpiling ES6 into PHP 🤓

  • Juha-Matti Santala
    Juha-Matti SantalaFeb 8, 2019

    I disagree on both notions:

    1. I wouldn't say that in PHP it's only "a few functions not consistent". PHP has quite a lot of issues that stem from it not being built for this kind of use case originally but then being evolved on top of a wild wild west of weird standard library.

    Like I mentioned in the beginning, it was a valid choice at the time for Rasmus to name the functions as he did.

    1. I personally think that there's a lot of similarities - not necessarily in the languages themselves but how they have evolved - in PHP and Javascript. Sure, 10 years ago Javascript was also a mess. These days, it's a joy to write with all the new stuff.
    • ohffs
      ohffsFeb 8, 2019

      I've seen some recent JS tutorials where JS programmers make a pages/ directory and put about.js, contact.js in there and then do things like require '../utilities.js' for a dozen helper files - it makes me nostalgic for PHP circa-2005 ;-)

  • Juha-Matti Santala
    Juha-Matti SantalaFeb 8, 2019

    Hey John!

    Why do think that?

  • Aleksi Kauppila
    Aleksi KauppilaFeb 8, 2019

    Generics would solve so much problems with arrays. They would allow us to create type safe collections where we could implement all those functions (map, filter, reduce etc).

    The issue is that array is not an object in PHP when in Python and JS arrays and lists are object.

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      Sure. I took a quite literal ES6 way of thinking here in a way that it would require some compiling/transpiling back to original.

      So maybe we could have

      array(1,2,3,4,5,6)
        ->filter(function(num) { return num % 2 === 0; })
        ->map(function(num) { return num * 2 ;})
      

      that would then transpile into

      array_map(
         function(num) { return num * 2; },
         array_filter(
           [1,2,3,4,5,6],
           function(num) { return num % 2 === 0; }
         )
      )
      

      so that it would be compatible with real deal.

      Like I mentioned, I'm not a language designer nor do I know much about how to make languages or compilers but this is the high-level thinking I have.

    • Johannes
      JohannesFeb 8, 2019

      At the least, generics would allow us to create our own array classes with generic strict types and I would bet that projects like symphony (which have a quite good robust collection implementation) would use this in the future. I am really hoping for generics in 7.4, as it is one of the most useful features in a "real" typed language! :)

      • Aleksi Kauppila
        Aleksi KauppilaFeb 8, 2019

        Unfortunately AFAIK there's no signs yet of generics being implemented in PHP. There is an RFC for generics targeting PHP 7.1, but i don't know if it's still active. Maybe in PHP 8?

        • Johannes
          JohannesFeb 8, 2019

          Aye, I have seen the RFC and I do hope that it is picked up before 8.x. Seeing how much that have changed in the 7.x versions (and especially seeing even harder "types" in 7.4) I do feel that it would not be impossible to see the RFC picked up in 7.4 or 7.5. I do hope so, but I'm not holding my breath! hehe

          Either way, the additions in each new minor version of the 7.x releases have given me much joy! :)

    • Daniel O.
      Daniel O.Feb 8, 2019

      Generics would be cool. On the other hand, it is already possible since PHP 7 to collect values of a single datatype. Just create a class and use type hinting. Here is an example: 3v4l.org/EKmWb

      • Aleksi Kauppila
        Aleksi KauppilaFeb 9, 2019

        This actually the approach i've been using for quite some time now. I usually just implement IteratorAggregate and create adding methods. Still, this usually means that i implement a lot of these classes. Lots of repetition, lots of new files.

  • Craftist
    CraftistFeb 8, 2019

    the arrow operator looks really redundant. the closure'd be better "=>" (since "=>" is only used inside array key-value pairs and foreach)

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      Yeah, the thin arrow function is just something I threw in there when writing. I don't mind writing full function declarations, the main point was to get rid of the array_ functions

  • Hamid Semix
    Hamid SemixFeb 8, 2019

    Great article

  • Vikas Yadav
    Vikas YadavFeb 8, 2019

    Its too late for php in my opinion. All major companies have dumped PHP and moved on to node. Javascript is too big to fail now. Already ruling front end with React/vue/Angular, started to dominate backend and now with React Native/nativescript, it has native mobile app development covered too.

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      I don't think so. Sure, a lot of companies are moving to other platforms and have been doing so for years with ones like Rails or Django (and more recently, Node). But for example Wordpress and Laravel are still having quite an impact in the world on a maybe bit different use case and I think there's good work that can be done to help there.

  • Miguel Piedrafita
    Miguel PiedrafitaFeb 8, 2019

    RFC it!

  • ohffs
    ohffsFeb 8, 2019

    I was going to mention the phpprocessor but I just noticed someone else already has :-) It's quite cool - but I've never been brave enough to use it on a production project even though I'm totally fine with webpack/babel/modernizr etc. :: shrugs ::

    There was a PHP RFC a while ago about standardising the names in the stdlib : wiki.php.net/rfc/consistent_functi... - don't think it ever went anywhere though. The list of functions to be renamed is quite 'impressive' ;-)

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      Thanks for sharing the RFC! That list in it is both impressive but also scary to see in one viewing how inconsistent it currently is.

  • Michael "Croydon" Keck
    Michael "Croydon" KeckFeb 8, 2019

    Are you aware of phpsadness.com ?

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      Yeah, I've read through bunch of those sites. I read through some of them for memory refreshment when writing this article.

      This one is another good one, although bunch of the stuff listed there have been fixed since.

  • Kamal Mustafa
    Kamal MustafaFeb 8, 2019

    Haxe has been supporting php for quite some time.

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      I had never heard of Haxe before, I have to take a look over the weekend!

  • Niko Heikkilä
    Niko HeikkiläFeb 8, 2019

    Problems with arrays mentioned in this post are the exact reason why I'm converting data to Laravel Collections whenever the chance comes. Collections are very pleasant to work with (method chaining for the win!) and I would love to see them integrated to the language itself. That and arrow functions, of course.

    Following this train of thought, I'd fancy to be able to develop efficient, maintainable, and secure PHP apps without adding framework as a dependency but that might be too wild to dream about.

    • Juha-Matti Santala
      Juha-Matti SantalaFeb 8, 2019

      That's really well put. Frameworks always come with quite a lot of extra weight. Especially when it's often the best parts of multiple frameworks that you want to take and that gets messy a lot.

    • Matthieu Cneude
      Matthieu CneudeNov 13, 2019

      It's possible. I was developing with a framework based on Sylex (which is now based on Symfony 4). It's very light, you don't have to couple everything and it only use the DBAL of doctrine instead of the ugly ORM. There are other lightweight PHP framework out there, too.

  • Matias Navarro Carter
    Matias Navarro CarterMay 6, 2019

    Great article. I think the main problem with it all is that PHP is so widely used that core maintainers have a very strict policy of not breaking the api. But I think PHP 8 will deal with more api changes.

    As a side note, I don't know how many BC changes ES6 brought to JS, but I'm inclined to think that they were new features mainly.

    In any case, you should check Nikita's Scalar Objects extension. I've tried it before and has been great pleasure to work with. It really empowers you a lot, because it let's you define your own api over the native types.

    • Juha-Matti Santala
      Juha-Matti SantalaMay 12, 2019

      Yeah, maintaining backwards compatibility is the key. And it's very crucial stuff because such a huge part of the Internet runs on PHP.

      ES6 was an extension but for me, the things that made me fall in love with it (after a quite a while of opposition) were the changes into how Javascript is written. () => {} shorthand for functions, class shorthand, template literals, etc.

      Thanks to this article, I've learned of a few ways to write more enjoyable PHP so I'm pretty happy about that. Scalar Objects extension looks pretty neat, thanks for the tip!

  • Aschwin Wesselius
    Aschwin WesseliusSep 5, 2019

    I think the presentation by Christopher Pitt on Laracon Amsterdam 2017 would be interesting to you:

    Transforming PHP

    I myself feel the same pain and I'm investing time in PoC's within PeachPie the .NET compiler for PHP.

    Yes, that's another compiler, not a new standard. But it provides me all the power of .NET, including semantics and syntax not (yet) available to PHP. Like generics and aspect oriented programming (AOP) with "attributes".

    This is exactly why I don't want to continue on PHP (alone) because the evolution of the language is slow.

    Unfortunately this is exactly the showcase of open source vs. proprietary software. JAVA has existed since 1995, as have Python. JAVA was backed by Sun and later by Oracle. Python, Perl and PHP have not been backed by companies or any industry.

    The .NET framework has been backed/invented by Microsoft and was solely working with the Windows platform. Very early, almost immediately Miguel de Icaza started on Mono, a .NET framework outside of Windows.

    Nowadays, this Mono has been integrated into the .NET Core framework, available for Linux and OS X. It is mature and very stable.

    What this means? That both JAVA and .NET are frameworks, moving into platforms. Where are Python, Perl and PHP? They are still just languages.

    These are fine for day-to-day little projects, but for future proof initiatives many of the languages don't have the oomph to grow into the same direction.

    These open source projects need a clear vision, tight conventions and a rigid schedule to implement new features. Otherwise they will not keep up. They will become extinct because of natural selection.

  • Josh Bruce
    Josh BruceOct 6, 2019

    Interesting. I call one approach I'm taking Shoop. Makes the base data types objects and wraps enough of the SL to perform interesting chains of transformations. I've enjoyed using it in the 8fold platform enough that I went ahead and made it public.

    I do think Rasmus is participating in the direction more and we'll see PHP evolve in interesting ways moving forward. When PHP7 came out he gave a lot of talks about the history and his participation and what's happened to the language and core maintainers over the years.

  • deathshadow60
    deathshadow60Dec 4, 2019

    Whilst I have my own list of changes that would improve PHP, and I heartily agree over how derpy PHP's naming conventions are, some of what you said doesn't feel like improvements to me.

    The daisy chained "building" methdodology of ->something->somethingElse always strikes me as painfully and agonizingly cryptic, and for what? "Wah wah, eye dunz wunna type?". PHP thanks to its C syntax is already painfully and agonizingly cryptic enough without making it HARDER to understand. One of the many reasons I'm not a fan of jQuery and often call it mentally enfeebled half-witted trash.

    Things I'd like to see?

    No more shorttags, EVERYTHING is code and nothing is allowed to blindly output.

    No more heredoc, nowdoc, or double quoted strings. Single quotes or golf tango foxtrot oscar.

    Make all "include" be require. The myth of overhead difference is BS and it would cause a fundamental shift in how people write PHP.

    No passing scope to includes. BREAK SCOPE.

    No more direct execution inside includes, make everything in an include HAVE to be an object or function method like any other normal library.

    Make includes filetype be a trigger to NOT allow the file to be opened for read/write from PHP itself. That means no fopen, no readfile, nothing OTHER than including it for execution.

    These might all sound odd, but do you realize how many PHP cracks/exploits would have fallen flat on their faces with these changes?

    But what do I know? My first step after RCA 1802 and 8080/Z80 Machine Language was Pascal, and I spent a decade programming ADA. "C is not my favorite language"

  • tasen-sp
    tasen-spNov 8, 2020

    I love that

Add comment