Skip to content
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

Update Piwik over HTTPS #7327

Merged
merged 10 commits into from Mar 10, 2015
Merged

Update Piwik over HTTPS #7327

merged 10 commits into from Mar 10, 2015

Conversation

mnapoli
Copy link
Contributor

@mnapoli mnapoli commented Mar 2, 2015

Fix for #6441

Piwik will update over HTTPS if supported by the system, else use HTTP. If using HTTPS, it will not fallback to HTTP (it would make HTTPS useless). HTTP is only used if a secure method (openssl/curl/fopen) is not supported.

Method Certificate Result Secure? System check
curl valid Success yes ok
curl invalid Error yes ok
curl + no openssl valid or invalid Success, using HTTP no warning
fopen valid Success yes ok
fopen invalid Error yes ok
fopen + no openssl valid or invalid Success, using HTTP no warning
socket valid Success no warning
socket valid Success no warning
socket + no openssl valid or invalid Success no warning

BC break? I have removed the latest_version_url option in global.ini.php because the URL can now be with or without HTTPS, and it wasn't consistent because the update URL for beta versions wasn't in the config. I don't think it's a BC break because that wasn't documented anywhere, and I doubt anybody would have any use for that…

TODO:

  • handle the case where trying to use fopen/curl but openssl is not installed (see this)
  • update the system check: fopen is now a valid method to update via HTTPS + check openssl is installed if fopen is used
  • fix tests (see this)

@mnapoli mnapoli self-assigned this Mar 2, 2015
@mnapoli mnapoli added the Pull Request WIP Indicates the current pull request is still work in progress and not ready yet for a review. label Mar 2, 2015
@mnapoli mnapoli added this to the Piwik 2.12.0 milestone Mar 2, 2015
@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 2, 2015

In a vagrant box I compiled PHP without openssl:

var_dump(extension_loaded('openssl'));
// false

var_dump(stream_get_wrappers());
array (
  0 => 'php',
  1 => 'file',
  2 => 'glob',
  3 => 'data',
  4 => 'http',
  5 => 'ftp',
  6 => 'phar',
)
// doesn't contain https

Trying to download over HTTPS doesn't work:

php -r "var_dump(file_get_contents('https://builds.piwik.org/LATEST'));"

Warning: file_get_contents(): Unable to find the wrapper "https" - did you forget to enable it when you configured PHP? in Command line code on line 1

Warning: file_get_contents(https://builds.piwik.org/LATEST): failed to open stream: No such file or directory in Command line code on line 1

bool(false)

So we have to fallback to an HTTP URL for installations that do not have openssl. This is insecure, but this is the only alternative to allow these people to update.

If openssl is enabled, then it will use HTTPS and fail if the certificate is invalid (so no insecure stuff on that side: no fallback to HTTP).

Here is the test I implemented:

    public static function isUpdatingOverHttps()
    {
        $openSslEnabled = extension_loaded('openssl');
        $usingMethodSupportingHttps = (Http::getTransportMethod() !== 'socket');

        return $openSslEnabled && $usingMethodSupportingHttps;
    }

Then:

        if (self::isUpdatingOverHttps()) {
            $url = 'https://builds.piwik.org/piwik.zip';
        } else {
            $url = 'http://builds.piwik.org/piwik.zip';
        }

@mnapoli mnapoli added Enhancement For new feature suggestions that enhance Matomo's capabilities or add a new report, new API etc. Needs Review PRs that need a code review and removed Pull Request WIP Indicates the current pull request is still work in progress and not ready yet for a review. labels Mar 2, 2015
@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 2, 2015

OK it's ready for review (I don't want to break the updater!)

@mnapoli mnapoli removed their assignment Mar 2, 2015
@bglxx
Copy link

bglxx commented Mar 2, 2015

Hi Matthieu,
I think there are something to do to increase security on the server side. Please take a look at

https://www.ssllabs.com/ssltest/analyze.html?d=builds.piwik.org&hideResults=on

Thats one of the reasons why I wrote, that this task isnt done within one hour. Most people think that https is secure by definition but there are a lot of small steps neccessary to have a higher level of security.

@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 2, 2015

@bglxx thank you, maybe you can open a separate issue for this (and detail the specific problems, I have to admit I'm not a SSL expert and I don't especially understand all the issues)? We try to keep topics small so that it's easier to follow and move forward.

@bglxx
Copy link

bglxx commented Mar 2, 2015

@mnapoli I will discuss it tomorrow with our security specialist and break it down in small parts. I'm not this high level specialist but I will arrange, that you will receive the input and I make small topics.

@mattab
Copy link
Member

mattab commented Mar 4, 2015

Btw I just found out that we already have a FAQ about enabling HTTPS support: http://piwik.org/faq/troubleshooting/faq_177/

could you add link to it from the System check when SSL is not yet working? (over time we will improve the faq with users comment, and maybe you already have some input on improving it, if so feel free to edit!)

…lid certificate.

We are using divezone.net because @mattab says that he will never fix the broken certificate. If this test ever fails in the future, go after him :p
- Piwik will update over HTTPS if curl is supported
- the system check verifies that updating over HTTPS is supported (= curl supported)
Added tests, there's one failing need to find a solution.
HTTP will be used if (and only if) HTTPS is not supported at all (e.g. openssl is not installed or fopen/curl is not supported). If HTTPS is supported, we try to update through HTTPS: any failure will stop the update process and we don't fallback to HTTP. This is the expected behavior: a failure could be a MITM attack.
@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 4, 2015

Yep now the user will see if he doesn't have openssl installed.

mnapoli added a commit that referenced this pull request Mar 10, 2015
@mnapoli mnapoli merged commit 195ccaf into master Mar 10, 2015
@mnapoli mnapoli deleted the https-update branch March 10, 2015 00:28
@@ -115,6 +115,8 @@
"SystemCheckCronArchiveProcess": "Archive Cron",
"SystemCheckCronArchiveProcessCLI": "Managing processes via CLI",
"SystemCheckPhpSetting": "To prevent some critical issue, you must set the following in your php.ini file: %s",
"SystemCheckUpdateHttps": "Update over HTTPS",
"SystemCheckUpdateHttpsNotSupported": "Piwik cannot use HTTPS to update, it will fall back to the insecure HTTP update. Check that CURL or allow_url_fopen is supported and that the openssl PHP extension is installed: http://piwik.org/faq/troubleshooting/faq_177/.",
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can you make the URL to the FAQ a placeholder %s and sprintf the URL at runtime (allows us to change URLs without having to invalidate translations)

@mattab
Copy link
Member

mattab commented Mar 10, 2015

(the PR wasn't reviewed before merge - it was on my todo list...)

I think this could regress the auto updater for many users, if somehow connecting via SSL does not work for them. The isUpdatingOverHttps could be true yet the download over SSL will fail. Maybe we can actually test to download a file in isUpdatingOverHttps such as https://builds.piwik.org/LATEST ?

(I'm worried that for some, possibly many, users it will not let them auto update, and then they will simply not keep Piwik up to date as much...)

otherwise, looks good!

@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 10, 2015

But what happen if the download fails? If we fallback on HTTP download then HTTPS is useless.

One thing we could do though is to add an option in INI to force using HTTP, so that if users are for some reason unable to update to HTTPS they can at least (and consciously) use HTTP instead. What do you think?

@mattab
Copy link
Member

mattab commented Mar 10, 2015

If the download over HTTPs fails, then HTTPS is not "useless" but it is "not used" which is different. That's different because it keeps BC: it is the same behavior as it is currently in <= 2.11.2. Since we mention in the System whether they have secure downloads, it is fine, we have done our job to let users know whether their config is secure or not. And it will work for all users which is more important than making sure all users are forced to use secure downloads.

Another point is that if users cannot update Piwik (or need to change their INI setting which many wouldn't care to do), they would not update. As a result security would be lessen for all these users since we often fix security bugs. I just want to make a point that auto-update working for all users is important feature 👍

@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 10, 2015

If update over HTTPS fails (when HTTP would work) that means that the certificate verification failed. That means (most certainly) a man-in-the-middle attack. So falling back to HTTP defeats the purpose of using HTTPS.

In other words, the only advantage of HTTPS here is to prevent downloading from an untrusted entity (the encryption aspect is useless here since the Piwik zip is public, there is no sensitive info exchanged). So when HTTPS fails because we download from an untrusted entity, using HTTP would render HTTPS completely useless (again, encryption doesn't add any value here).

I agree that we need to keep people up to date though, so I'm OK for providing an alternative solution. But it must be one that is not automatic, else HTTPS brings absolutely no value. It could be a big fat warning explaining the problem and offering to use HTTP for example, but that requires big changes in the update process I imagine?

@mattab
Copy link
Member

mattab commented Mar 10, 2015

The warning in the system check should be quite visible to users, but you're right we should also warn when users are actually about to do the upgrade. In this view: https://github.com/piwik/piwik/blob/master/plugins/CoreUpdater/templates/newVersionAvailable.twig#L27-38 maybe we add a warning with the existing string SystemCheckUpdateHttpsNotSupported when we know HTTPS won't work.

To know HTTPS won't work the only way IMO is to issue a test download on HTTPS...

For the style we have this orange warning box used already in the updater screen (see here: https://github.com/piwik/piwik-ui-tests/blob/master/Updater_main.png) so maybe we reuse this?

@defuse
Copy link

defuse commented Mar 11, 2015

Here's a rule of thumb: The default should be HTTPS, and it should never fall back to HTTP without an explicit and informed action by a human user. Think browser certificates. If the cert is bad, you have to click at least 3 buttons to get through it (and on some browsers you can't even click through). When it happens, it is the only thing happening. The warning is not mixed in with other error messages, so it has the user's full attention.

So I propose: Attempt the download with HTTPS (don't do a separate test download, beware TOCTTOU), if it fails, display a page whose only purpose is to inform the user of the attack (bonus points for a solid red background) and ask them if they really want to proceed.

@mnapoli
Copy link
Contributor Author

mnapoli commented Mar 11, 2015

Completely agree with you @defuse. I will comment in the original issue.

@mattab
Copy link
Member

mattab commented Mar 12, 2015

that's actually what I proposed above. the solution is very simple IMO:

  • isUpdatingOverHttps should actually download a file over HTTPs from https://builds.piwik.org that's the only way to know whether it will work
  • imagine HTTPS downloads don't work: a warning is displayed in the system check, and a orange warning is displayed in the Update page in the view {% if can_auto_update %} block.
  • if HTTPS download don't work, because we have displayed orange warning to user, then we use HTTP

Result: It's secure, simple, and it works for all users auto-magically

@mattab
Copy link
Member

mattab commented Mar 22, 2015

fallback to http was done in #7429

@mattab mattab added the Major Indicates the severity or impact or benefit of an issue is much higher than normal but not critical. label Mar 22, 2015
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Enhancement For new feature suggestions that enhance Matomo's capabilities or add a new report, new API etc. Major Indicates the severity or impact or benefit of an issue is much higher than normal but not critical. Needs Review PRs that need a code review
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

4 participants