Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:82357 Return-Path: Mailing-List: contact internals-help@lists.php.net; run by ezmlm Delivered-To: mailing list internals@lists.php.net Received: (qmail 62527 invoked from network); 10 Feb 2015 09:56:20 -0000 Received: from unknown (HELO lists.php.net) (127.0.0.1) by localhost with SMTP; 10 Feb 2015 09:56:20 -0000 Authentication-Results: pb1.pair.com header.from=php@tutteli.ch; sender-id=pass Authentication-Results: pb1.pair.com smtp.mail=php@tutteli.ch; spf=pass; sender-id=pass Received-SPF: pass (pb1.pair.com: domain tutteli.ch designates 80.74.154.78 as permitted sender) X-PHP-List-Original-Sender: php@tutteli.ch X-Host-Fingerprint: 80.74.154.78 ns73.kreativmedia.ch Linux 2.6 Received: from [80.74.154.78] ([80.74.154.78:43954] helo=hyperion.kreativmedia.ch) by pb1.pair.com (ecelerity 2.1.1.9-wez r(12769M)) with ESMTP id 93/90-47508-0C5D9D45 for ; Tue, 10 Feb 2015 04:56:18 -0500 Received: (qmail 1462 invoked from network); 10 Feb 2015 10:56:12 +0100 Received: from cm135-167.liwest.at (HELO RoLaptop) (81.10.135.167) by ns73.kreativmedia.ch with ESMTPSA (AES256-SHA encrypted, authenticated); 10 Feb 2015 10:56:12 +0100 To: "'Dmitry Stogov'" , "'Joe Watkins'" Cc: "'Yasuo Ohgaki'" , "'PHP Internals'" , "'Stanislav Malyshev'" References: <54D7ED22.3080001@gmail.com> In-Reply-To: Date: Tue, 10 Feb 2015 10:56:10 +0100 Message-ID: <007901d04517$cd3c4d70$67b4e850$@tutteli.ch> MIME-Version: 1.0 Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Mailer: Microsoft Outlook 14.0 Thread-Index: AQGgxP9HPTh52uHWkGo6jLSeXRdtNAMgQV04AXznbe0C/KNi4gHjmxmHAVkKc8gBfNJbegGHSzWZAVLQRzQCoXlWsAGB4HqFAkW/W+gCKZgqpwFlBHY3AtCjwQoDOJqgupxPLP9w Content-Language: de-ch Subject: AW: [PHP-DEV] Design by Contract From: php@tutteli.ch ("Robert Stoll") We could provide an Invariant class in order to support invariant cases = at least to a certain degree:=20 http://3v4l.org/vjBRG Of course, that does not provide the same support as native invariants = but maybe better than nothing. At least we would have a consistent = Invariant class throughout the code bases. We could go even further and provide some syntactic sugar in order that = one does not need to write new Invariant(...) as in line 28 -- for = instance: $this->a =3D require(> 100);=20 which is short for $this->a =3D new Invariant(function($value){return $value > 100;}, = '$this->a > 100'); Cheers, Robert > -----Urspr=C3=BCngliche Nachricht----- > Von: Dmitry Stogov [mailto:dmitry@zend.com] > Gesendet: Dienstag, 10. Februar 2015 08:06 > An: Joe Watkins > Cc: Yasuo Ohgaki; PHP Internals; Stanislav Malyshev > Betreff: Re: [PHP-DEV] Design by Contract >=20 > good point, but I think we can do nothing about that. > Anyway, it should be reflected in RFC. >=20 > Dmitry. >=20 >=20 >=20 > On Tue, Feb 10, 2015 at 9:59 AM, Joe Watkins = wrote: >=20 > > I'm not sure we can always enforce invariant contracts ... > > > > Evaluating invariant expressions on entry and exit is not enough, > > since a property can be changed without the use of a method. > > > > Can or should, we do anything about that ? > > > > This should also be covered in the RFC, I think. > > > > Cheers > > Joe > > > > On Tue, Feb 10, 2015 at 6:49 AM, Dmitry Stogov = wrote: > > > >> Hi, > >> > >> can I make some minor correction? > >> > >> Thanks. Dmitry. > >> > >> > >> > >> On Tue, Feb 10, 2015 at 9:25 AM, Yasuo Ohgaki = wrote: > >> > >>> Hi Dmitry, > >>> > >>> On Tue, Feb 10, 2015 at 1:43 PM, Dmitry Stogov = wrote: > >>> > >>>> On Feb 9, 2015 11:20 PM, "Yasuo Ohgaki" = wrote: > >>>> > > >>>> > Hi Dmitry and Joe, > >>>> > > >>>> > On Mon, Feb 9, 2015 at 8:27 PM, Dmitry Stogov > >>>> wrote: > >>>> >> > >>>> >> yes. this may work. > >>>> >> probably better to put it after extends and implements. > >>>> >> > >>>> >> > >>>> >> Dmitry. > >>>> >> > >>>> >> On Mon, Feb 9, 2015 at 2:19 PM, Joe Watkins > >>>> >> > >>>> wrote: > >>>> >>> > >>>> >>> Could this be described as a requirement of the class ? > >>>> >>> > >>>> >>> class Mine > >>>> >>> require(invariant-expr) > >>>> >>> extends Something > >>>> >>> implements Someface { > >>>> >>> > >>>> >>> public function method($param) : return > >>>> >>> require(input-expr), > >>>> >>> return(output-expr) { > >>>> >>> > >>>> >>> } > >>>> >>> } > >>>> >>> > >>>> >>> To avoid invariant keyword maybe. > >>>> > > >>>> > > >>>> > This would work. > >>>> > If users have adopted DbC in some way, 'invariant' may be used > >>>> already. > >>>> > > >>>> > I see two issues. > >>>> > > >>>> > Interface works, but most classes are class without interfaces. > >>>> > Then > >>>> users have to repeat > >>>> > require()/return() many times to check class state or have to = use > >>>> interface for DbC. > >>>> > > >>>> > >>>> In D classes may have "invariant" constraints. We may use = "require" > >>>> keyword for it. The constraints ineritance rules and order of = calls > >>>> to constrains must be the same s in D. > >>>> > >>>> class Foo { > >>>> private $sum =3D 0; > >>>> require($this->sum >=3D 0); // invariant constraint will be > >>>> called before and after every method > >>>> function add($n) { > >>>> $this->sum +=3D $n; > >>>> } > >>>> } > >>>> > >>> > >>> OK. I'll update the RFC. > >>> > >>> > >>>> > Since compiler does not know a method() is for DbC invariant, = it > >>>> > will > >>>> be compiled and exists > >>>> > in production execution. > >>>> > > >>>> > Use of interface: > >>>> > - no additional keyword (pros) > >>>> > - requires interface for DbC, most classes does not require > >>>> interface (cons) > >>>> > - if interface is not used, user has to repeat invariant > >>>> > conditions > >>>> over and over (cons) > >>>> > - requires to define method that should not exist in = production > >>>> (cons) > >>>> > >>>> I didn't understand you idea. > >>>> > >>> > >>> Joe's idea was to use Interface for invariant condition grouping. > >>> If we use your idea, issue is solved. > >>> > >>> class Foo { > >>>> private $sum =3D 0; > >>>> require($this->sum >=3D 0); // invariant constraint will be > >>>> called before and after every method > >>>> function add($n) { > >>>> $this->sum +=3D $n; > >>>> } > >>>> } > >>>> > >>> Ok. > >>> > >>>> > > >>>> > New keyword: > >>>> > - does not require interface for efficient definition (pros). > >>>> > - new keyword (cons) > >>>> > > >>>> > It seems we are better to choose proper keyword for = 'invariant'. > >>>> 'invariant' is not common, so 'invariant' > >>>> > may be good enough choice. Does anyone use 'invariant' as > >>>> function/method/class/constant names? > >>>> > If there is better name, suggestion is appreciated. > >>>> > > >>>> > On place closure call like javascript is not supported in PHP, > >>>> > but > >>>> function works with assert. > >>>> > > >>>> > >>>> > function foo() { return FALSE; } > >>>> > assert(foo()); > >>>> > ?> > >>>> > PHP Warning: assert(): Assertion failed in - on line 3 > >>>> > > >>>> > This wouldn't be changed for require()/return()/invariant()? > >>>> > > >>>> > We need a switch to change development/production. I'll use > >>>> "dbc=3DOn/Off" for now. > >>>> > If you have any better idea, please let me know. (dbc will be > >>>> INI_SYSTEM) > >>>> > >>>> Check the "expectations" RFC. I think, it's going to be 3 state > >>>> switch, zero-cost disable, run-time disable, run-time enable. So, > >>>> it may be INI_ALL, but it won't be possible to switch from/to = zero-cost at run-time. > >>>> > >>> > >>> Ok. > >>> > >>>> > > >>>> > For CLI, there will be no command line switch for dbc. It > >>>> > executes > >>>> script production mode by > >>>> > default. If user needs development mode > >>>> > > >>>> > php -d dbc=3D1 script.php > >>>> > > >>>> > should be used. > >>>> > > >>>> > > >>>> > And finally, are we going to allow custom assertion error = message? > >>>> e.g. > >>>> > > >>>> > require($a > 0, 'Parameter $a must be positive number'); > >>>> > >>>> I think, it may be useful. > >>>> > >>> Ok. I'll use it. > >>> > >>>> > > >>>> > Since this contract is definition like "implements"/"extends", = we > >>>> > may > >>>> not allow > >>>> > custom error message. I'll write the RFC not to allow custom > >>>> > error > >>>> messages unless > >>>> > you dislike it. > >>>> > > >>>> > I think we have enough consensus/information to start writing = the RFC. > >>>> > If I have any concern, I'll ask here. > >>>> > >>>> Ok, go forward :) > >>>> > >>> Updated wiki page. > >>> https://wiki.php.net/rfc/dbc2 > >>> > >>> If you would like to change something, please let me know. > >>> I don't think finished draft at all and I don't mind going back = and > >>> forth. > >>> > >>> Regards, > >>> > >>> -- > >>> Yasuo Ohgaki > >>> yohgaki@ohgaki.net > >>> > >> > >> > >