Conversation
| When clients wish to upload a file using the server's recommended service, they | ||
| can send a request to the upload URI. The request method MUST be POST. Clients | ||
| SHOULD authenticate their HTTP request with the same credentials used on the | ||
| IRC connection (e.g. HTTP Basic for SASL PLAIN, HTTP Bearer for SASL |
There was a problem hiding this comment.
The spirit of my draft was that servers would embed credentials in the URL, to allow uploading to third-party services. With your design, third-party services get connection credentials that are valid for the IRCd in the most common SASL scheme (PLAIN).
There was a problem hiding this comment.
Yes. This is an intentional design decision. The filehost server can forward the request to another server if need be.
There was a problem hiding this comment.
but it still knows the password
There was a problem hiding this comment.
I'm not sure I understand?
What I meant is that the filehost server can be hosted by the same folks as the IRC server, can check the credentials in the request, and can forward requests without IRC credentials to another server if need be.
Here's why I deviated from your proposal:
- Putting secrets in URLs is a bit scary. ISUPPORT is in general not security-sensitive.
- The upload service cannot be any random third-party: it needs to implement the spec's endpoints. In general, third-party upload services have a custom API.
- With your proposal, the external service still needs to be somehow tied to the IRC server to check the credentials embedded in the request URL. Credentials need to be per IRC connection. With signed tokens you hit issues regarding revocation etc.
- It resulted in a lot of additional complexity in my server implementation. On the other hand, proxying is very simple (and implemented in soju).
There was a problem hiding this comment.
What I meant is that the filehost server can be hosted by the same folks as the IRC server
My point was that it doesn't have to be.
The upload service cannot be any random third-party: it needs to implement the spec's endpoints.
There's no endpoint, it's just a URL that accepts generic HTTP POST
With your proposal, the external service still needs to be somehow tied to the IRC server to check the credentials embedded in the request URL.
My thinking was that the IRC server would create token on the external service, not the other way around.
Putting secrets in URLs is a bit scary. ISUPPORT is in general not security-sensitive.
It resulted in a lot of additional complexity in my server implementation. On the other hand, proxying is very simple (and implemented in soju).
Those however, are good points. I'm sold.
|
This is missing the normal
This absence has already led to ObsidianIRC jumping the gun: https://github.com/ObsidianIRC/ObsidianIRC/blob/9632acfb35cbd208bfc94e66d5e2882f47ef58ec/src/protocol/isupport.ts#L64 if (key === "FILEHOST" || key === "draft/FILEHOST") { |
I think the reason for this, and the reason why ObsidianIRC supports both of these, is because supporting draft prefixes or vendor prefixes in ISUPPORT tokens is a relatively new relaxation of the requirements in the IRC protocol. This spec was drafted before that relaxation, and could still be updated to use the draft prefix. |
This PR's |
|
Prefixes in ISUPPORT tokens was a relaxation made in the past few months, maybe you're thinking of prefixed CAP tokens? There were prefixed ISUPPORT tokens in the wild, but at the time it was technically against the protocol, and it was in fact in part due to this specification that the whole thing was brought up and relaxed. ObsidianIRC opted to support both because, at the time, using prefixes on ISUPPORT tokens was against IRC protocol, but you are right that we should now be supporting only the prefixed version. At the time of implementing, it could have gone either way, which is why we support both. |
|
Ah, I had no idea the spec change there was so recent and that both soju and this proposal were previously out of compliance. Apologies. |
|
No need for apologies heh, thank you for your interest |
|
I think another thing was that there was prior art on the filehost spec from progval which didn't have the prefix in it, so relying on it being unprefixed to determine if it's a final version won't work so great. |
| Its value MUST be a URI and SHOULD use the `https` scheme. Clients MUST ignore | ||
| tokens with an URI scheme they don't support. Clients MUST refuse to use | ||
| unencrypted URI transports (such as plain `http`) if the IRC connection is | ||
| encrypted (e.g. via TLS). |
There was a problem hiding this comment.
Is there any actual relation between an IRC server's use of TLS vs insecure connection, and the accompanying upload server's connection protocol?
Many IRC networks provide insecure connections for wider client support. If a client is going to put in the effort today to implement draft/filehost, wouldn't it be more sensible to require HTTPS, given that we're sending credentials over the network? HTTPS is not hard to implement today, and I think we can make that requirement of a web server. Otherwise we encourage insecure practices for a brand new feature. Either that, or not be opinionated about what protocol is used to connect to the upload server.
There was a problem hiding this comment.
Is there any actual relation between an IRC server's use of TLS vs insecure connection, and the accompanying upload server's connection protocol?
Allowing insecure uploads when the user has set up a secure IRC connection is a kind of mixed content security issue. A user connecting via TLS wouldn't assume that their credentials get exposed via HTTP when uploading a file.
wouldn't it be more sensible to require HTTPS, given that we're sending credentials over the network?
There are uses for plaintext IRC connections which aren't compatibility with very old clients. For instance, during development, or over Tor, or on a private network (e.g. VPN).
There was a problem hiding this comment.
These motivations make sense to me. Would it be a good idea to include them in the RFC? I could see others asking why it's that way otherwise.
There was a problem hiding this comment.
I usually don't include design decision motivations in normative specs. Completely fine adding something if it's deemed better.
|
not sure if it would count towards ratification, but I wrote a thing to use FILEHOST to proxy to various pastebins: https://github.com/classabbyamp/convoyeur |
|
Added the prefix disclaimer. |
as specified by ircv3/ircv3-specifications#562 since 2026-01-04
as specified by the proposed draft since 2026-01-04 Link: ircv3/ircv3-specifications#562
|
Which servers support this so far? |
|
AFAIK soju only so far. Ergo has added a way to manually insert ISUPPORT tokens from the config file but that requires server operators to bring up a separate HTTP file upload server: https://github.com/ergochat/ergo/blob/c79b65cf8ad25e77367c863f20ddf38cfeb52bf3/default.yaml#L401 |
|
UnrealIRCd has a 3rd party module: https://github.com/unrealircd/unrealircd-contrib/blob/929da5a2d628370b86129543d6936c08d7c4efa3/files/filehost.c |
|
This also merely advertises a new ISUPPORT token. What HTTP server implementation would a user point the URL to? (Seems like the |
|
Is there a reason this doesn't include HTTP DELETE (validated against the user's account name)? It could be an optional feature. |
|
We've considered adding more features, but to be usable in a modern multi-client context this would need a lot more. Probably would need a way to list a user's own uploads. DELETE on its own would not be useful from my clients PoV. |
as specified by the proposed draft since 2026-01-04 Link: ircv3/ircv3-specifications#562
|
When implementing support for this and
As a result of this, I opted to not send the user's credentials by default in Halloy. I do not know concretely what sorts of changes should be made to the spec if any, but I figured I would at least raise my thoughts here to prompt discussion. |
|
I have previously raised the idea of the server providing credentials to the user for the upload server. I still think this (as well as my proposal to formally require that upload servers use TUS) are a good idea. |
|
@sadiepowell does tus provide additional security over regular uploads? |
|
No, but its a standard system for handling resumable uploads which is better than the vibes-based approach in the current spec. |
|
Some relevant prior work here is Access-Control-Allow-Credentials. Similar problem, and the solution was that only the same origin may send credentials, otherwise they can't be used. This is an OK guarantee that your credentials don't leave the server you already trust. May or may not make sense for IRC. |
|
Just going to forward this contribution I made from the Halloy repo: It might make sense here to have a standardized OAuth/OIDC-style handshake between the file hosting providers, the bouncer/server and the client. I'd be happy to write up an RFP to IRCv3 to add this as the standard if people would be interested. Here's a little mermaid diagram of how this could work: sequenceDiagram
actor Client
participant Server
participant Filehost@{ "type": "database"}
Filehost-->>Server: Requests OIDC configuration
Server->>Filehost: Returns OIDC configuration with JWKS url
Filehost-->>Server: Requests JSON Web Keyset (JWKS) to verify tokens issued by the server
Server->>Filehost: Returns JWKS
Client-->>Server: Establish connection
Server->>Client: Advertises FILEHOST
Client -->>Server: Requests access token
Server -->>Filehost: Requests nonce and provides client IP address to expect upload from
Filehost->>Server: Returns nonce (bound to client IP)
Server->>Client: Returns signed JWT with expiration, nonce and hashed username as data
Client->>Filehost: Sends file using multipart/form-data with key `file` and the JWT in the Authorization header
Filehost->>Client: Verifies signature with cached JWKS, nonce, expiration, audience and if valid returns file URL
Originally posted by @reesericci in squidowl/halloy#1680 (comment) |
|
ObsidianIRC uses JWT >.> |
|
@furudean I don't understand your concern. The user already sends the credentials to the IRC server each time they connect. This spec makes it so clients also send credentials to the server-controlled upload endpoint. What is the threat model here? Why would a server send an untrusted ISUPPORT token?
|
|
I can't talk for @furudean but it makes sens to me to want to reduce the amount of credentials on the wire. And the filehost service doesn't necessarily lives on the same physical server as the IRCd. Not sending credentials to the filehost server could limit the impact of a compromised server. |
|
Credentials are transmitted every time a client connects anyways, so the benefit of skipping it when uploading is pretty low. I agree that securing credentials in general is a good idea, but I think it would be worthwhile to improve that for the IRC connection too instead of limiting it to HTTP file upload. This is possible via multiple ways, e.g. #584 or OAuth2 with dynamic client registration. |
|
Networks may want to offload file storage to a server which they do not control so I think it would be good to provide temporary tokens for use with the upload server. |
|
My two cents: this specification works for the use cases it was intended for, and lacks features that would allow it to scale to a public network:
I think it would be appropriate for this spec to coexist with a greenfield design that has hardening and additional features (I like Sadie's suggestion of tus.io). |
|
I agree that we should take steps towards supporting OpenID connect - it would provide us a solid foundation to build on. I think this filehost specification is a good place to start because IRCv3 file hosts don't currently exist (except Soju), so we can implement this however we'd like. |
This is shipped by soju + gamja + goguma + senpai as a vendored spec, and is based on an earlier draft by @progval.