GET is (and all methods, including all safe and idempotent methods, are) allowed to have side effects, per the spec. Safe and idempotent are not mathematical constructs as defined in HTTP, they are more “business” constructs.
I know what you mean. It feels like we're missing an idea of scope for resources. If there was some kind of transaction scope or session scope or something, then a QUERY could create resources within that scope, so we could know that in the long run, it has no side effects. But that would be antithetical to the idea of statelessness perhaps.
Or maybe we just need distributed garbage collection for URLs.
> GET is allowed to have side effects, just not beyond the first invocation of a given request.
GET can have side effects, and has no difference first and subsequent invocations (because it is safe as well as idempotent). Were it idempotent but not safe, it could have side effects that the client was accountable for the first request, but no different ones of that kind for subsequent uses.
The way I look at it is that the system must continue to meet its requirements (whatever they might be) whether it gets one GET request or many in response to a single action within the user agent (clicking a link, submitting a form, script making a request, etc.). In general, logging two requests instead of one does not violate any requirements and in fact logging every request, even duplicates, is the expected behavior. Adding the same item to a list twice in response to a single UI interaction, on the other hand, would not give the desired effect.