Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:129693 X-Original-To: internals@lists.php.net Delivered-To: internals@lists.php.net Received: from php-smtp4.php.net (php-smtp4.php.net [45.112.84.5]) by lists.php.net (Postfix) with ESMTPS id A76EA1A00BC for ; Fri, 26 Dec 2025 17:57:17 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=php.net; s=mail; t=1766771842; bh=/LRDPq0hhSgqLUgxJfUlHkevujaKb18KQkCmF7AA+R8=; h=References:In-Reply-To:From:Date:Subject:To:Cc:From; b=dDywQRADXzVP1iKAGhOmmp+ogd4DfsJrAjGs29dv37bSUUBIMdmM+glUpetwbwukz t+pSCtizeYaH11Um7e702znBrTyXWvFoyUeQc63jZklhpTOodPj09x0xtl3N8KwJ9n +UQE/+NPovcbrKIwKCD/Bn7DiYW4IWdeM4T6Ss6IPaM0IDCS6+QJGK+kbcMxHmD9e6 kfcmIMT8IgdBraF8qzBH0fx+i8QZbQZAVnzwk3FUXAYZUDRLnS2u/Dd/9kx5JBrTRj kLPViUDuTnjgvhzjiwkdBPy4fh+jsi6GCBzyhy5xZ/jwSPSCozx8TiGMeA8vnXByk5 PngsGLA/eTRUw== Received: from php-smtp4.php.net (localhost [127.0.0.1]) by php-smtp4.php.net (Postfix) with ESMTP id 138FB180041 for ; Fri, 26 Dec 2025 17:57:18 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 4.0.1 (2024-03-25) on php-smtp4.php.net X-Spam-Level: * X-Spam-Status: No, score=1.8 required=5.0 tests=BAYES_50,DMARC_NONE, FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM,HEADER_FROM_DIFFERENT_DOMAINS, HTML_MESSAGE,RCVD_IN_DNSWL_NONE,RCVD_IN_MSPIKE_H3,RCVD_IN_MSPIKE_WL, SPF_HELO_NONE,SPF_PASS autolearn=no autolearn_force=no version=4.0.1 X-Spam-Virus: No X-Envelope-From: Received: from mail-oa1-f52.google.com (mail-oa1-f52.google.com [209.85.160.52]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by php-smtp4.php.net (Postfix) with ESMTPS for ; Fri, 26 Dec 2025 17:57:17 +0000 (UTC) Received: by mail-oa1-f52.google.com with SMTP id 586e51a60fabf-3f13043e2fdso2408256fac.1 for ; Fri, 26 Dec 2025 09:57:12 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1766771832; x=1767376632; h=cc:to:subject:message-id:date:from:in-reply-to:references :mime-version:x-gm-gg:x-gm-message-state:from:to:cc:subject:date :message-id:reply-to; bh=wScZfTpGIqD12pZN6v0IrXpWNnJgbGJjusbzgg3G9Wc=; b=SMWRd/EqBH1RoUQ1FzMCd8z9sp0yXZJ0tRlU50a00S9JpglpOAZ7tkdeQILzZ5HuPe xjmIdf5OyXMxofOZDY2OejVrLSSG/RoYTRWW1QmeFRxTq8uHqhsliiTVAbfCW8az4M+1 95buGmtHLpBgdw2zYLMXtJRTN78OopFSKyfJ2nYfSren8v8hDO75urppEZxT25WrjuU1 h8rI6teHm+MZxENCpr5utTeeVn+x3mTrc7T+SMfrlZ2yUpcg+xXSk9nD4VLDabSyOj0W TUJIjqdtyTYpJ6bUpzDwk5u/oJLeIIaJAzvb8o20QXXYcAnrb5zPkxdk+IzDp+1bdO2s I38A== X-Gm-Message-State: AOJu0YyUkfXSI+Kd3xlRvOoRByA9C8HhfbB2+jmgp5w14TKorkNRPA1U bP0CMP4wwDE961fVQSvhwy0Vsu+K4eoPtbN5WyburJoNSCWrx5T4U4rdNjECJduoXpmQmyGckMF 2YYjKybbHMkG/37OP69yiySStLe/w/TRckS2B X-Gm-Gg: AY/fxX5KabjOiTSTs/HHB+k1mnPMSRCJhhBt+wy8jnG3nHgakJz2+iOqVb6v2DjyH8v k/pZTnbkJeVWaWCopp4vplcKU/1vO0vKq8iqW2DPWITFfPZqq1Rz667MB4w0d3MjBmJ0qK4fPFv QM34xGd2+zxpvKXqrfIuDnChSGsuSneJepxpZxsSuHLo+Kw8KouS6rTQMGjnYuL84QLOqtb4D9O i8ozCQOy8cUJUZSZXtYRRIej4o7Yz3M1Ai002+GCJms72dOOI/QHi8juN33W22EQf8sRkIGSPiY 7MT3 X-Google-Smtp-Source: AGHT+IGTgzIdTiEOMG9TiY0cy5pdEnqpFv6fPoc1lk4D/CKrNhfLd7x++QrkTvAdwpqy58rxA+tmLKiemWJge+QzdGE= X-Received: by 2002:a05:6820:8307:b0:65d:72a:97c7 with SMTP id 006d021491bc7-65d0e970fe2mr5310724eaf.25.1766771831936; Fri, 26 Dec 2025 09:57:11 -0800 (PST) Precedence: list list-help: list-unsubscribe: list-post: List-Id: x-ms-reactions: disallow MIME-Version: 1.0 References: In-Reply-To: Date: Fri, 26 Dec 2025 18:57:00 +0100 X-Gm-Features: AQt7F2qENfbfd0-_ik82cxO2RvNhXe4tvCAOPPVuvS1HTcU00IVNhOpnKlNLXrU Message-ID: Subject: Re: [PHP-DEV] [RFC] Polling API To: =?UTF-8?Q?Tim_D=C3=BCsterhus?= Cc: PHP internals list Content-Type: multipart/alternative; boundary="000000000000711b7f0646de9fe2" From: bukka@php.net (Jakub Zelenka) --000000000000711b7f0646de9fe2 Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable On Fri, Oct 31, 2025 at 1:06=E2=80=AFPM Jakub Zelenka wrote= : > Hi, > > On Fri, Oct 31, 2025 at 10:40=E2=80=AFAM Tim D=C3=BCsterhus wrote: > >> Hi >> >> Am 2025-10-30 22:06, schrieb Jakub Zelenka: >> > I would like to introduce a new polling API RFC that is part of my >> > stream >> > evolution work: >> > >> > https://wiki.php.net/rfc/poll_api >> >> 1. >> >> Thank you for the RFC. I've taken a first skim of the proposal and it >> immediately raised the question of naming and namespacing in particular. >> Our naming policy at >> https://github.com/php/policies/blob/main/coding-standards-and-naming.rs= t#bundled-ewill >> be alwaysxtensions >> >> says that =E2=80=9Cnamespaces SHOULD be used=E2=80=9D and given that thi= s is a >> completely new API, I think we should namespace them. >> >> My understanding is that the proposed API relies on a file descriptor >> and not something like a timeout. It therefore makes sense to me to put >> it into a `namespace Io\Poll;` or similar. We would then also have: >> >> namespace Io; >> class IoException extends \Exception {} >> namespace Io\Poll; >> class PollException extends \Io\IoException {} >> >> > I thought about this and think this might be a good idea. > > This is implemented as suggested and RFC updated. > >> The StreamPollHandle method should possibly be placed in the global >> namespace still, since the stream functions are sitting there - and a >> SocketPollHandle would of course be sitting in the namespace of the >> Sockets extension. >> > > Yeah those could stay in global and just extend Io\Poll\Handle. > > >> 2. As for the PollBackend enum. >> >> Is there a reason why this is a backed enum? Generally speaking enums >> should not be backed, unless there is a good reason for this. I don't >> think there is in this case - and none of the native enums are backed so >> far. >> >> > I missed that they should not be backed. I just saw `enum AdjacentPositio= n > : string` in Dom so thought that it's fine to use it... Will change it. > > This is also fixed and it's no longer a backed enum. > 3. Exception-wise. >> >> StreamPollHandle::__construct(): This should probably be a ValueError, >> not a PollException, since passing an invalid stream is a programmer >> error. >> > > This makes sense. > > >> >> In the other cases it probably makes sense to further split the >> PollException into purpose-built exceptions according to the Throwable >> policy at >> >> https://github.com/php/policies/blob/main/coding-standards-and-naming.rs= t#throwables >> (=E2=80=9CThe exception message MUST NOT be the only means of distinguis= hing >> exception causes that the user might want to handle differently.=E2=80= =9D). >> >> > This makes sense and I will introduce more exceptions. I will not use > exception per errno but some middle ground is a good idea. Maybe per op > exception with codes representing specific errors would be make sense? > > I created a new exception hierarchy that is hopefully in line with Throwable policy. > As an example PollContext::__construct() should probably throw a >> BackendUnavailableException or something like this. > > There are now getAvailableBackends so users should check it out before so I used ValueError for this part. > >> 4. PollBackend >> >> Is the availability of the backends known at compile time of PHP or at >> runtime only? Depending on that it might make sense to only >> conditionally define the enum cases, allowing users to check >> availability with `defined()` or checking the output of `::cases()`. >> Alternatively, a `public static function getAvailableBackends(): array` >> could be added. >> >> > It's compile time but not sure if I like exposing enum only if compiled i= n > as it makes the checks harder. This part is not really something that > users should use but it's really more for testing purpose. In reality > everyone should just use default Auto... But getAvailableBackends() might > make sense even for testing. Maybe it could also have per enum method > isAvailable() so user can check that but not sure if it's needed. > > Added getAvailableBackends(), isAvailable() and supportsEdgeTriggering() methods. Kind regards, Jakub --000000000000711b7f0646de9fe2 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable
On Fri, Oct 31, 2025 at 1:06=E2=80=AFPM J= akub Zelenka <bukka@php.net> wro= te:
Hi,=

= On Fri, Oct 31, 2025 at 10:40=E2=80=AFAM Tim D=C3=BCsterhus <tim@bastelstu.be> wrote:<= br>
Hi

Am 2025-10-30 22:06, schrieb Jakub Zelenka:
> I would like to introduce a new polling API RFC that is part of my > stream
> evolution work:
>
> https://wiki.php.net/rfc/poll_api

1.

Thank you for the RFC. I've taken a first skim of the proposal and it <= br> immediately raised the question of naming and namespacing in particular. Our naming policy at
https://= github.com/php/policies/blob/main/coding-standards-and-naming.rst#bundled-e= will be alwaysxtensions
says that =E2=80=9Cnamespaces SHOULD be used=E2=80=9D and given that this i= s a
completely new API, I think we should namespace them.

My understanding is that the proposed API relies on a file descriptor
and not something like a timeout. It therefore makes sense to me to put it into a `namespace Io\Poll;` or similar. We would then also have:

=C2=A0 =C2=A0 =C2=A0namespace Io;
=C2=A0 =C2=A0 =C2=A0class IoException extends \Exception {}
=C2=A0 =C2=A0 =C2=A0namespace Io\Poll;
=C2=A0 =C2=A0 =C2=A0class PollException extends \Io\IoException {}


I thought about this and think this mi= ght be a good idea.

=C2=A0
This is implemented as suggested and RFC updated.

=C2=A0
The StreamPollHandle method should possibly be placed in the global
namespace still, since the stream functions are sitting there - and a
SocketPollHandle would of course be sitting in the namespace of the
Sockets extension.

Yeah those could sta= y in global and just extend Io\Poll\Handle.
=C2=A0
2. As for the PollBackend enum.

Is there a reason why this is a backed enum? Generally speaking enums
should not be backed, unless there is a good reason for this. I don't <= br> think there is in this case - and none of the native enums are backed so far.


I missed that they should not be backe= d. I just saw `enum AdjacentPosition : string` in Dom so thought that it= 9;s fine to use it... Will change it.
=C2=A0

This is also fixed and it's no long= er a backed enum.
=C2=A0
3. Exception-wise.

StreamPollHandle::__construct(): This should probably be a ValueError,
not a PollException, since passing an invalid stream is a programmer
error.

This makes sense.
=C2= =A0

In the other cases it probably makes sense to further split the
PollException into purpose-built exceptions according to the Throwable
policy at
https://github.c= om/php/policies/blob/main/coding-standards-and-naming.rst#throwables (=E2=80=9CThe exception message MUST NOT be the only means of distinguishin= g
exception causes that the user might want to handle differently.=E2=80=9D).=


This makes sense and I will introduce = more exceptions. I will not use exception per errno but some middle ground = is a good idea. Maybe per op exception with codes representing specific err= ors would be make sense?
=C2=A0

I created a new exception hierarchy that is hopefull= y in line with=C2=A0Throwable policy.
=C2=A0
As an example PollContext::__construct() should probably throw a
BackendUnavailableException or something like this.

There are now getAvailableBackends= so users should check it out before so I used ValueError for this part.
=C2=A0

4. PollBackend

Is the availability of the backends known at compile time of PHP or at
runtime only? Depending on that it might make sense to only
conditionally define the enum cases, allowing users to check
availability with `defined()` or checking the output of `::cases()`.
Alternatively, a `public static function getAvailableBackends(): array` could be added.


It's compile ti= me but not sure if I like exposing enum only if compiled in as it makes the= checks harder.=C2=A0 This part is not really something that users should u= se but it's really more for testing purpose. In reality everyone should= just use default Auto... But=C2=A0getAvailableBackends() might make sense = even for testing. Maybe it could also have per enum method isAvailable() so= user can check that but not sure if it's needed.

<= /div>

Added=C2=A0=C2=A0getAvail= ableBackends(),=C2=A0isAvailable() and=C2=A0supportsEdgeTriggering() method= s.

Kind regards,

Jakub
--000000000000711b7f0646de9fe2--