-
Notifications
You must be signed in to change notification settings - Fork 734
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Make clientName
and clientVersion
get-only protocol requirements
#954
Conversation
Thanks @designatednerd for putting this PR out so quickly. IMO those requirements should be totally removed from the protocol. I think that folks using custom implementations are doing so because they want to be in control, and are accepting the corresponding responsibilities. I see protocols as describing the requirements that Apollo's SDK needs to work properly, and not as guiding the external implementation. It gives me the inaccurate impression that the Apollo SDK needs to read those values to work properly, while the documentation of |
The iOS SDK doesn't, but Apollo Graph Manager does (as would basically anything else that's trying to look at what version/client are sending a particular request). It's certainly a best practice to include these in some way, shape, or form so that anything looking at where requests are coming from is able to quickly tell what's coming from what version of what client. I would like to steer people real hard towards following this best practice, and making them at least implement these properties, even if they want to send them with other headers. |
@gsabran Better? |
👍Ok thanks! |
@bwhiteley @cysp any further thoughts? I'll leave this open until tomorrow morning for more comments. |
As an implementor of a custom We don't use the graph manager (though we're interested in its capabilities and will be thinking more about it "soon"), but perhaps a dashboard on there with a list of user-agents from which it has seen queries without client identification would be a good way to remind implementors to supply the client identification headers? Now that these properties are networktransport-default-client-vars-light.diffdiff --git c/Sources/Apollo/NetworkTransport.swift i/Sources/Apollo/NetworkTransport.swift
index 63a90fe3..766944fc 100644
--- c/Sources/Apollo/NetworkTransport.swift
+++ i/Sources/Apollo/NetworkTransport.swift
@@ -41,6 +41,10 @@ public extension NetworkTransport {
return "\(identifier)-apollo-ios"
}
+ var clientName: String {
+ return Self.defaultClientName
+ }
+
/// The default client version to use when setting up the `clientVersion` property.
static var defaultClientVersion: String {
var version = String()
@@ -62,6 +66,10 @@ public extension NetworkTransport {
return version
}
+
+ var clientVersion: String {
+ return Self.defaultClientVersion
+ }
/// Adds the Apollo client headers for this instance of `NetworkTransport` to the given request
/// - Parameter request: A mutable URLRequest to add the headers to. |
I can't believe I didn't think of this (I think because I was still thinking about the "override to get/set" situation), this is an excellent idea. |
/// The header field name for the Client Name | ||
static var headerFieldNameClientName: String { | ||
/// The field name for the Apollo Client Name header | ||
var headerFieldNameApolloClientName: String { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have two questions about these header name properties:
- what was the reason that these changed to be instance variables, rather than static variables? (since
addApolloClientHeaders()
is in a generic context, I think it has access toSelf
to access the static properties, it certainly does with newer versions of Swift) - at the moment these fields are not protocol requirements, so despite the fact that
addApolloClientHeaders()
accesses them throughself
, because that's happening in a generic context theNetworkTransport
default implementation is used and any specialisation in an implementation is ignored, is that intentional? if that is intentional (and it would make sense to me that it is, because why would implementors want to customise the header field names?) it would be less surprising (at least to me) when reading the code if those were just static variables somewhere, not accessed through the protocol. 🙃
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So there's a couple thoughts happening here:
- It seemed goofy to me that at the call site you had to specify the class name of the current class, although that's less bad with being able to call
Self
within the protocol (I thought theSelf
outside of the protocol thing hadn't landed yet?), and there was no real reason for them to be static rather than instance other than it seemed good for namespacing. However, now that by default they're mostly accessed within the protocol, I'll rethink this change. - This is certainly in the realm of "my opinion" vs "the right way to do things", but I hate free-floating static variables. It's almost always primarily related to something, so I think it's way better to have static variables on whatever it is they're related to rather than floating in space.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Cool, namespacing is good.
From reading the code I was unsure whether it was intentional that implementations of NetworkTransport
were not capable of specialising those properties because I saw them being accessed statically on implementation types:
/~https://github.com/apollographql/apollo-ios/search?q=headerFieldNameClientName&unscoped_q=headerFieldNameClientName
🙃
/// The header field name for the Client Name | ||
static var headerFieldNameClientName: String { | ||
/// The field name for the Apollo Client Name header | ||
var headerFieldNameApolloClientName: String { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Cool, namespacing is good.
From reading the code I was unsure whether it was intentional that implementations of NetworkTransport
were not capable of specialising those properties because I saw them being accessed statically on implementation types:
/~https://github.com/apollographql/apollo-ios/search?q=headerFieldNameClientName&unscoped_q=headerFieldNameClientName
🙃
|
I too somehow missed that it's up to an implementation of |
Are you saying it doesn't have to be these particular headers? Is this what |
Ultimately I agree with @gsabran now that I understand better what's going on here. This is basically some documentation and a convenience function. However, by changing the properties to get-only and providing default implementations, the properties no longer impose an undue burden on custom implementations of |
Co-Authored-By: Scott Talbot <stalbot@scentregroup.com>
It doesn't have to be these particular headers if you're not using Apollo Graph Manager. It does if you're using Apollo graph manager. Given that the library is owned and maintained by Apollo, we're certainly going to do everything we can to make it easy for people to use Graph Manager. 😇
Having this information passed as its own custom header also allows any existing use of |
BREAKING CHANGE
This has been much-discussed in #877 and #917, and it's clear that for people implementing their own
NetworkTransport
method rather than using one of ours, having to provide a setter for this is really annoying. If implementers still want to make the property get/set, they can (and we do withHTTPNetworkTransport
).Also added a convenience method to add the headers to any
URLRequest
, and added a note to thesend
method that these should probably be sent along if you want to use monitoring tools like Apollo Graph Manager.