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

"occ maintenance:install" fails, if path to data dir contains a symlink #12247

Open
MichaIng opened this issue Nov 4, 2018 · 9 comments
Open
Assignees
Labels
0. Needs triage Pending check for reproducibility or if it fits our roadmap 25-feedback bug feature: install and update hotspot: filename handling Filenames - invalid, portable, blacklisting, etc.

Comments

@MichaIng
Copy link
Member

MichaIng commented Nov 4, 2018

Steps to reproduce

  1. Download and place current Nextcloud 14.0.3
  2. Use occ maintenance:install to install Nextcloud, choosing a data directory with is inside a symlink. E.g. /mnt/data is a symlink, pointing to /mnt/external, then choose --data-dir /mnt/data/ncdata as install option.

Expected behaviour

Install should finish without error message.

Actual behaviour

Install throws error:

In Local.php line 387:

  Following symlinks is not allowed


maintenance:install [--database DATABASE] [--database-name DATABASE-NAME] [--database-host DATABASE-HOST] [--database-port DATABASE-PORT] [--database-user DATABASE-USER] [--database-pass [DATABASE-PASS]] [--database-table-prefix [DATABASE-TABLE-PREFIX]] [--database-table-space [DATABASE-TABLE-SPACE]] [--admin-user ADMIN-USER] [--admin-pass ADMIN-PASS] [--data-dir DATA-DIR]
  • The install actually works fine. config.php is fully configured with data dir containing the chosen path with symlink inside.
  • WebUI opens, creating/uploading files works well, data dir is used as expected.
  • Only the skeleton files/folders are not copied to the data dir, so when logging into Nextcloud the first time, the data dir is empty.

Further info

  • This is due to the code line from the error message. It's aim is to disable symlink from INSIDE the data dir to OUTSIDE it. However both is not the case, thus the check is done incorrectly.
  • In the past this did work, so I guess it's due to a recent change. I just checked on Nextcloud 13.0.7 and there it works well with exactly the same setup.

Server configuration

Operating system:
Debian Stretch

Web server:
Does not matter, same with Apache2, Nginx, Lighttpd

Database:
MariaDB 10.1

PHP version:
PHP7.0

Nextcloud version:
14.0.3

Updated from an older Nextcloud/ownCloud or fresh install:
Fresh install

Where did you install Nextcloud from:
Official download source

Signing status:
No failures

List of activated apps:
Default on fresh install, irrelevant

Nextcloud configuration:

Config report
{
    "system": {
        "passwordsalt": "***REMOVED SENSITIVE VALUE***",
        "secret": "***REMOVED SENSITIVE VALUE***",
        "trusted_domains": [
            "localhost",
            "*"
        ],
        "datadirectory": "***REMOVED SENSITIVE VALUE***",
        "dbtype": "mysql",
        "version": "14.0.3.0",
        "memcache.local": "\\OC\\Memcache\\APCu",
        "filelocking.enabled": true,
        "memcache.locking": "\\OC\\Memcache\\Redis",
        "redis": {
            "host": "***REMOVED SENSITIVE VALUE***",
            "port": 0
        },
        "overwrite.cli.url": "http:\/\/localhost\/nextcloud",
        "dbname": "***REMOVED SENSITIVE VALUE***",
        "dbhost": "***REMOVED SENSITIVE VALUE***",
        "dbport": "",
        "dbtableprefix": "oc_",
        "mysql.utf8mb4": true,
        "dbuser": "***REMOVED SENSITIVE VALUE***",
        "dbpassword": "***REMOVED SENSITIVE VALUE***",
        "installed": true,
        "instanceid": "***REMOVED SENSITIVE VALUE***",
        "maintenance": false
    }
}
  • However, does not matter, since error appears on install step before doing any config changes.
  • But it shows, that everything is configured as expected, some additions from our install script (memcache, locking, 4byte support).

Are you using external storage, if yes which one:
No, but using symlinks usually has the intention to move userdata to an external drive, either after Nextcloud was installed already or prior to this, but having an always correct data dir path, even that the actual (symlinked) location changes from one drive/location to another.

Are you using encryption: no

Are you using an external user-backend, if yes which one: no

€: @nextcloud-bot nice try, but nothing is related 😉

@nextcloud-bot
Copy link
Member

GitMate.io thinks possibly related issues are #11153 (occ maintenance:install needs a --adminemail argument), #7563 ([occ] Hide "not installed" info on "occ maintenance:install"), #8179 (Upgrade fails if the config dir contains config.php~ file), #3555 (Scripted "occ maintenance:install" only accepts the admin password as cleartext), and #5446 (occ maintenance:repair should fix missing directories in user data directories.).

@skjnldsv skjnldsv added the 0. Needs triage Pending check for reproducibility or if it fits our roadmap label Jun 12, 2019
@wiswedel
Copy link
Contributor

wiswedel commented Mar 4, 2020

This worked for me: https://central.owncloud.org/t/exception-while-scanning-following-symlinks-is-not-allowed/1282/7

@MichaIng
Copy link
Member Author

MichaIng commented Mar 4, 2020

@wiswedel
Of course one can work around the issue, or use readlink, however I would prefer the installer to limit symlinks only as intended and not in the here mentioned case.


Related commit: 7b1b723
If I understand correctly, the actual check is done here: https://github.com/nextcloud/server/blob/master/lib/private/Files/Storage/Local.php#L404-L406
But I don't see why this fails in the mentioned case since "realPath" is compared with "realDataDir" which should match if the data dir is inside a symlinked location. All other related variables seem to be derived correctly, e.g. "dataDirLength" is estimated from "realDataDir" as well...

... ah and of course the above must be true since Nextcloud operates fine, besides the skeleton file transer, and this is where it must fail:

  • The skeleton dir is /path/to/nextcloud/core/skeleton/, so not inside the data dir, so the checked path does not match realDataDir of course.

So I can imagine two solutions:

  1. Check whether pathToResolve is actually inside dataDir, before comparing the real paths, so the symlink check is only done when the source path is actually inside the data dir already. However I see that the whole function assumes that the source path is inside the data dir ($fullPath = $this->datadir . $path;) which is not true in case of skeleton file. So I am a bid confused why this works at all 🤔.
  2. Since the function assumes that source path is in the data dir, copying the skeleton files should probably not use it, but copy those files another way. For security reasons this might be better, so that the function fails in every case where the source file is not located in the data dir, since this is never wanted anyway, besides for skeleton files?

But probably I misunderstand the code 😉.

@MichaIng
Copy link
Member Author

MichaIng commented Mar 4, 2020

@icewind1991
I pull you in since you commited related code. I'll also give some steps to replicate later. Let me know if I you have some debugging steps for me or logs I should paste etc.

@skjnldsv skjnldsv added 1. to develop Accepted and waiting to be taken care of and removed 0. Needs triage Pending check for reproducibility or if it fits our roadmap labels Apr 10, 2020
@MichaIng
Copy link
Member Author

MichaIng commented Jul 18, 2020

A probably related case: https://dietpi.com/forum/t/nc-symlinks-not-allowed/4304

[core] Error: Following symlinks is not allowed ('/mnt/dietpi_userdata/nextcloud_data/uwjhn/cache' -> '/mnt/7627eacf-bfd9-4168-9bd0-897988222727/dietpi_userdata/nextcloud_data/uwjhn/cache/' not inside '/mnt/dietpi_userdata/nextcloud_data/uwjhn/')

POST /nextcloud/index.php/login
from 192.168.178.35 by uwjhn at 2020-07-15T18:21:40+00:00
[index] Error: OCP\Files\ForbiddenException: Following symlinks is not allowed at <<closure>>

 0. /var/www/nextcloud/lib/private/Files/Storage/Local.php line 158
    OC\Files\Storage\Local->getSourcePath("/cache")
 1. /var/www/nextcloud/lib/private/Files/Storage/Common.php line 879
    OC\Files\Storage\Local->getMetaData("/cache")
 2. <<closure>>
    OC\Files\Storage\Common->getDirectoryContent("")
 3. /var/www/nextcloud/lib/private/Files/Cache/Scanner.php line 408
    iterator_to_array(Generator {})
 4. /var/www/nextcloud/lib/private/Files/Cache/Scanner.php line 388
    OC\Files\Cache\Scanner->handleChildren("", false, 3, 139, true, 0)
 5. /var/www/nextcloud/lib/private/Files/Cache/Scanner.php line 340
    OC\Files\Cache\Scanner->scanChildren("", false, 3, 139, true)
 6. /var/www/nextcloud/lib/private/Files/View.php line 1339
    OC\Files\Cache\Scanner->scan("", false)
 7. /var/www/nextcloud/lib/private/Files/View.php line 1383
    OC\Files\View->getCacheEntry(OCA\Files_Trashb ... }}, "", "/uwjhn")
 8. /var/www/nextcloud/lib/private/Files/Node/Root.php line 201
    OC\Files\View->getFileInfo("/uwjhn")
 9. /var/www/nextcloud/lib/private/Files/Node/Folder.php line 147
    OC\Files\Node\Root->get("/uwjhn")
10. /var/www/nextcloud/lib/private/Files/Node/Root.php line 384
    OC\Files\Node\Folder->nodeExists("/uwjhn")
11. <<closure>>
    OC\Files\Node\Root->getUserFolder("*** sensitive parameter replaced ***")
12. /var/www/nextcloud/lib/private/Files/Node/LazyRoot.php line 66
    call_user_func_array([OC\Files\Node\Root {},"getUserFolder"], ["*** sensitive parameter replaced ***"])
13. /var/www/nextcloud/lib/private/Files/Node/LazyRoot.php line 283
    OC\Files\Node\LazyRoot->__call("getUserFolder", ["*** sensitive parameter replaced ***"])
14. /var/www/nextcloud/lib/private/Server.php line 1556
    OC\Files\Node\LazyRoot->getUserFolder("*** sensitive parameter replaced ***")
15. /var/www/nextcloud/lib/private/User/Session.php line 552
    OC\Server->getUserFolder("*** sensitive parameter replaced ***")
16. /var/www/nextcloud/lib/private/User/Session.php line 412
    OC\User\Session->prepareUserLogin(true, true)
17. /var/www/nextcloud/lib/private/Authentication/Login/CompleteLoginCommand.php line 44
    OC\User\Session->completeLogin("*** sensitive parameters replaced ***")
18. /var/www/nextcloud/lib/private/Authentication/Login/ALoginCommand.php line 40
    OC\Authentication\Login\CompleteLoginCommand->process(OC\Authentication\Login\LoginData {})
19. /var/www/nextcloud/lib/private/Authentication/Login/LoggedInCheckCommand.php line 61
    OC\Authentication\Login\ALoginCommand->processNextOrFinishSuccessfully(OC\Authentication\Login\LoginData {})
20. /var/www/nextcloud/lib/private/Authentication/Login/ALoginCommand.php line 40
    OC\Authentication\Login\LoggedInCheckCommand->process(OC\Authentication\Login\LoginData {})
21. /var/www/nextcloud/lib/private/Authentication/Login/EmailLoginCommand.php line 58
    OC\Authentication\Login\ALoginCommand->processNextOrFinishSuccessfully(OC\Authentication\Login\LoginData {})
22. /var/www/nextcloud/lib/private/Authentication/Login/ALoginCommand.php line 40
    OC\Authentication\Login\EmailLoginCommand->process(OC\Authentication\Login\LoginData {})
23. /var/www/nextcloud/lib/private/Authentication/Login/UidLoginCommand.php line 54
    OC\Authentication\Login\ALoginCommand->processNextOrFinishSuccessfully(OC\Authentication\Login\LoginData {})
24. /var/www/nextcloud/lib/private/Authentication/Login/ALoginCommand.php line 40
    OC\Authentication\Login\UidLoginCommand->process(OC\Authentication\Login\LoginData {})
25. /var/www/nextcloud/lib/private/Authentication/Login/UserDisabledCheckCommand.php line 57
    OC\Authentication\Login\ALoginCommand->processNextOrFinishSuccessfully(OC\Authentication\Login\LoginData {})
26. /var/www/nextcloud/lib/private/Authentication/Login/ALoginCommand.php line 40
    OC\Authentication\Login\UserDisabledCheckCommand->process(OC\Authentication\Login\LoginData {})
27. /var/www/nextcloud/lib/private/Authentication/Login/PreLoginHookCommand.php line 53
    OC\Authentication\Login\ALoginCommand->processNextOrFinishSuccessfully(OC\Authentication\Login\LoginData {})
28. /var/www/nextcloud/lib/private/Authentication/Login/Chain.php line 108
    OC\Authentication\Login\PreLoginHookCommand->process(OC\Authentication\Login\LoginData {})
29. /var/www/nextcloud/core/Controller/LoginController.php line 307
    OC\Authentication\Login\Chain->process(OC\Authentication\Login\LoginData {})
30. /var/www/nextcloud/lib/private/AppFramework/Http/Dispatcher.php line 170
    OC\Core\Controller\LoginController->tryLogin("*** sensitive parameters replaced ***")
31. /var/www/nextcloud/lib/private/AppFramework/Http/Dispatcher.php line 100
    OC\AppFramework\Http\Dispatcher->executeController(OC\Core\Controller\LoginController {}, "tryLogin")
32. /var/www/nextcloud/lib/private/AppFramework/App.php line 137
    OC\AppFramework\Http\Dispatcher->dispatch(OC\Core\Controller\LoginController {}, "tryLogin")
33. /var/www/nextcloud/lib/private/AppFramework/Routing/RouteActionHandler.php line 47
    OC\AppFramework\App::main("OC\\Core\\Controller\\LoginController", "tryLogin", OC\AppFramework\ ... {}, {_route: "core.login.tryLogin"})
34. <<closure>>
    OC\AppFramework\Routing\RouteActionHandler->__invoke({_route: "core.login.tryLogin"})
35. /var/www/nextcloud/lib/private/Route/Router.php line 297
    call_user_func(OC\AppFramework\ ... {}, {_route: "core.login.tryLogin"})
36. /var/www/nextcloud/lib/base.php line 1007
    OC\Route\Router->match("/login")
37. /var/www/nextcloud/index.php line 37
    OC::handleRequest()

POST /nextcloud/index.php/login
from 192.168.178.35 by uwjhn at 2020-07-15T18:21:40+00:00

It seems like the realDataDir is not derived correctly here for the source file, since /mnt/dietpi_userdata is a symlink to /mnt/7627eacf-bfd9-4168-9bd0-897988222727/dietpi_userdata, hence expanding data dir and comparing with source should match.

@szaimen

This comment was marked as resolved.

@szaimen szaimen added needs info 0. Needs triage Pending check for reproducibility or if it fits our roadmap and removed 1. to develop Accepted and waiting to be taken care of labels Jan 9, 2023
@MichaIng
Copy link
Member Author

Yes, it still occurs with NC 25.0.2:

In Local.php line 513:

  Following symlinks is not allowed

@szaimen
Copy link
Contributor

szaimen commented Jan 14, 2023

Hm... Did you check if that makes it work?

'localstorage.allowsymlinks' => false,

@MichaIng
Copy link
Member Author

MichaIng commented Jan 14, 2023

This doesn't help: The setting is not taken over into the config.php, regardless whether it is set to false or true, so it always defaults to false on install.

However, my point is that the check is done wrong, respectively the concern does not apply in the mentioned case, since the symlink is not "within" the data directory/the data dir does not contain the symlink, but it's part of the path "to" the data directory. So it is impossible "for Nextcloud to access files outside the data directory" in this setup (wording from config.sample.php).

@joshtrichards joshtrichards added the hotspot: filename handling Filenames - invalid, portable, blacklisting, etc. label Sep 4, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
0. Needs triage Pending check for reproducibility or if it fits our roadmap 25-feedback bug feature: install and update hotspot: filename handling Filenames - invalid, portable, blacklisting, etc.
Projects
None yet
Development

No branches or pull requests

7 participants