Why is my instance trying to install NextCloud after upgrade?
I've just upgraded to nextcloud:23.0.0-apache and after first restart it worked fine, but after that every restart fails to start NextCloud.
When I check the status it appears as not installed:
> docker exec -u 33 nextcloud-app php occ status
Nextcloud is not installed - only a limited number of commands are available
- installed: false
- version: 23.0.0.10
- versionstring: 23.0.0
- edition:
- maintenance: false
- needsDbUpgrade: false
- productname: Nextcloud
- extendedSupport: false
But my database is in place and intact:
nextcloud=# SELECT count(*) FROM pg_catalog.pg_tables WHERE tableowner = 'oc_admin';
count
-------
126
(1 row)
And my data is still there:
nextcloud=# SELECT count(*) FROM oc_users;
count
-------
42
(1 row)
So what is happening?
If I try to run php occ maintenance:install by hand it fails with:
Error while trying to initialise the database: An exception occurred while executing a query:
SQLSTATE[42P07]: Duplicate table: 7 ERROR: relation "oc_migrations" already exists
So how is this supposed to work?
I found the installation called by php occ maintenance:install is performed by this file:
https://github.com/nextcloud/server/blob/v23.0.0/core/Command/Maintenance/Install.php
But it appears the actual installation is performed here: https://github.com/nextcloud/server/blob/v23.0.0/lib/private/Setup.php#L278
But what interests me is how the installed status is detected:
'installed' => $this->config->getSystemValueBool('installed', false),
https://github.com/nextcloud/server/blob/0619207f13792250aea775a2c3133d41ab625980/core/Command/Status.php#L58
Based on lines like this it just appears to be line in the PHP config:
cat > ./tests/autoconfig-pgsql.php <<DELIM
<?php
\$AUTOCONFIG = array (
'installed' => false,
'dbtype' => 'pgsql',
https://github.com/nextcloud/server/blob/0619207f13792250aea775a2c3133d41ab625980/tests/travis/install.sh#L72-L76
As far as I can tell the /var/www/html/config/config.php file is generated at startup.
I tried creating a /usr/src/nextcloud/config/install.config.php file with contents like this:
<?php
$CONFIG = array (
'installed' => true,
);
But that didn't change anything. This is very confusing.
The installed value doesn't appear to be part of the config definition:
https://github.com/nextcloud/server/blob/v23.0.0/lib/private/SystemConfig.php
I don't get where $this->config->getSystemValueBool('installed', false) is supposed to come from...
I found this, which shows how $AUTOCONFIG values from autoconfig.php are loaded:
public function loadAutoConfig($post) {
if (file_exists($this->autoConfigFile)) {
\OCP\Util::writeLog('core', 'Autoconfig file found, setting up Nextcloud…', ILogger::INFO);
$AUTOCONFIG = [];
include $this->autoConfigFile;
$post = array_merge($post, $AUTOCONFIG);
}
https://github.com/nextcloud/server/blob/v23.0.0/core/Controller/SetupController.php#L130-L136
I tried creating my own config.php based off of sample.config.php, but now I'm getting this:
It looks like you are trying to reinstall your Nextcloud.
However the file CAN_INSTALL is missing from your config directory.
Please create the file CAN_INSTALL in your config folder to continue.
I do not want to install anything, I just want it to start. This is baffling behavior.
How can I stop it from trying to install things and just have it start.
This page appears to be coming from core/templates/installation_forbidden.php which is used in displaySetupForbidden():
private function displaySetupForbidden() {
\OC_Template::printGuestPage('', 'installation_forbidden');
}
https://github.com/nextcloud/server/blob/v23.0.0/core/Controller/SetupController.php#L89-L91
Which is used in every call to SetupController->run():
if (!is_file(\OC::$configDir.'/CAN_INSTALL')) {
$this->displaySetupForbidden();
return;
}
https://github.com/nextcloud/server/blob/v23.0.0/core/Controller/SetupController.php#L67-L70
And it looks like the attempt to run setup is executed at every call to handleRequest():
public static function handleRequest() {
\OC::$server->getEventLogger()->start('handle_request', 'Handle request');
$systemConfig = \OC::$server->getSystemConfig();
// Check if Nextcloud is installed or in maintenance (update) mode
if (!$systemConfig->getValue('installed', false)) {
\OC::$server->getSession()->clear();
$setupHelper = new OC\Setup(
$systemConfig,
\OC::$server->get(\bantu\IniGetWrapper\IniGetWrapper::class),
\OC::$server->getL10N('lib'),
\OC::$server->query(\OCP\Defaults::class),
\OC::$server->get(\Psr\Log\LoggerInterface::class),
\OC::$server->getSecureRandom(),
\OC::$server->query(\OC\Installer::class)
);
$controller = new OC\Core\Controller\SetupController($setupHelper);
$controller->run($_POST);
exit();
}
https://github.com/nextcloud/server/blob/v23.0.0/lib/base.php#L922-L941
And it looks like indeed the installed config value is checked to see if SetupController->run() should be called.
It appears the secret sauce is the presence of these three values together:
'version' => '23.0.0.10',
'instanceid' => 'xyz',
'installed' => true,
And then starting the container with apache2-foreground as entrypoint to avoid any installation/seeding steps.
How are you running the container? It is likely you have run into some oddities with how this container operates.
It works like the following
- Container start
- Check
/var/www/html/version.php - See if
/usr/src/nextcloud/version.phpis equal or newer - if this is a new version, copy
/usr/src/nextcloudinto/var/www/html - continue with upgrade
If the /var/www/html isn't persisted with a volume mount, then weird/bad things will happen.
Yes, this is deeply weird/wrong.
Completely agree, this behavior of copying stuff from /usr/src/nextcloud to /var/www/html is very dangerous and could easily lead to someone losing their encryption secret and rest of configuration.
This is why I've made apache2-foreground the entrypoint for the container and run Nginx in a separate container as running multiple services in a single container is quite the anti-pattern.
Completely agree, this behavior of copying stuff from
/usr/src/nextcloudto/var/www/htmlis very dangerous and could easily lead to someone losing their encryption secret and rest of configuration.This is why I've made
apache2-foregroundthe entrypoint for the container and run Nginx in a separate container as running multiple services in a single container is quite the anti-pattern.
Then you could fpm + nginx?
If your database /var/www/html/config /var/www/html/data /var/www/html/themes intact, you can deploy a new clean one with persistent, and bind mount / copy back the config,data,themes to new persistent root.
What? I already have it working, also, your suggestion is confusing.
So here is the thing, i used to accidentally remove the persistent webroot or whatever you called, as i always backup that three folder i mentioned, in another accidental peristent webroot i can redeploy without missing anything, as the three folder will determine the nextcloud state
Yes, I already have it working. My point still stands. Copying things over is a dangerous way to do setup if the files include things like encryption keys.
Well in this case there wouldn't be encryption keys; but it is still bad.
Containers shouldn't be copying their application files to a mounted volume before running it from the mounted volume! It is bad practice!
- It Adds a significant amount of time to upgrades.
- It complicates systems with multiple replicas.
- Potentially adds network overhead (many users have persistent volume mounts served by NFS/Ceph/Gluster/etc)
- Increases storage space needed for no advantage.
- Adds a unnecessary volume, complicating configuration for no benefit.
- if you skip the volume mount and run
apache2-foregroundit still copies (for no reason!) and utilizes local ephemeral storage.
Why is it like this? I can see two reasons why it was considered to be a good idea.
- php-fpm. A webservice(nginix) container needs the static application files, and rsyncing them to a volume is a way to achieve that.
- There is a single command run on the old install before the rsync:
run_as 'php /var/www/html/occ app:list' | sed -n "/Enabled:/,/Disabled:/p" > /tmp/list_before. This is generating a list of current addo-ons, so it can check them against add-ons after the rsync/update.
Howerver to these points:
- At the very least the non php-fpm images should not do this, like for the mod-php apache image. The rsync could be kept as a optional flag to support a nginix container. The better, more correct solution would be to release a nginix container, with the required Nextcloud static content as a separate tag.
- While this is nice, I am not sure it is required. A clean install shouldn't have a massive list of disabled add-ons. Just display the currently disabled add-ons at the end and it would be fine.
Proposed solution:
- Get rid of the copy at least for the apache container, but ideally for all of them.
- Consider adding a new container tag that runs nginix and has the Nextcloud static content that it needs to serve baked in.
- Check the version from
config.phpin the container.
Well in this case there wouldn't be encryption keys; but it is still bad.
Yes there would, I almost lost mine because of this. I only recovered it because I still had old volumes available.
If I ran docker volume prune I would have been in a bad spot.
There are encryption keys in /var/www/html !? If you're talking about keys in a custom apps directory then that should be its own volume for sure -- that vol will have to persist no matter what the deal is with /var/www/html due to how NC is designed.
I had the same issue. I think the reason was a non-compatible addon when upgrading from v22 to v23 (also my instance has no internet access). After updating the addon manually and restarting, Nextcloud was displayed as installed again.
@jakubgs I had the same issue, what I have done in my case is taking the containers down and removing them entirely with an exception to the volumes/data and then rebuilding using the latest release of NextCloud, I have gone to check why this is happening and from what I have noticed the config.php is messed up
The following environment variables are incorrect:
- POSTGRES_USER
- POSTGRES_PASSWORD
- NEXTCLOUD_TRUSTED_DOMAINS
Those variables are not as configured in my docker-compose, rather as the following:
- DB username is oc_administrator%
- DB Password is something random
And I also suggest having an environment variable to state whether this is an existing installation where no reinstallation/installation should be triggered.
In my case, I found that something had replaced the instanceid value (and a bunch of other stuff) in the config.php on the persistent volume :facepalm:
Service was restored by re-instating a backup of my config.php file with the correct values.
I am running into the same issue with
It looks like you are trying to reinstall your Nextcloud. However the file CAN_INSTALL is missing from your config directory. Please create the file CAN_INSTALL in your config folder to continue.
Reason is my config.php got blown away, I don't have a backup because I stupidly rm -r /usr/local/www/nextcloud-old/ directory which has the config/config.php folder. 🤦
My current config.php file looks like this:
root@nextcloud:/ # cat /usr/local/www/nextcloud/config/config.php
<?php
$CONFIG = array (
'instanceid' => 'id value here, which I don't know how to verify...',
);
What are my choices to get my service back running?
I am running into the same issue with
It looks like you are trying to reinstall your Nextcloud. However the file CAN_INSTALL is missing from your config directory. Please create the file CAN_INSTALL in your config folder to continue.Reason is my
config.phpgot blown away, I don't have a backup because I stupidlyrm -r /usr/local/www/nextcloud-old/directory which has theconfig/config.phpfolder. 🤦My current
config.phpfile looks like this:root@nextcloud:/ # cat /usr/local/www/nextcloud/config/config.php <?php $CONFIG = array ( 'instanceid' => 'id value here, which I don't know how to verify...', );What are my choices to get my service back running?
Next cloud when using online updater provides back up for config.php by default. Thanks Nextcloud for doing this and it saved my butt. haha. Location is here:
cat /mnt/data/updater-snadfnes/backups/nextcloud-23.0.8.1-1662165509/config/config.php Modify the content to match your current install version and updater.secret change to 'updater.release.channel' => 'stable',
After making the change visit the website will prompt you to update. Click on the update button will fix the system.
I am running into the same issue with
It looks like you are trying to reinstall your Nextcloud. However the file CAN_INSTALL is missing from your config directory. Please create the file CAN_INSTALL in your config folder to continue.Reason is myconfig.phpgot blown away, I don't have a backup because I stupidlyrm -r /usr/local/www/nextcloud-old/directory which has theconfig/config.phpfolder. 🤦 My currentconfig.phpfile looks like this:root@nextcloud:/ # cat /usr/local/www/nextcloud/config/config.php <?php $CONFIG = array ( 'instanceid' => 'id value here, which I don't know how to verify...', );What are my choices to get my service back running?
Next cloud when using online updater provides back up for config.php by default. Thanks Nextcloud for doing this and it saved my butt. haha. Location is here:
cat /mnt/data/updater-snadfnes/backups/nextcloud-23.0.8.1-1662165509/config/config.php Modify the content to match your current install version and updater.secret change to 'updater.release.channel' => 'stable',
After making the change visit the website will prompt you to update. Click on the update button will fix the system.
Thanks for this.
For the sake of generalisation: what you mentioned as /mnt/data is the path-to-nextcloud-data-folder. It was not the same to me.
Then, updater-snadfnes is actually different for everyone. In fact, "snadfness" is very likely your instanceid value.
Cheers,