[PHP-DEV] [RFC][DISCUSSION] Object-oriented curl API v2

On Fri, Jun 27, 2025, at 4:58 PM, Ayesh Karunaratne wrote:

However, I softly oppose this RFC in its current state and the way it
seems to be going.

So I think we've identified a key disagreement about not just the goal, but the intent. To what extent should PHP core ship with a usable HTTP client?

Right now it ships with Curl, which... in its current form is not usable. It's a low-level tool with an inscrutable API we inherited from C. It's not viable as a user-facing tool. It's a tool that's only useful to people writing client libraries like Guzzle or CurlClass or Symfony HTTP or such.

On the one hand, Marco is correct that for a web-centric language to not ship with a non-sucky way to send web requests is... kinda embarrassing. Even if the use cases where you can't install a 3rd party library are few, they are non-zero. And that also doesn't help new users figure out what to use. (Eg, the person who wrote most of the code for our main application at work, learning PHP as he went, is sending lots of requests using... an ungodly mess of curl that can't even understand. Because he didn't know that things like Guzzle even existed.)

On the other hand, Ben is correct that an HTTP client is a not-small task, with a very deep rabbit hole.

So there's two closely related but distinct asks here:

1. Make working with curl suck less (giving it an OOP interface is part of that but not all)
2. Ship a useful first-party HTTP client that can handle the 80% case, even if it's not full featured.

Beefing up Curl's interface until it fulfills part 2 is one approach, but not the only.

At one extreme would be the "do nothing, status quo is fine" position. Ayesh seems to be close to that position, maybe with a little polish for funsies. The other extreme would essentially be "Guzzle in core," which I don't think anyone is advocating. Where between those extremes we should land is debatable.

Personally I'm of the mind that a simple, basic-features HTTP client in core would be a good thing; that's central enough that it should not be left to userland. It doesn't need to offer every possible feature; no need for async multiplexing, for example. But sending GET and POST requests with straightforward bodies should be table-stakes for a web language, and right now, that's a second class citizen. If it's written in such a way that it can be extended easily in user-space, so much the better.

Whether that basic-features client is Curl itself or a bundled wrapper that uses Curl, I have no strong preference. The challenge of making it separate from Curl is, shocker, that it's bikeshed bait. Does that imply using the new URL/URI classes? Does it imply we need request/response objects? The rabbit hole indeed gets deep fast.

So the first question, I think, is what is the consensus between these three coarse-grained positions:

1. Status quo is fine. PHP core not having a user-friendly way to send HTTP requests is acceptable. Maybe make Curl a little nicer, but only to make life easier for Guzzle et al.
2. We should develop the Curl API until it's usable for basic HTTP behavior, but no further.
3. We should bundle an HTTP client that wraps Curl (with or without minor improvements to Curl), exact scope TBD.

Personally, I'm open to either 2 or 3. 3 is more bikesheddable, but possibly the better end result.

Where does everyone else stand?

--Larry Garfield

On Jun 28, 2025, at 00:01, Larry Garfield <larry@garfieldtech.com> wrote:

On Fri, Jun 27, 2025, at 4:58 PM, Ayesh Karunaratne wrote:

However, I softly oppose this RFC in its current state and the way it
seems to be going.

So I think we've identified a key disagreement about not just the goal, but the intent. To what extent should PHP core ship with a usable HTTP client?

Right now it ships with Curl, which... in its current form is not usable. It's a low-level tool with an inscrutable API we inherited from C. It's not viable as a user-facing tool. It's a tool that's only useful to people writing client libraries like Guzzle or CurlClass or Symfony HTTP or such.

On the one hand, Marco is correct that for a web-centric language to not ship with a non-sucky way to send web requests is... kinda embarrassing. Even if the use cases where you can't install a 3rd party library are few, they are non-zero. And that also doesn't help new users figure out what to use. (Eg, the person who wrote most of the code for our main application at work, learning PHP as he went, is sending lots of requests using... an ungodly mess of curl that can't even understand. Because he didn't know that things like Guzzle even existed.)

On the other hand, Ben is correct that an HTTP client is a not-small task, with a very deep rabbit hole.

So there's two closely related but distinct asks here:

1. Make working with curl suck less (giving it an OOP interface is part of that but not all)
2. Ship a useful first-party HTTP client that can handle the 80% case, even if it's not full featured.

Beefing up Curl's interface until it fulfills part 2 is one approach, but not the only.

At one extreme would be the "do nothing, status quo is fine" position. Ayesh seems to be close to that position, maybe with a little polish for funsies. The other extreme would essentially be "Guzzle in core," which I don't think anyone is advocating. Where between those extremes we should land is debatable.

Personally I'm of the mind that a simple, basic-features HTTP client in core would be a good thing; that's central enough that it should not be left to userland. It doesn't need to offer every possible feature; no need for async multiplexing, for example. But sending GET and POST requests with straightforward bodies should be table-stakes for a web language, and right now, that's a second class citizen. If it's written in such a way that it can be extended easily in user-space, so much the better.

Whether that basic-features client is Curl itself or a bundled wrapper that uses Curl, I have no strong preference. The challenge of making it separate from Curl is, shocker, that it's bikeshed bait. Does that imply using the new URL/URI classes? Does it imply we need request/response objects? The rabbit hole indeed gets deep fast.

So the first question, I think, is what is the consensus between these three coarse-grained positions:

1. Status quo is fine. PHP core not having a user-friendly way to send HTTP requests is acceptable. Maybe make Curl a little nicer, but only to make life easier for Guzzle et al.
2. We should develop the Curl API until it's usable for basic HTTP behavior, but no further.
3. We should bundle an HTTP client that wraps Curl (with or without minor improvements to Curl), exact scope TBD.

Personally, I'm open to either 2 or 3. 3 is more bikesheddable, but possibly the better end result.

Where does everyone else stand?

--Larry Garfield

I’m also open to 2 or 3, but 3 sounds more like something that I think should live in userland, so I lean much more towards 2.

Cheers,
Ben

However, I softly oppose this RFC in its current state and the way it
seems to be going.

So I think we’ve identified a key disagreement about not just the goal, but the intent. To what extent should PHP core ship with a usable HTTP client?

Right now it ships with Curl, which… in its current form is not usable. It’s a low-level tool with an inscrutable API we inherited from C. It’s not viable as a user-facing tool. It’s a tool that’s only useful to people writing client libraries like Guzzle or CurlClass or Symfony HTTP or such.

On the one hand, Marco is correct that for a web-centric language to not ship with a non-sucky way to send web requests is… kinda embarrassing. Even if the use cases where you can’t install a 3rd party library are few, they are non-zero. And that also doesn’t help new users figure out what to use. (Eg, the person who wrote most of the code for our main application at work, learning PHP as he went, is sending lots of requests using… an ungodly mess of curl that can’t even understand. Because he didn’t know that things like Guzzle even existed.)

On the other hand, Ben is correct that an HTTP client is a not-small task, with a very deep rabbit hole.

So there’s two closely related but distinct asks here:

  1. Make working with curl suck less (giving it an OOP interface is part of that but not all)
  2. Ship a useful first-party HTTP client that can handle the 80% case, even if it’s not full featured.

Beefing up Curl’s interface until it fulfills part 2 is one approach, but not the only.

At one extreme would be the “do nothing, status quo is fine” position. Ayesh seems to be close to that position, maybe with a little polish for funsies. The other extreme would essentially be “Guzzle in core,” which I don’t think anyone is advocating. Where between those extremes we should land is debatable.

Personally I’m of the mind that a simple, basic-features HTTP client in core would be a good thing; that’s central enough that it should not be left to userland. It doesn’t need to offer every possible feature; no need for async multiplexing, for example. But sending GET and POST requests with straightforward bodies should be table-stakes for a web language, and right now, that’s a second class citizen. If it’s written in such a way that it can be extended easily in user-space, so much the better.

Whether that basic-features client is Curl itself or a bundled wrapper that uses Curl, I have no strong preference. The challenge of making it separate from Curl is, shocker, that it’s bikeshed bait. Does that imply using the new URL/URI classes? Does it imply we need request/response objects? The rabbit hole indeed gets deep fast.

So the first question, I think, is what is the consensus between these three coarse-grained positions:

  1. Status quo is fine. PHP core not having a user-friendly way to send HTTP requests is acceptable. Maybe make Curl a little nicer, but only to make life easier for Guzzle et al.
  2. We should develop the Curl API until it’s usable for basic HTTP behavior, but no further.
  3. We should bundle an HTTP client that wraps Curl (with or without minor improvements to Curl), exact scope TBD.

Personally, I’m open to either 2 or 3. 3 is more bikesheddable, but possibly the better end result.

Where does everyone else stand?

–Larry Garfield

I think #2 is the way to go. I personally just use Symfony’s HTTP Client 99.9% of the time - there is one exception in recent years where I had to go low-level cURL and craft an extremely specific HTTP request. Yes, it is a SOAP service for a government system, because of course it is.

I’m not even sure it’s a good idea to add those namespaced options: using CURLOPT_SSL_VERIFYHOST is perfect to find the corresponding curl documentation with your favorite search engine. php’s doc is awesome, but it cannot compete with the details provided by curl’s doc on the topic.

Valid. This cannot be avoided if any kind of RFC is to be accepted, so I think the next best solution is to put effort into documentation and ensure that things are referenced (like the new Enum options having very obvious links to the original constants and to the curl documentation), making discoverability easy.
The good thing is that OOP API is purely new, so there is not going to be tons of old content about it to make things messy.

···

Arvīds Godjuks+371 26 851 664
arvids.godjuks@gmail.com
Telegram: @psihius https://t.me/psihius

Hi

Am 2025-06-26 18:53, schrieb Larry Garfield:

2. Please don't name the exception "Exception". It needs some slightly more useful name, to avoid confusion in a file that also uses \Exception.

More specifically, since it does introduce an entirely new namespace it should be considered a “new extension” and must therefore follow the Exception policy outlined in: policies/coding-standards-and-naming.rst at main · php/policies · GitHub

Best regards
Tim Düsterhus

More specifically, since it does introduce an entirely new namespace it
should be considered a “new extension” and must therefore follow the
Exception policy outlined in:
policies/coding-standards-and-naming.rst at main · php/policies · GitHub

Embarrassingly, I had read your RFC adding that section - it's kind of
what got me thinking about adding a curl namespace in the first place!
- but I guess I didn't put it into long-term memory. Thanks for the
catch, I'll update that when I can.

Thanks for your response Ayesh! I hope to see this RFC on php.watch :slight_smile:

However, I softly oppose this RFC in its current state and the way it
seems to be going.

I have pushed Curl and libcurl to some uncommon cases such as HTTP/3,
DoH, the new debug callback (which I authored the PR for), IMAP, and a
few other obscure tweaks. For all of them, the current `curl_setopt`
worked, and the more I used it, the more I understood that having just
a few Curl functions and a sea of Curl options is the least
"presumptive way", regardless of the protocol and the options Curl
provides.

The extension is named `Curl`, because it's supposed to provide Curl
functionality into PHP. It provides low-level functionality, but we
should leave it to the PHP users to build the libraries that have
fluent APIs.

It would be helpful for me to understand what specifically you are
objecting to in the current discussion, putting aside the suggested
enumeration changes. Do you object to any HTTP-oriented methods at
all, like something to set the HTTP method? Would you object to
methods that apply to all, or nearly all, transport types, like a
setTimeout() method?

I think a more light-weight approach would be to:

- Move all of them to the `\Curl` namespace.
- Rename Curl options to `\Curl\Option` namespace, and rename them,
so that `CURLOPT_SSL_VERIFYHOST` becomes `Curl\Option\SSL_VERIFYHOST`
- Rename Curl error codes to similar `\Curl\Error` constants.
- Have the `CurlHandle` object accept options, e.g.
`$ch->setOption(Curl\Option\SSL_VERIFYHOST, 2)`. libcurl Easy handlers
do not have a way to retrieve the option once it's set, so there will
be no `getOption` either.
- Make Curl throw exceptions, and never `false` on `\Curl\execute()`,
with the Exception's error code and message mapped to the Curl error
code and message. We will not need to bring over `curl_error` or
`curl_errno` functions.

Acknowledged, thank you. The RFC does propose what you're suggesting
with never returning false and instead throwing exceptions, but it
feels like it might still be useful to have properties on the actual
object. Do you have opinions on that?

Realistically, I don't think we can deprecate and remove the `\curl_*`
functions any time soon, so this will actually add more maintenance
work for php-src at the end too.

Agreed, I do not plan on suggesting this, not even under Future Scope.

I'm not even sure it's a good idea to add those namespaced options: using CURLOPT_SSL_VERIFYHOST is perfect to find the corresponding curl documentation with your favorite search engine. php's doc is awesome, but it cannot compete with the details provided by curl's doc on the topic.

That's a good point, but I do feel like there is value in having these
under a namespace; a part of the reason I am interested in this
proposal is that I'd like to see more of PHP core living under
namespaces, since I think it will present a more consistent vision of
the "standard library". I wonder if there is a way we could preserve
the link, at least? In my proposal, the enum values are equivalent to
their curl constant equivalents, which I thought would help with
discoverability in the documentation.

For the record - and I'll say this elsewhere - based on the discussion
so far I am planning on withdrawing the proposal for separate enums.
I'm still considering using a single enum to group all of these
options, however, instead of constants.

Thanks for your thoughtful response, Larry! I agree with your summary.

1. Status quo is fine. PHP core not having a user-friendly way to send HTTP requests is acceptable. Maybe make Curl a little nicer, but only to make life easier for Guzzle et al.
2. We should develop the Curl API until it's usable for basic HTTP behavior, but no further.
3. We should bundle an HTTP client that wraps Curl (with or without minor improvements to Curl), exact scope TBD.

Personally, I'm open to either 2 or 3. 3 is more bikesheddable, but possibly the better end result.

Where does everyone else stand?

Based on the feedback so far (I do plan on waiting for more responses
to your email), and on my own preferences, I wonder if there is a
hybrid option I could propose. Perhaps the RFC could offer both a
\Curl\Handle (tentative name) to address position 1, and a
\Curl\BasicHttpHandle (also tentative name) that addresses position 2?
If people were amenable, I'd even make the BasicHttpHandle a separate
vote.

I agree that 3 is both more bikesheddable and also possibly ideal, but
I feel my above suggestion maybe strikes the right balance between the
"status quo is fine, I don't want to see random HTTP-related methods
on my low(est)-level curl object" and the "I'd like to do basic HTTP
stuff with curl, without a library" crowds.

Barring that, my preference would be 2, but I'd accept 1 just to have
it pass - like I mentioned elsewhere, I think there is value in
introducing namespaces and object-oriented APIs for "modernization"
and language consistency reasons.

Based on the feedback so far (I do plan on waiting for more responses
to your email), and on my own preferences, I wonder if there is a
hybrid option I could propose. Perhaps the RFC could offer both a
\Curl\Handle (tentative name) to address position 1, and a
\Curl\BasicHttpHandle (also tentative name) that addresses position 2?
If people were amenable, I'd even make the BasicHttpHandle a separate
vote.

I agree that 3 is both more bikesheddable and also possibly ideal, but
I feel my above suggestion maybe strikes the right balance between the
"status quo is fine, I don't want to see random HTTP-related methods
on my low(est)-level curl object" and the "I'd like to do basic HTTP
stuff with curl, without a library" crowds.

Barring that, my preference would be 2, but I'd accept 1 just to have
it pass - like I mentioned elsewhere, I think there is value in
introducing namespaces and object-oriented APIs for "modernization"
and language consistency reasons.

Having thought about this some more, while I'm still feeling somewhat
positive about my suggestion I'm just not sure it's the best way to
proceed. I started to sketch what a BasicHttpHandle class would look
like, and I'm stuck on how to get data about the response out of the
class.

Naively, we could have $response_status_code and $response_headers
properties, and have the same fetch() and execute() methods I
suggested elsewhere to get the response body. Alternatively, we could
return a simple CurlHttpResponse object which contains all three
properties in the fetch() and execute() implementations for the
BasicHttpHandle class.

Both of these are fine, but they would lock us out of being PSR7
compatible. I think that people would probably desire PSR7
compatibility, and I would feel uncomfortable with eliminating or
tainting the possibility of achieving this. For example, if we had
this BasicHttpHandle and then later introduced PSR7 response objects,
we'd need to either break backwards compatibility for the class, or
introduce a second class. We could also go straight to returning a
PSR7 compatible response for the BasicHttpHandle class, but I think
that likely deserves its own RFC.

So in closing, if people felt generally okay with the limitation of
not being PSR7 compatible, I'd probably still add some form of my
BasicHttpHandle suggestion as a secondary vote. If people thought PSR7
was necessary, I'd drop it, and leave a PSR7-in-core RFC for the
future. In that case, I'd go with Larry's option 1 for the RFC; I've
currently updated the RFC to match that option for now.

On Jul 2, 2025, at 10:48, Eric Norris <eric.t.norris@gmail.com> wrote:

Based on the feedback so far (I do plan on waiting for more responses
to your email), and on my own preferences, I wonder if there is a
hybrid option I could propose. Perhaps the RFC could offer both a
\Curl\Handle (tentative name) to address position 1, and a
\Curl\BasicHttpHandle (also tentative name) that addresses position 2?
If people were amenable, I'd even make the BasicHttpHandle a separate
vote.

I agree that 3 is both more bikesheddable and also possibly ideal, but
I feel my above suggestion maybe strikes the right balance between the
"status quo is fine, I don't want to see random HTTP-related methods
on my low(est)-level curl object" and the "I'd like to do basic HTTP
stuff with curl, without a library" crowds.

Barring that, my preference would be 2, but I'd accept 1 just to have
it pass - like I mentioned elsewhere, I think there is value in
introducing namespaces and object-oriented APIs for "modernization"
and language consistency reasons.

Having thought about this some more, while I'm still feeling somewhat
positive about my suggestion I'm just not sure it's the best way to
proceed. I started to sketch what a BasicHttpHandle class would look
like, and I'm stuck on how to get data about the response out of the
class.

Naively, we could have $response_status_code and $response_headers
properties, and have the same fetch() and execute() methods I
suggested elsewhere to get the response body. Alternatively, we could
return a simple CurlHttpResponse object which contains all three
properties in the fetch() and execute() implementations for the
BasicHttpHandle class.

Both of these are fine, but they would lock us out of being PSR7
compatible. I think that people would probably desire PSR7
compatibility, and I would feel uncomfortable with eliminating or
tainting the possibility of achieving this. For example, if we had
this BasicHttpHandle and then later introduced PSR7 response objects,
we'd need to either break backwards compatibility for the class, or
introduce a second class. We could also go straight to returning a
PSR7 compatible response for the BasicHttpHandle class, but I think
that likely deserves its own RFC.

So in closing, if people felt generally okay with the limitation of
not being PSR7 compatible, I'd probably still add some form of my
BasicHttpHandle suggestion as a secondary vote. If people thought PSR7
was necessary, I'd drop it, and leave a PSR7-in-core RFC for the
future. In that case, I'd go with Larry's option 1 for the RFC; I've
currently updated the RFC to match that option for now.

I think it’s good to keep PSR-7 in mind when designing the interface, but I don’t think it’s necessary to strive for 100% compatibility. Userland will end up writing wrappers for it that implement PSR-7. IMO, the interface should attempt to more closely follow curl nomenclature and idioms, since it’s an interface for interacting with curl.

Cheers,
Ben

On Wed, Jul 2, 2025, at 10:48 AM, Eric Norris wrote:

Based on the feedback so far (I do plan on waiting for more responses
to your email), and on my own preferences, I wonder if there is a
hybrid option I could propose. Perhaps the RFC could offer both a
\Curl\Handle (tentative name) to address position 1, and a
\Curl\BasicHttpHandle (also tentative name) that addresses position 2?
If people were amenable, I'd even make the BasicHttpHandle a separate
vote.

I agree that 3 is both more bikesheddable and also possibly ideal, but
I feel my above suggestion maybe strikes the right balance between the
"status quo is fine, I don't want to see random HTTP-related methods
on my low(est)-level curl object" and the "I'd like to do basic HTTP
stuff with curl, without a library" crowds.

Barring that, my preference would be 2, but I'd accept 1 just to have
it pass - like I mentioned elsewhere, I think there is value in
introducing namespaces and object-oriented APIs for "modernization"
and language consistency reasons.

Having thought about this some more, while I'm still feeling somewhat
positive about my suggestion I'm just not sure it's the best way to
proceed. I started to sketch what a BasicHttpHandle class would look
like, and I'm stuck on how to get data about the response out of the
class.

Naively, we could have $response_status_code and $response_headers
properties, and have the same fetch() and execute() methods I
suggested elsewhere to get the response body. Alternatively, we could
return a simple CurlHttpResponse object which contains all three
properties in the fetch() and execute() implementations for the
BasicHttpHandle class.

Both of these are fine, but they would lock us out of being PSR7
compatible. I think that people would probably desire PSR7
compatibility, and I would feel uncomfortable with eliminating or
tainting the possibility of achieving this. For example, if we had
this BasicHttpHandle and then later introduced PSR7 response objects,
we'd need to either break backwards compatibility for the class, or
introduce a second class. We could also go straight to returning a
PSR7 compatible response for the BasicHttpHandle class, but I think
that likely deserves its own RFC.

So in closing, if people felt generally okay with the limitation of
not being PSR7 compatible, I'd probably still add some form of my
BasicHttpHandle suggestion as a secondary vote. If people thought PSR7
was necessary, I'd drop it, and leave a PSR7-in-core RFC for the
future. In that case, I'd go with Larry's option 1 for the RFC; I've
currently updated the RFC to match that option for now.

The question of PHP-native request/response objects has come up a couple of times, and even had an RFC that went to a vote (declined). My stance has been, and remains, that such objects do NOT need to match PSR-7... but they should be powerful enough to effectively replace/displace PSR-7. If it's just another backend that PSR-7 consumes, we've added very little to the ecosystem. If they're robust enough that they can replace PSR-7 and HttpFoundation in time, we've helped to standardize the ecosystem. (And FIG will be able to adapt, don't worry.)

(Eg, I would strongly recommend leveraging properties instead of methods for any built-in objects, which didn't exist when PSR-7 was written but now so; we should absolutely use the new built-in URI/URL classes instead of user-space ones, etc.)

Of course, as you can expect, "design and include request/response objects powerful enough to supplant PSR-7" is a non-small and highly bikesheddable topic, and PHP is notoriously structurally bad at being able to have those conversations. That's part of why it's never happened.

--Larry Garfield

On Wed, Jul 2, 2025, at 10:48 AM, Eric Norris wrote:

Having thought about this some more, while I'm still feeling somewhat
positive about my suggestion I'm just not sure it's the best way to
proceed. I started to sketch what a BasicHttpHandle class would look
like, and I'm stuck on how to get data about the response out of the
class.

Another thing I just realized. IF we have an in-core HTTP client we intend for end-users to use (as opposed to just a less-sucky Curl that only Guzzle and Symfony to use), it needs to have a defined interface to go along with it so that people can mock it for testing purposes. I would consider this a hard requirement for any "user facing" HTTP client.

--Larry Garfield

Hi all,

The question of PHP-native request/response objects has come up a couple of times, and even had an RFC that went to a vote (declined). My stance has been, and remains, that ... they should be powerful enough to effectively replace/displace PSR-7.

Where and when have you previously articulated that stance? Because I'd be thrilled to re-open yet another version (the 3rd) of that RFC.

-- pmj

On Wed, Jul 2, 2025, at 12:34 PM, Paul M. Jones wrote:

Hi all,

The question of PHP-native request/response objects has come up a couple of times, and even had an RFC that went to a vote (declined). My stance has been, and remains, that ... they should be powerful enough to effectively replace/displace PSR-7.

Where and when have you previously articulated that stance? Because I'd
be thrilled to re-open yet another version (the 3rd) of that RFC.

-- pmj

I believe I stated it (perhaps phrased differently, it's been a while) in the discussion thread of your previous RFC. And voted against the RFC on the grounds that I didn't feel it was robust enough to effectively replace PSR-7 and HttpFoundation.

--Larry Garfield

Hi all,

On Jul 2, 2025, at 12:41, Larry Garfield <larry@garfieldtech.com> wrote:

On Wed, Jul 2, 2025, at 12:34 PM, Paul M. Jones wrote:

Hi all,

The question of PHP-native request/response objects has come up a couple of times, and even had an RFC that went to a vote (declined). My stance has been, and remains, that ... they should be powerful enough to effectively replace/displace PSR-7.

Where and when have you previously articulated that stance? Because I'd
be thrilled to re-open yet another version (the 3rd) of that RFC.

-- pmj

I believe I stated it (perhaps phrased differently, it's been a while) in the discussion thread of your previous RFC.

You commented three times in that thread; the relevant one appears to be the second, and includes Symfony's HttpFoundation:

- RFC: Server-Side Request and Response Objects (v2) - Externals

- RFC: Server-Side Request and Response Objects (v2) - Externals "I would be very much in favor of a proposal that goes much further, with the aim that it can eventually deprecate PSR-7 and HttpFoundation, or at least large portions of them."

- RFC: Server-Side Request and Response Objects (v2) - Externals

I included that sentiment under "Disruptive to (or insufficiently unifying of) userland ecosystem" in the after-action on that RFC: <[RFC] [EPILOGUE] Server-Side Request and Response Objects (v2) - Externals.

To sum up: your position is that any HTTP-related offering here must be able to supplant both PSR-7 and HttpFoundation?

Further: now that Symfony has its own HttpClient, should that be supplanted as well?

And voted against the RFC on the grounds that I didn't feel it was robust enough to effectively replace PSR-7 and HttpFoundation.

You were not a voter at the time. Memories fade, I guess.

-- pmj

On Wed, Jul 2, 2025 at 11:48 AM Eric Norris <eric.t.norris@gmail.com> wrote:

> Based on the feedback so far (I do plan on waiting for more responses
> to your email), and on my own preferences, I wonder if there is a
> hybrid option I could propose. Perhaps the RFC could offer both a
> \Curl\Handle (tentative name) to address position 1, and a
> \Curl\BasicHttpHandle (also tentative name) that addresses position 2?
> If people were amenable, I'd even make the BasicHttpHandle a separate
> vote.
>
> I agree that 3 is both more bikesheddable and also possibly ideal, but
> I feel my above suggestion maybe strikes the right balance between the
> "status quo is fine, I don't want to see random HTTP-related methods
> on my low(est)-level curl object" and the "I'd like to do basic HTTP
> stuff with curl, without a library" crowds.
>
> Barring that, my preference would be 2, but I'd accept 1 just to have
> it pass - like I mentioned elsewhere, I think there is value in
> introducing namespaces and object-oriented APIs for "modernization"
> and language consistency reasons.

Having thought about this some more, while I'm still feeling somewhat
positive about my suggestion I'm just not sure it's the best way to
proceed. I started to sketch what a BasicHttpHandle class would look
like, and I'm stuck on how to get data about the response out of the
class.

Naively, we could have $response_status_code and $response_headers
properties, and have the same fetch() and execute() methods I
suggested elsewhere to get the response body. Alternatively, we could
return a simple CurlHttpResponse object which contains all three
properties in the fetch() and execute() implementations for the
BasicHttpHandle class.

Both of these are fine, but they would lock us out of being PSR7
compatible. I think that people would probably desire PSR7
compatibility, and I would feel uncomfortable with eliminating or
tainting the possibility of achieving this. For example, if we had
this BasicHttpHandle and then later introduced PSR7 response objects,
we'd need to either break backwards compatibility for the class, or
introduce a second class. We could also go straight to returning a
PSR7 compatible response for the BasicHttpHandle class, but I think
that likely deserves its own RFC.

So in closing, if people felt generally okay with the limitation of
not being PSR7 compatible, I'd probably still add some form of my
BasicHttpHandle suggestion as a secondary vote. If people thought PSR7
was necessary, I'd drop it, and leave a PSR7-in-core RFC for the
future. In that case, I'd go with Larry's option 1 for the RFC; I've
currently updated the RFC to match that option for now.

Thanks Ben, Larry, and Paul for your responses to my suggestion for a
BasicHttpHandle class. After reflecting further, I have decided to
move this to the Future Scope section, as it feels weighty enough to
stand as its own RFC. I'd like to think about this a bit more, but I
will note that having a Request and Response interface in core would
greatly simplify the proposal for a simple curl-based HTTP client, so
I'd likely support any effort on that front.

I've also updated the Curl\MultiHandle class proposal to account for
removing the CURLOPT_RETURNTRANSFER option.

At this point I believe the RFC is in a semi-final state at this
point, barring any additional discussion. Thanks all for the feedback
so far!

On Mon, Jul 7, 2025 at 12:53 PM Eric Norris <eric.t.norris@gmail.com> wrote:

On Wed, Jul 2, 2025 at 11:48 AM Eric Norris <eric.t.norris@gmail.com> wrote:
>
> > Based on the feedback so far (I do plan on waiting for more responses
> > to your email), and on my own preferences, I wonder if there is a
> > hybrid option I could propose. Perhaps the RFC could offer both a
> > \Curl\Handle (tentative name) to address position 1, and a
> > \Curl\BasicHttpHandle (also tentative name) that addresses position 2?
> > If people were amenable, I'd even make the BasicHttpHandle a separate
> > vote.
> >
> > I agree that 3 is both more bikesheddable and also possibly ideal, but
> > I feel my above suggestion maybe strikes the right balance between the
> > "status quo is fine, I don't want to see random HTTP-related methods
> > on my low(est)-level curl object" and the "I'd like to do basic HTTP
> > stuff with curl, without a library" crowds.
> >
> > Barring that, my preference would be 2, but I'd accept 1 just to have
> > it pass - like I mentioned elsewhere, I think there is value in
> > introducing namespaces and object-oriented APIs for "modernization"
> > and language consistency reasons.
>
> Having thought about this some more, while I'm still feeling somewhat
> positive about my suggestion I'm just not sure it's the best way to
> proceed. I started to sketch what a BasicHttpHandle class would look
> like, and I'm stuck on how to get data about the response out of the
> class.
>
> Naively, we could have $response_status_code and $response_headers
> properties, and have the same fetch() and execute() methods I
> suggested elsewhere to get the response body. Alternatively, we could
> return a simple CurlHttpResponse object which contains all three
> properties in the fetch() and execute() implementations for the
> BasicHttpHandle class.
>
> Both of these are fine, but they would lock us out of being PSR7
> compatible. I think that people would probably desire PSR7
> compatibility, and I would feel uncomfortable with eliminating or
> tainting the possibility of achieving this. For example, if we had
> this BasicHttpHandle and then later introduced PSR7 response objects,
> we'd need to either break backwards compatibility for the class, or
> introduce a second class. We could also go straight to returning a
> PSR7 compatible response for the BasicHttpHandle class, but I think
> that likely deserves its own RFC.
>
> So in closing, if people felt generally okay with the limitation of
> not being PSR7 compatible, I'd probably still add some form of my
> BasicHttpHandle suggestion as a secondary vote. If people thought PSR7
> was necessary, I'd drop it, and leave a PSR7-in-core RFC for the
> future. In that case, I'd go with Larry's option 1 for the RFC; I've
> currently updated the RFC to match that option for now.

Thanks Ben, Larry, and Paul for your responses to my suggestion for a
BasicHttpHandle class. After reflecting further, I have decided to
move this to the Future Scope section, as it feels weighty enough to
stand as its own RFC. I'd like to think about this a bit more, but I
will note that having a Request and Response interface in core would
greatly simplify the proposal for a simple curl-based HTTP client, so
I'd likely support any effort on that front.

I've also updated the Curl\MultiHandle class proposal to account for
removing the CURLOPT_RETURNTRANSFER option.

At this point I believe the RFC is in a semi-final state at this
point, barring any additional discussion. Thanks all for the feedback
so far!

I'd like to bring this to a vote since discussion has died down, but I
feel that I should implement the proposal before doing so. As always
this is the hard part, and since I'm back from an extended break at
work I will have less time to focus on this.

I've mentioned this before, but if anyone would like to collaborate on
the implementation, please reach out! Otherwise, I'll update this
thread with a link to the implementation at some point in the future,
give it a little more time for discussion, and bring the proposal to a
vote.

On Mon, Jul 21, 2025 at 10:47 AM Eric Norris <eric.t.norris@gmail.com> wrote:

On Mon, Jul 7, 2025 at 12:53 PM Eric Norris <eric.t.norris@gmail.com> wrote:
>
> On Wed, Jul 2, 2025 at 11:48 AM Eric Norris <eric.t.norris@gmail.com> wrote:
> >
> > > Based on the feedback so far (I do plan on waiting for more responses
> > > to your email), and on my own preferences, I wonder if there is a
> > > hybrid option I could propose. Perhaps the RFC could offer both a
> > > \Curl\Handle (tentative name) to address position 1, and a
> > > \Curl\BasicHttpHandle (also tentative name) that addresses position 2?
> > > If people were amenable, I'd even make the BasicHttpHandle a separate
> > > vote.
> > >
> > > I agree that 3 is both more bikesheddable and also possibly ideal, but
> > > I feel my above suggestion maybe strikes the right balance between the
> > > "status quo is fine, I don't want to see random HTTP-related methods
> > > on my low(est)-level curl object" and the "I'd like to do basic HTTP
> > > stuff with curl, without a library" crowds.
> > >
> > > Barring that, my preference would be 2, but I'd accept 1 just to have
> > > it pass - like I mentioned elsewhere, I think there is value in
> > > introducing namespaces and object-oriented APIs for "modernization"
> > > and language consistency reasons.
> >
> > Having thought about this some more, while I'm still feeling somewhat
> > positive about my suggestion I'm just not sure it's the best way to
> > proceed. I started to sketch what a BasicHttpHandle class would look
> > like, and I'm stuck on how to get data about the response out of the
> > class.
> >
> > Naively, we could have $response_status_code and $response_headers
> > properties, and have the same fetch() and execute() methods I
> > suggested elsewhere to get the response body. Alternatively, we could
> > return a simple CurlHttpResponse object which contains all three
> > properties in the fetch() and execute() implementations for the
> > BasicHttpHandle class.
> >
> > Both of these are fine, but they would lock us out of being PSR7
> > compatible. I think that people would probably desire PSR7
> > compatibility, and I would feel uncomfortable with eliminating or
> > tainting the possibility of achieving this. For example, if we had
> > this BasicHttpHandle and then later introduced PSR7 response objects,
> > we'd need to either break backwards compatibility for the class, or
> > introduce a second class. We could also go straight to returning a
> > PSR7 compatible response for the BasicHttpHandle class, but I think
> > that likely deserves its own RFC.
> >
> > So in closing, if people felt generally okay with the limitation of
> > not being PSR7 compatible, I'd probably still add some form of my
> > BasicHttpHandle suggestion as a secondary vote. If people thought PSR7
> > was necessary, I'd drop it, and leave a PSR7-in-core RFC for the
> > future. In that case, I'd go with Larry's option 1 for the RFC; I've
> > currently updated the RFC to match that option for now.
>
> Thanks Ben, Larry, and Paul for your responses to my suggestion for a
> BasicHttpHandle class. After reflecting further, I have decided to
> move this to the Future Scope section, as it feels weighty enough to
> stand as its own RFC. I'd like to think about this a bit more, but I
> will note that having a Request and Response interface in core would
> greatly simplify the proposal for a simple curl-based HTTP client, so
> I'd likely support any effort on that front.
>
> I've also updated the Curl\MultiHandle class proposal to account for
> removing the CURLOPT_RETURNTRANSFER option.
>
> At this point I believe the RFC is in a semi-final state at this
> point, barring any additional discussion. Thanks all for the feedback
> so far!

I'd like to bring this to a vote since discussion has died down, but I
feel that I should implement the proposal before doing so. As always
this is the hard part, and since I'm back from an extended break at
work I will have less time to focus on this.

I've mentioned this before, but if anyone would like to collaborate on
the implementation, please reach out! Otherwise, I'll update this
thread with a link to the implementation at some point in the future,
give it a little more time for discussion, and bring the proposal to a
vote.

Apologies, quick clarification: I do not intend to target PHP 8.5, and
will update the RFC to note this.