Settings

Theme

Comparing the PHP 7 and Hack Type Systems

dmiller.io

46 points by jazzdan 11 years ago · 37 comments

Reader

Vendan 11 years ago

  Fatal error: Argument 1 passed to myLog() must be of the type string, integer given, called in /home/vagrant/basic/main.php on line 9 and defined in /home/vagrant/basic/main.php on line 4
"HHVM says the error occurred on line 6 where PHP says it occurred on line 9. I prefer HHVM's approach here as it shows us where we called the function with the bad data, not where the function is defined that we are calling with bad data."

Hrm, PHP is telling you both line 4 and line 9, as where the function is defined and where it's being called with bad data, which is quite nice. In comparison, HHVM is saying line 6, which is a closing brace for the myLog function. In my books, PHP's approach is way way better then HHVM's

  • Bahamut 11 years ago

    It's hard to say what is better - oftentimes when you see a large stack trace for an error, it can be difficult to determine where the offending line is, especially on first glance. Personally, I think I agree with the author, but PHP 7 does look to give more information, which can be better in some situations.

    • jontro 11 years ago

      However in this case line 6 is not the problem in any way (as the grandparent is saying). Looks like a bug in the error reporting?

      • TazeTSchnitzel 11 years ago

        Hmm, perhaps the opcode has the wrong line number attached to it. A bug report could be filed for that, probably a trivial fix.

    • stephenr 11 years ago

      I disagree - even if hack was reporting the correct line number it's only half the story, and is objectively worse for fixing the error.

    • Vendan 11 years ago

      Part of the point is that the article is just dead wrong. "I prefer HHVM's approach here as it shows us where we called the function with the bad data". HHVM says line 6, which is the end of the function, not where the function was called. In fact, they go on to state "not where the function is defined that we are calling with bad data." while still having said "PHP says it occurred on line 9" But line 9 IS where the function was called with bad data. The article misinterpreted the 2 errors...

jwatzman 11 years ago

It's worth pulling out what I think is the most fundamental difference between the two type systems, from the end of the article:

After writing a couple small programs in Hack I've realized that it's not types themselves that make writing Hack enjoyable: it's the tight feedback loop Hack creates between the machine and myself. Integrating the Hack type checker into my editor means that my entire codebase is analyzed in a split second as soon as I save a file. This immediately surfaces any dumb, or subtle mistakes I made. I find myself writing code fearlessly: when I forget what a function returns, I just write code that calls it with what I think it returns. If I'm wrong, the type checker will tell me immediately. I can fix it quickly, and move on.

Hack's type system is static -- it's enforced by a static analysis tool that instantly reports errors in all of your code. PHP can only report errors that it actually encounters at runtime. Along with the "fearlessness" above, it also means that you might miss you forgot to check for a null in an error case... until it explodes at runtime in production. Hack's static type system can mechanically check for all of these immediately.

  • TazeTSchnitzel 11 years ago

    The difference isn't between the systems, it's a difference in tooling, in that Hack comes with its own type checker. Part of the motivation for PHP 7's expanded type hinting support was to enable better static analysis tools. I expect we'll see something similar to Hack's type checker for PHP 7 in not too long. Actually, some IDEs already check types, I think.

    Of course, a tool for PHP 7 can only go so far, because PHP 7's type hints aren't sufficient to cover everything, unlike Hack which has things like nullable support.

  • stephenr 11 years ago

    Even without static types tools like PHPStorm have offered that type of analysis and error reporting.

aaronharnly 11 years ago

I believe that 1 == true as much as the next nerd, but still, this line:

  declare(strict_types=1)
is that not a bit ironic?
  • allendoerfer 11 years ago

    I think so, too. I know, I am just hating, but to me it seems like they just can not quite change their culture. Even if they implement something clean and elegant like strong typing their hacky past finds a way to slip in.

    Nevertheless, congrats to them, they actually deliver.

    • imakesnowflakes 11 years ago

      > I know, I am just hating...

      People has recently become quite reluctant to 'hate' on php, as if it is some kind of deformed being who needs emotional support. It is like criticizing Christopher Nolan.

      You just don't 'hate' on it with out sliding in a few praises. I know that criticizing the language will result in heated (often irritating) debate with the php fan boys (I call them fan boys because other php users will not come justify the language, with things like, "every language has faults so it is ok"). But I think we can use a little less sugar coating. I am not telling that the language should be killed right off, but please just don't romanticize it's faults and send people who are serious about programming down a path they have to (hopefully) come back 9 or 10 years later (When they are finally disillusioned).

      EDIT: he..he..downvotes!

      • alien3d 11 years ago

        Upvote.It's getting over complicated each update and not for simple development.While language like c# get more easier like old days php.

  • TazeTSchnitzel 11 years ago

    Yes, and as the person who came up with that, I was well aware of the irony. It was originally this:

      declare(strict_typehints=TRUE);
    
    However, I changed it to the form that you see there because it was shorter. I felt that in the grand scheme of things it's not very important: declare() isn't a function, it's a language construct, and saving 5 chars from something that'll be typed very frequently is probably worth it.
    • mirashii 11 years ago

      > saving 5 chars from something that'll be typed very frequently is probably worth it.

      This mindset is something that I've personally seen uniquely permeate every layer of the PHP community, more than anywhere else. I'm honestly curious, what makes communities seem to value things like typing less characters over clarity and correctness? The most important thing to me is reducing the amount of mental state needed for a human to read any line of code.

      • echaozh 11 years ago

        Because PHP is for really fast development, and not for slow movers who actually think a lot. That's what I sense after joining a company using PHP.

        The language itself feels like a bag of features copied over from top contenders from the TIOBE index. You can see the fastness in the core of the language design.

        After all, you use PHP to perform MySQL queries in the middle of HTML tags. If you want to do this, you know some principles are merely burden for your smooth execution of the web site development, and should be throw out the window at first thought.

        • stephenr 11 years ago

          Just because you can do something doesn't mean you should

          The sort of approach you're describing is not suggested or used by anyone with half a clue what they're doing.

        • giaour 11 years ago

          We program so hard we don't have time to think. Or type. At least not with as many characters as a sane person would.

      • TazeTSchnitzel 11 years ago

        In this case I don't think it sacrifices much clarity, and it avoids the word "typehint" which is controversial (correctness is disputed). Using TRUE wouldn't necessarily be more correct, it's fairly arbitrary.

    • ars 11 years ago

      I sort of wish you had done:

        declare(types=strict);
      
      instead. That way other options can be added in the future.
      • TazeTSchnitzel 11 years ago

        Not syntactically legal, unless it's special-cased or we unusually make a lowercase constant for that purpose. declare() takes a constant value.

        Well, it could've been this:

            declare(types="strict");
        
        Alas, we are beyond feature-freeze now. Also, I quit PHP development.
      • giaour 11 years ago

        I believe there was some discussion of using the same strict declaration as javascript ('use "strict";'), but there's already an "easter egg" in PHP that causes your program to exit and prints out something like "I think you're using the wrong language."

        For some reason, this Easter egg was deemed too important to displace with an actual language construct.

        • TazeTSchnitzel 11 years ago

          Well, there's also the fact that something that changes the language behaviour really should be a pragma and not a magic import statement.

      • stephenr 11 years ago

        i quite like this concept too, but both are still better than Hack's

            <?hh // strict
        
        Strict what?
    • BringTheTanks 11 years ago

      Well, there are non-ironic alternatives:

          declare(strict_typehints=TRUE); // not ironic, not short
          declare(strict_types=1); // ironic, short
          declare(strict=true); // not ironic, even shorter
      
      JS has one strict mode, this could've been an opportunity to introduce an umbrella mode for strict coding in general.

      Also the declare syntax could've been augmented to support passing implicit boolean parameters without setting a value:

          declare(strict); // oh yeah.
      
      So... you know. Not that it matters what you call it, but choosing ugly (and ironic) over pretty (and sane) shouldn't be taken so lightly.
    • giaour 11 years ago

      As someone who will be typing it very frequently, I wish the more verbose and obvious version had won out.

ejcx 11 years ago

I really like writing hack and haven't tried PHP7. It makes a huge difference having types. If you have a function

    function dowork(@?string $w)
You can allow execution to continue but still log the error. It's made me aware of all sorts of edge case bugs that I never would have been able to find before.

XHP has allowed me to do the same, by forcing me to write well formed html and I love it

  • mirashii 11 years ago

    You should seriously consider trying a language with a more complete and robust type system that is checked at compile time. If you like the fact that these kind of corner cases can be logged, imagine if you can find them before you ever hit them at compile time.

    • coldtea 11 years ago

      Which Hack does too (static checking). What he describes (logging) can be enabled as an alternative to that.

      Maybe you should try it?

      • mirashii 11 years ago

        If you're logging, the only good reason to do so instead of fixing errors which your type checker found at compile time is if you're mixing PHP and Hack, which is where you'd get type errors that couldn't be determined at compile time. I'm suggesting using a language with an environment that is more completely statically checked (and preferably also has a more complete type system, something functional perhaps).

TazeTSchnitzel 11 years ago

> HHVM calls this a "catachable" fatal error. This is interesting as in the RFC the error shown actually matches HHVM's error.

It was a "catchable" fatal error (i.e. E_RECOVERABLE_ERROR) in PHP 5.x for typehints. But PHP 7 is changing it to be an Exception instead, and for some reason it currently produces an inaccurate error message in the master branch - it should say "Uncaught exception" (which it is), but that's not been fixed yet. Trunk builds aren't ready for production use, etc.

allan_s 11 years ago

For nullable types, there's a plan/rfc to have them too

https://github.com/php/php-src/pull/1045 https://wiki.php.net/rfc/nullable_types

not for 7.0 but hopefully for 7.1

Keyboard Shortcuts

j
Next item
k
Previous item
o / Enter
Open selected item
?
Show this help
Esc
Close modal / clear selection