]> sipb.mit.edu Git - ikiwiki.git/blob - doc/plugins/openid/troubleshooting.mdwn
default User-Agent changed
[ikiwiki.git] / doc / plugins / openid / troubleshooting.mdwn
1 **TL;DR**
2
3 [[!toc levels=4]]
4
5 # An odyssey through lots of things that have to be right before OpenID works
6
7 Having just (at last) made an ikiwiki installation accept my
8 OpenID, I have learned many of the things that may have to be checked
9 when getting the [[plugins/openid]] plugin to work. (These are probably
10 the reasons why [ikiwiki.info](/) itself won't accept my OpenID!)
11
12 Just to describe my OpenID setup a bit (and why it makes a good stress-test
13 for the OpenID plugin :).
14
15 I'm using my personal home page URL as my OpenID. My page lives at
16 a shared-hosting service I have hired. It contains links that delegate
17 my OpenID processing to [indieauth.com](https://indieauth.com).
18
19 IndieAuth, in turn, uses
20 [rel-me authentication](http://microformats.org/wiki/RelMeAuth) to find
21 an [OAuth](http://microformats.org/wiki/OAuth) provider that can authenticate
22 me. (At present, I am using [github](http://github.com) for that, which
23 is an OAuth provider but not an OpenID provider, so the gatewaying provided
24 by IndieAuth solves that problem.) As far as ikiwiki is concerned,
25 IndieAuth is my OpenID provider; the details beyond that are transparent.
26
27 So, what were the various issues I had to sort out before my first successful
28 login with the [[plugins/openid]] plugin?
29
30 ## no_identity_server: Could not determine ID provider from URL.
31
32 This is the message [ikiwiki.info](/) shows as soon as I enter my home URL
33 as an OpenID. It is also the first one I got on my own ikiwiki installation.
34
35 ### various possible causes ...
36
37 There could be lots of causes. Maybe:
38
39 * the offered OpenID is an `https:` URL and there is an issue in checking
40     the certificate, so the page can't be retrieved?
41 * the page can be retrieved, but it isn't well-formed HTML and the library
42     can't parse it for the needed OpenID links?
43 * ...?
44
45 ### make a luckier setting of useragent ?!
46
47 In my case, it was none of the above. It turns out my shared-hosting provider
48 has a rule that refuses requests with `User-Agent: libwww-perl/6.03` (!!).
49 This is the sort of problem that's really hard to anticipate or plan around.
50 I could fix it (_for this case!_) by changing `useragent:` in `ikiwiki.setup`
51 to a different string that my goofy provider lets through.
52
53 __Recommendation:__ set `useragent:` in `ikiwiki.setup` to some
54 unlikely-to-be-blacklisted value. I can't guess what the best
55 unlikely-to-be-blacklisted value is; if there is one, it's probably the
56 next one all the rude bots will be using anyway, and some goofy provider
57 like mine will blacklist it.
58
59 > If your shared hosting provider is going to randomly break functionality,
60 > I would suggest "voting with your wallet" and taking your business to
61 > one that does not.
62 >
63 > In principle we could set the default UA (if `$config{useragent}` is
64 > unspecified) to `IkiWiki/3.20140915`, or `IkiWiki/3.20140915 libwww-perl/6.03`
65 > (which would be the "most correct" option AIUI), or some such.
66 > That might work, or might get randomly blacklisted too, depending on the
67 > whims of shared hosting providers. If you can't trust your provider to
68 > behave helpfully then there isn't much we can do about it.
69 >
70 > Blocking requests according to UA seems fundamentally flawed, since
71 > I'm fairly sure no hosting provider can afford to blacklist UAs that
72 > claim to be, for instance, Firefox or Chrome. I wouldn't want
73 > to patch IkiWiki to claim to be an interactive browser by default,
74 > but malicious script authors will have no such qualms, so I would
75 > argue that your provider's strategy is already doomed... --[[smcv]]
76
77 >> I agree, and I'll ask them to fix it (and probably refer them to this page).
78 >> One reason they still have my business is that their customer service has
79 >> been notably good; I always get a response from a human on the first try,
80 >> and on the first or second try from a human who understands what I'm saying
81 >> and is able to fix it. With a few exceptions over the years. I've dealt with organizations not like that....
82 >>
83 >> But I included the note here because I'm sure if _they're_ doing it, there's
84 >> probably some nonzero number of other hosting providers where it's also
85 >> happening, so a person setting up OpenID and being baffled by this failure
86 >> needs to know to check for it. Also, while the world of user-agent strings
87 >> can't have anything but relatively luckier and unluckier choices, maybe
88 >> `libwww/perl` is an especially unlucky one?
89
90 >>> Yippee! _My_ provider found their offending `mod_security` rule and took it out,
91 >>> so now [ikiwiki.info](/) accepts my OpenID. I'm still not sure it wouldn't be
92 >>> worthwhile to change the useragent default.... -- Chap
93
94 #### culprit was an Atomicorp ModSecurity rule
95
96 Further followup: my provider is using [ModSecurity](https://www.modsecurity.org/)
97 with a ruleset commercially supplied by [Atomicorp](https://www.atomicorp.com/products/modsecurity.html),
98 which seems to be where this rule came from. They've turned the rule off for _my account_.
99 I followed up on my ticket with them, suggesting they at least think about turning it off
100 more systemwide (without waiting for other customers to have bizarre problems that are
101 hard to troubleshoot), or opening a conversation with Atomicorp about whether such a rule
102 is really a good idea. Of course, while they were very responsive about turning it off
103 _for me_, it's much iffier whether they'll take my advice any farther than that.
104
105 So, this may crop up for anybody with a provider that uses Atomicorp ModSecurity rules.
106
107 The ruleset produces a log message saying "turn this rule off if you use libwww-perl", which
108 just goes to show whoever wrote that message wasn't thinking about what breaks what. It would
109 have to be "turn this rule off if any of _your_ customers might ever need to use or depend on
110 an app or service _hosted anywhere else_ that _could_ have been implemented using libwww-perl,
111 over which you and your customer have no knowledge or control."
112
113 Sigh. -- Chap
114
115 > Thanks for the pointer. It seems the open-source ruleset blacklists libwww-perl by default
116 > too... this seems very misguided but whatever. I've changed our default User-Agent to
117 > `ikiwiki/3.20141012` (or whatever the version is). If we get further UA-blacklisting
118 > problems I'm very tempted to go for `Mozilla/5.0 (but not really)` as the
119 > next try. --[[smcv]]
120
121 ## Error: OpenID failure: naive_verify_failed_network: Could not contact ID provider to verify response.
122
123 Again, this could have various causes. It was helpful to bump the debug level
124 and get some logging, to see:
125
126     500 Can't connect to indieauth.com:443 (Net::SSL from Crypt-SSLeay can't
127     verify hostnames; either install IO::Socket::SSL or turn off verification
128     by setting the PERL_LWP_SSL_VERIFY_HOSTNAME environment variable to 0)
129
130 I don't belong to the camp that solves every verification problem by turning
131 verification off, so this meant finding out how to get verification to be done.
132 It turns out there are two different Perl modules that can be used for SSL:
133
134 * `IO::Socket::SSL` (verifies hostnames)
135 * `Net::SSL` (_does not_ verify hostnames)
136
137 Both were installed on my hosted server. How was Perl deciding which one
138 to use?
139
140 ### set `PERL_NET_HTTPS_SSL_SOCKET_CLASS` appropriately
141
142 It turns out
143 [there's an environment variable](https://rt.cpan.org/Public/Bug/Display.html?id=71599).
144 So just set `PERL_NET_HTTPS_SSL_SOCKET_CLASS` to `IO::Socket::SSL` and the
145 right module gets used, right?
146
147 [Wrong](https://github.com/csirtgadgets/LWPx-ParanoidAgent/commit/fed6f7d7df8619df0754e8883cfad2ac15703a38#diff-2).
148 That change was made to `ParanoidAgent.pm` back in November 2013 because of an
149 unrelated [bug](https://github.com/csirtgadgets/LWPx-ParanoidAgent/issues/4)
150 in `IO::Socket::SSL`. Essentially, _hmm, something goes wrong in
151 `IO::Socket::SSL` when reading certain large documents, so we'll fix it by
152 forcing the use of `Net::SSL` instead (the one that never verifies hostnames!),
153 no matter what the admin has set `PERL_NET_HTTPS_SSL_SOCKET_CLASS` to!_
154
155 ### undo change that broke `PERL_NET_HTTPS_SSL_SOCKET_CLASS`
156
157 Plenty of [comments](https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=738493)
158 quickly appeared about how good an idea that wasn't, and it was corrected in
159 June 2014 with [one commit](https://github.com/csirtgadgets/LWPx-ParanoidAgent/commit/a92ed8f45834a6167ff62d3e7330bb066b307a35)
160 to fix the original reading-long-documents issue in `IO::Socket::SSL` and
161 [another commit](https://github.com/csirtgadgets/LWPx-ParanoidAgent/commit/815c691ad5554a219769a90ca5f4001ae22a4019)
162 that reverts the forcing of `Net::SSL` no matter how the environment is set.
163
164 Unfortunately, there isn't a release in CPAN yet that includes those two
165 commits, but they are only a few lines to edit into your own locally-installed
166 module.
167
168 > To be clear, these are patches to [[!cpan LWPx::ParanoidAgent]].
169 > Debian's `liblwpx-paranoidagent-perl (>= 1.10-3)` appears to
170 > have those two patches. --[[smcv]]
171 >
172 > Irrelevant to this ikiwiki instance, perhaps relevant to others:
173 > I've added these patches to [pkgsrc](http://www.pkgsrc.org)'s
174 > [[!pkgsrc www/p5-LWPx-ParanoidAgent]] and they'll be included in the
175 > soon-to-be-cut 2014Q3 branch. --[[schmonz]]
176
177 ## Still naive_verify_failed_network, new improved reason
178
179     500 Can't connect to indieauth.com:443 (SSL connect attempt failed
180     with unknown error error:14090086:SSL
181     routines:SSL3_GET_SERVER_CERTIFICATE:certificate verify failed)
182
183 Yay, at least it's trying to verify! Now why can't it verify IndieAuth's
184 certificate?
185
186 [Here's why](https://tools.ietf.org/html/rfc6066#section-3). As it turns out,
187 [indieauth.com](https://indieauth.com/) is itself a virtual host on a shared
188 server. If you naively try
189
190     openssl s_client -connect indieauth.com:443
191
192 you get back a certificate for [indieweb.org](https://indieweb.org/)
193 instead, so the hostname won't verify. If you explicitly indicate what server
194 name you're connecting to:
195
196     openssl s_client -connect indieauth.com:443 -servername indieauth.com
197
198 then, magically, the correct certificate comes back.
199
200 ### ensure `OpenSSL`, `Net::SSLeay`, `IO::Socket::SSL` new enough for SNI
201
202 If your `openssl` doesn't recognize the `-servername` option, it is too old
203 to do SNI, and a newer version needs to be built and installed. In fact,
204 even though SNI support was reportedly backported into OpenSSL 0.9.8f, it will
205 not be used by `IO::Socket::SSL` unless it is
206 [1.0 or higher](http://search.cpan.org/~sullr/IO-Socket-SSL-1.998/lib/IO/Socket/SSL.pod#SNI_Support).
207
208 Then a recent `Net::SSLeay` perl module needs to be built and linked against it.
209
210 > I would tend to be somewhat concerned about the update status and security
211 > of a shared hosting platform that is still on an OpenSSL major version from
212 > pre-2010 - it might be fine, because it might be RHEL or some similarly
213 > change-averse distribution backporting security fixes to ye olde branch,
214 > but equally it might be as bad as it seems at first glance.
215 > "Let the buyer beware", I think... --[[smcv]]
216
217 >> As far as I can tell, this particular provider _is_ on Red Hat (EL 5).
218 >> I can't conclusively tell because I'm in what appears to be a CloudLinux container when I'm in,
219 >> and certain parts of the environment (like `rpm`) I can't see. But everything
220 >> I _can_ see is like several RHEL5 boxen I know and love.
221
222
223 ### Local OpenSSL installation will need certs to trust
224
225 Bear in mind that the OpenSSL distribution doesn't come with a collection
226 of trusted issuer certs. If a newer version is built and installed locally
227 (say, on a shared server where the system locations can't be written), it will
228 need to be given a directory of trusted issuer certs, say by linking to the
229 system-provided ones. However, a change to the certificate hash algorithm used
230 for the symlinks in that directory was [reportedly](http://www.cilogon.org/openssl1)
231 made with OpenSSL 1.0.0. So if the system-provided trusted certificate directory
232 was set up for an earlier OpenSSL version, all the certificates in it will be
233 fine but the hash symlinks will be wrong. That can be fixed by linking only the
234 named certificate files from the system directory into the newly-installed one,
235 and then running the new version of `c_rehash` there.
236
237 ## Still certificate verify failed
238
239 Using [SNI](https://tools.ietf.org/html/rfc6066#section-3)-supporting versions
240 of `IO::Socket::SSL`, `Net::SSLeay`, and `OpenSSL` doesn't do any good if an
241 upper layer hasn't passed down the name of the host being connected to so the
242 SSL layer can SNI for it.
243
244 ### ensure that `LWPx::ParanoidAgent` passes server name to SSL layer for SNI
245
246 That was fixed in `LWPx::ParanoidAgent` with
247 [this commit](https://github.com/csirtgadgets/LWPx-ParanoidAgent/commit/df6df19ccdeeb717c709cccb011af35d3713f546),
248 which needs to be backported by hand if it hasn't made it into a CPAN release
249 yet.
250
251 > Also in Debian's `liblwpx-paranoidagent-perl (>= 1.10-3)`, for the record.
252 > --[[smcv]]
253 >
254 > And now in pkgsrc's `www/p5-LWPx-ParanoidAgent`, FWIW. --[[schmonz]]
255
256 Only that still doesn't end the story, because that hand didn't know what
257 [this hand](https://github.com/noxxi/p5-io-socket-ssl/commit/4f83a3cd85458bd2141f0a9f22f787174d51d587#diff-1)
258 was doing. What good is passing the name in
259 `PeerHost` if the SSL code looks in `PeerAddr` first ... and then, if that
260 doesn't match a regex for a hostname, decides you didn't supply one at all,
261 without even looking at `PeerHost`?
262
263 Happily, is is possible to assign a key that _explicitly_ supplies the
264 server name for SNI:
265
266     --- LWPx/Protocol/http_paranoid.pm    2014-09-08 03:33:00.000000000 -0400
267     +++ LWPx/Protocol/http_paranoid.pm    2014-09-08 03:33:27.000000000 -0400
268     @@ -73,6 +73,7 @@
269             close($el);
270              $sock = $self->socket_class->new(PeerAddr => $addr,
271                                               PeerHost => $host,
272     +                                         SSL_hostname => $host,
273                                               PeerPort => $port,
274                                               Proto    => 'tcp',
275                                               Timeout  => $conn_timeout,
276
277 ... not submitted upstream yet, so needs to be applied by hand.
278
279 > I've [reported this to Debian](https://bugs.debian.org/761635)
280 > (which is where ikiwiki.info's supporting packages come from).
281 > Please report it upstream too, if the Debian maintainer doesn't
282 > get there first. --[[smcv]]
283
284 > Applied in pkgsrc. I haven't attempted to conduct before-and-after
285 > test odysseys, but here's hoping your travails save others some
286 > time and effort. --[[schmonz]]
287
288 > Reported upstream as [LWPx-ParanoidAgent#14](https://github.com/csirtgadgets/LWPx-ParanoidAgent/issues/14)
289 > _and_ [IO-Socket-SSL#16](https://github.com/noxxi/p5-io-socket-ssl/issues/16). -- Chap
290
291 # Success!!
292
293 And with that, ladies and gents, I got my first successful OpenID login!
294 I'm pretty sure that if the same fixes can be applied to
295 [ikiwiki.info](/) itself, a wider range of OpenID logins (like mine, for
296 example :) will work here too.
297
298 -- Chap