Hi all,
We have discussed most of issues for https://wiki.php.net/rfc/dbc2
==Missing parts of the RFC for me==
- Advantage over annotation:
Written as code, executed as code. ("Written as document, available
as document" would be
annotation advantage)
- Advantage over assert() only solution:
Part of DbC can be done by assert() only, but it reduces readability.
Post condition can be
located anywhere in function. It makes difficult to distinguish if
assert() is contract or internal
error. Invariant helps to reduce number of assert() a lot. In short,
contract and internal logic
assertion is different assertion.
DbC encourage proper class design. It's taken from Eiffel site.
https://www.eiffel.com/values/design-by-contract/introduction/
"These observations shed light on the true significance of
inheritance: not just a reuse,
subtyping and classification mechanism, but a way to ensure
compatible semantics by
other means. They also provide useful guidance as to how to use
inheritance properly."
DbC encourages proper secure design. Since DbC removes all assertion
from production
code, users must ensure app input/output validity when it accepts
input and write outputs.
http://cwe.mitre.org/top25/#Mitigations
https://www.owasp.org/images/0/08/OWASP_SCP_Quick_Reference_Guide_v2.pdf
DbC also encourages proper defense in depth, since users must think
"where is the
best place for defense in depth?" with DbC.
These helps users to adopt desirable secure and efficient
application architecture. This
cannot be accomplished only by assert().
- Recursion
Since DbC evaluate contracts automatically, certain code may lead to
infinite recursion.
Most obvious is calling itself. e.g.
myMethod() {
require(MyMethod());
}
We don't need protections for bad code.
- Clearness:
Interface/trait support. I suppose it is. Am I correct?
Normal function support may not be obvious for people didn't involve
discussion.
Global invariant (main function invariant). This is not supported.
- Future scope:
Internal module class/interface support. e.g. SessionHandlerInterface
Someone may insist immutable over invariant. Immutable and invariant
is not the
same for me. It may be better to state "immutables" as stricter
constraint.
Joe, could you add some them? You do better job than me :) I don't mind
whichever
you pick. These are not mandatory.
==Ideas for open issues==
- Contracts inheritance rules
Invariant should be implicit like D and Eiffel and evaluated always under
DbC mode.
For method calls, overridden method should not evaluate parents contract on
entry.
It should be evaluated when parent method is called.
D had restriction to call public methods from invaliant. Calling public
method from
invariant might be better to be restricted. It might be OK to allow user to
shoot
their own foot since user can do that with protected/private method anyway.
- Consider introduction of static require() as class invariant for static
methods
I probably don't understand the idea correctly. Could you give some
explanations?
- Need to discuss syntax
There were many ideas for possible syntaxes, I prefer current simple syntax.
Syntax is not my priority. I don't mind require{assert();},
return{assert();}, etc.
Since "error message" can be added and any expression is allowed, writing
contracts
as code may be better. We are better to avoid new keyword whenever it's
possible.
- How to manage votes for 2 RFCs
Both RFCs are large enough. How about make vote only RFC
https://wiki.php.net/rfc/dbc_vote
- Explain what is DbC.
- Choose "Introduce Native DbC for PHP - Yes or No"
- For people voted for Yes, "Annotation or Code" refer
links to https://wiki.php.net/rfc/dbc,
https://wiki.php.net/rfc/dbc2
- Choose "Annotation or Code"
==Annotation DbC Implementation==
Dmitry, I guess it wouldn't be too hard for you to implement this RFC. How
about annotation
version? Can it be implemented with reasonable amount of efforts?
Thank you all those who are contributed discussion!
I hope you choose to have DbC support. DbC helps to achieve "strict/precise
development"
and "maximum performance in production" at the same time.
Regards,
P.S. It takes time to get used to new syntax. We may be better try to
expose new syntax
as much as possible. i.e. Put new syntax in mails whenever possible.
Native DbC support syntax:
class Child {
require($this->age < 18); // Invariant (Class state condition)
public function someMethod($input)
require(somethingAbout($input)) // Precondition
return($ret, somethingReturn($ret)) // Postcondition
{
/* Great! We are certain that caller satisfy precondition, return
appropriate return value and have proper class state! */
}
}
--
Yasuo Ohgaki
[email protected]