Skip to content

[Bug]: Bug: Federation API (/ocm-provider/) causes fatal hash_hkdf error even when the app is disabled #54597

@Evertondiego-dev

Description

@Evertondiego-dev

⚠️ This issue respects the following points: ⚠️

Bug description

Bug Description

A Nextcloud instance is stuck in a loop of fatal errors related to hash_hkdf(). The root cause seems to be a bug where the core application attempts to execute the Federation/OCM controller (/ocm-provider/) even after the corresponding apps (federation and cloud_federation_api) have been explicitly disabled via occ. This behavior persists even after a full re-installation where the database backup was restored, indicating the corrupted state is carried over and the application does not correctly handle the "disabled" status of the app.

Steps to Reproduce

This issue is tied to a specific corrupted database state, making it hard to reproduce from scratch. However, the conditions are:

  1. Have a Nextcloud instance (v31.0.8.1 in my case) where the database state for the Federation feature is corrupted (likely a missing or malformed app-core-ocm_external key).
  2. Disable the federation and cloud_federation_api apps using the occ app:disable command.
  3. The server's internal crawler continues to hit the /ocm-provider/ endpoint, or a user opens the "Files" app.
  4. The fatal error is triggered.

Expected Behavior

After an app is disabled, its controllers and routes should be completely deactivated. Any call to its endpoints (like /ocm-provider/) should result in a standard 404 Not Found error, and no code from the disabled app should be executed.

Actual Behavior

The OCMController from the disabled app is still being routed and executed, leading to the fatal error when it tries to access its cryptographic keys. The log is spammed with the following exception:

{
  "reqId": "4e3gqUYkAKq9mdvrtfOo",
  "level": 3,
  "time": "2025-08-25T04:44:31+00:00",
  "remoteAddr": "172.20.0.1",
  "user": "--",
  "app": "index",
  "method": "HEAD",
  "url": "/ocm-provider/",
  "message": "hash_hkdf(): Argument #2 ($key) cannot be empty in file '/var/www/html/lib/private/Security/Crypto.php' line 147",
  "userAgent": "Nextcloud Server Crawler",
  "version": "31.0.8.1",
  "exception": {
    "Exception": "Exception",
    "Message": "hash_hkdf(): Argument #2 ($key) cannot be empty in file '/var/www/html/lib/private/Security/Crypto.php' line 147",
    "File": "/var/www/html/lib/private/AppFramework/Http/Dispatcher.php",
    "Line": 146,
    "Previous": {
      "Exception": "ValueError",
      "Message": "hash_hkdf(): Argument #2 ($key) cannot be empty",
      "File": "/var/www/html/lib/private/Security/Crypto.php",
      "Line": 147
    }
  }
}

### Steps to reproduce

1. You can copy and paste this text directly into the "Steps to reproduce" box:
(Você pode copiar e colar este texto diretamente na caixa "Steps to reproduce"):
2. Start with a clean installation of Nextcloud Hub 10 (31.0.8).
(Comece com uma instalação limpa do Nextcloud Hub 10 (31.0.8).)
3. Enable the federation and cloud_federation_api apps.
(Ative os aplicativos federation e cloud_federation_api.)
4. Simulate the database corruption by removing the external OCM key. Connect to your database and run the following SQL query:
(Simule a corrupção do banco de dados removendo a chave OCM externa. Conecte-se ao seu banco de dados e execute a seguinte query SQL:)
5. DELETE FROM oc_appconfig WHERE appid = 'cloud_federation_api' AND configkey = 'app-core-ocm_external';
6. Disable the federation and cloud_federation_api apps again using the web interface or the occ command.
(Desative os aplicativos federation e cloud_federation_api novamente, usando a interface web ou o comando occ.)
7. Trigger a background job or the server crawler. You can do this by running the cron job manually:
(Execute uma tarefa de fundo ou o rastreador do servidor. Você pode fazer isso executando o cron job manualmente:)
sudo -u www-data php /path/to/nextcloud/cron.php
8. Check the nextcloud.log file. The fatal error hash_hkdf(): Argument #2 ($key) cannot be empty will appear, triggered by a HEAD request to /ocm-provider/.
(Verifique o arquivo nextcloud.log. O erro fatal hash_hkdf(): Argument #2 ($key) cannot be empty irá aparecer, acionado por uma requisição HEAD para /ocm-provider/.)


### Expected behavior

Expected behavior
(Comportamento Esperado)

Após um aplicativo ser desativado, o Nextcloud não deve tentar executar nenhum código relacionado a ele. O servidor não deve encaminhar requisições para endpoints de aplicativos desativados.

### Nextcloud Server version

31

### Operating system

Debian/Ubuntu

### PHP engine version

PHP 8.3

### Web server

Nginx

### Database engine version

MariaDB

### Is this bug present after an update or on a fresh install?

Updated from a MINOR version (ex. 32.0.1 to 32.0.2)

### Are you using the Nextcloud Server Encryption module?

Encryption is Disabled

### What user-backends are you using?

- [x] Default user-backend _(database)_
- [ ] LDAP/ Active Directory
- [ ] SSO - SAML
- [ ] Other

### Configuration report

```json
{
    "system": {
        "instanceid": "***REMOVED SENSITIVE VALUE***",
        "passwordsalt": "***REMOVED SENSITIVE VALUE***",
        "secret": "***REMOVED SENSITIVE VALUE***",
        "trusted_domains": [
            "31.97.245.34:8080",
            "geddocsint.duckdns.org",
            "www.geddocsint.duckdns.org",
            "localhost:8080"
        ],
        "datadirectory": "***REMOVED SENSITIVE VALUE***",
        "dbtype": "mysql",
        "version": "31.0.8.1",
        "overwrite.cli.url": "https:\/\/geddocsint.duckdns.org",
        "overwriteprotocol": "https",
        "overwritehost": "geddocsint.duckdns.org",
        "trusted_proxies": "***REMOVED SENSITIVE VALUE***",
        "dbport": "",
        "dbtableprefix": "oc_",
        "mysql.utf8mb4": true,
        "dbuser": "***REMOVED SENSITIVE VALUE***",
        "dbpassword": "***REMOVED SENSITIVE VALUE***",
        "dbname": "***REMOVED SENSITIVE VALUE***",
        "dbhost": "***REMOVED SENSITIVE VALUE***",
        "installed": true,
        "defaultapp": "",
        "default_phone_region": "BR",
        "maintenance": false,
        "loglevel": 2,
        "maintenance_window_start": 3,
        "dbtxnlevel": "READ-COMMITTED",
        "memcache.local": "\\OC\\Memcache\\APCu",
        "memcache.distributed": "\\OC\\Memcache\\Redis",
        "memcache.locking": "\\OC\\Memcache\\Redis",
        "redis": {
            "host": "***REMOVED SENSITIVE VALUE***",
            "password": "***REMOVED SENSITIVE VALUE***",
            "port": 6379
        },
        "session_handler": "redis",
        "session_save_path": "tcp:\/\/redis:6379",
        "session_lifetime": 604800,
        "app_install_overwrite": [
            "stt_helper"
        ],
        "htaccess.RewriteBase": "\/",
        "apps_paths": [
            {
                "path": "\/var\/www\/html\/apps",
                "url": "\/apps",
                "writable": false
            },
            {
                "path": "\/var\/www\/html\/custom_apps",
                "url": "\/custom_apps",
                "writable": true
            }
        ],
        "forwarded_for_headers": [
            "HTTP_X_REAL_IP"
        ]
    }
}

List of activated Apps

Enabled:
  - activity: 4.0.0
  - app_api: 5.0.2
  - bruteforcesettings: 4.0.0
  - circles: 31.0.0
  - cloud_federation_api: 1.14.0
  - comments: 1.21.0
  - contactsinteraction: 1.12.0
  - dashboard: 7.11.0
  - dav: 1.33.0
  - federatedfilesharing: 1.21.0
  - federation: 1.21.0
  - files: 2.3.1
  - files_downloadlimit: 4.0.0
  - files_fulltextsearch: 31.0.0
  - files_pdfviewer: 4.0.0
  - files_reminders: 1.4.0
  - files_sharing: 1.23.1
  - files_trashbin: 1.21.0
  - files_versions: 1.24.0
  - firstrunwizard: 4.0.0
  - fulltextsearch: 31.0.0
  - logreader: 4.0.0
  - lookup_server_connector: 1.19.0
  - nextcloud_announcements: 3.0.0
  - notifications: 4.0.0
  - oauth2: 1.19.1
  - onlyoffice: 9.10.0
  - password_policy: 3.0.0
  - photos: 4.0.0
  - privacy: 3.0.0
  - profile: 1.0.0
  - provisioning_api: 1.21.0
  - recommendations: 4.0.0
  - related_resources: 2.0.0
  - richdocuments: 8.7.4
  - serverinfo: 3.0.0
  - settings: 1.14.0
  - sharebymail: 1.21.0
  - spreed: 21.1.3
  - support: 3.0.0
  - survey_client: 3.0.0
  - systemtags: 1.21.1
  - text: 5.0.0
  - theming: 2.6.1
  - theming_customcss: 1.18.0
  - twofactor_backupcodes: 1.20.0
  - updatenotification: 1.21.0
  - user_status: 1.11.0
  - viewer: 4.0.0
  - weather_status: 1.11.0
  - webhook_listeners: 1.2.0
  - workflowengine: 2.13.0
Disabled:
  - admin_audit: 1.21.0
  - electronicsignatures: 3.0.5 (installed 3.0.5)
  - encryption: 2.19.0
  - files_external: 1.23.0
  - files_fulltextsearch_tesseract: 27.0.1 (installed 27.0.1)
  - suspicious_login: 9.0.1
  - twofactor_nextcloud_notification: 5.0.0
  - twofactor_totp: 13.0.0-dev.0
  - user_ldap: 1.22.0

Nextcloud Signing status

Nextcloud Logs

{"reqId":"oBxLcmmh78IBW8DbZ3aN","level":3,"time":"2025-08-25T05:46:48+00:00","remoteAddr":"172.20.0.1","user":"--","app":"index","method":"HEAD","url":"/ocm-provider/","message":"hash_hkdf(): Argument #2 ($key) cannot be empty in file '/var/www/html/lib/private/Security/Crypto.php' line 147","userAgent":"Nextcloud Server Crawler","version":"31.0.8.1","exception":{"Exception":"Exception","Message":"hash_hkdf(): Argument #2 ($key) cannot be empty in file '/var/www/html/lib/private/Security/Crypto.php' line 147","Code":0,"Trace":[{"file":"/var/www/html/lib/private/AppFramework/App.php","line":161,"function":"dispatch","class":"OC\\AppFramework\\Http\\Dispatcher","type":"->","args":[{"__class__":"OC\\Core\\Controller\\OCMController"},"discovery"]},{"file":"/var/www/html/lib/private/Route/Router.php","line":315,"function":"main","class":"OC\\AppFramework\\App","type":"::","args":["OC\\Core\\Controller\\OCMController","discovery",{"__class__":"OC\\AppFramework\\DependencyInjection\\DIContainer"},{"_route":"core.ocm.discovery"}]},{"file":"/var/www/html/lib/base.php","line":1061,"function":"match","class":"OC\\Route\\Router","type":"->","args":["/ocm-provider/"]},{"file":"/var/www/html/index.php","line":24,"function":"handleRequest","class":"OC","type":"::","args":[]}],"File":"/var/www/html/lib/private/AppFramework/Http/Dispatcher.php","Line":146,"Previous":{"Exception":"ValueError","Message":"hash_hkdf(): Argument #2 ($key) cannot be empty","Code":0,"Trace":[{"file":"/var/www/html/lib/private/Security/Crypto.php","line":147,"function":"hash_hkdf","args":["sha512",{"__class__":"SensitiveParameterValue"}]},{"file":"/var/www/html/lib/private/Security/Crypto.php","line":102,"function":"decryptWithoutSecret","class":"OC\\Security\\Crypto","type":"->","args":["*** sensitive parameters replaced ***"]},{"file":"/var/www/html/lib/private/Security/IdentityProof/Manager.php","line":109,"function":"decrypt","class":"OC\\Security\\Crypto","type":"->","args":["*** sensitive parameters replaced ***"]},{"file":"/var/www/html/lib/private/Security/IdentityProof/Manager.php","line":162,"function":"retrieveKey","class":"OC\\Security\\IdentityProof\\Manager","type":"->","args":["app-core-ocm_external"]},{"file":"/var/www/html/lib/private/OCM/OCMSignatoryManager.php","line":103,"function":"getAppKey","class":"OC\\Security\\IdentityProof\\Manager","type":"->","args":["core","ocm_external"]},{"file":"/var/www/html/apps/cloud_federation_api/lib/Capabilities.php","line":81,"function":"getLocalSignatory","class":"OC\\OCM\\OCMSignatoryManager","type":"->","args":[]},{"file":"/var/www/html/core/Controller/OCMController.php","line":71,"function":"getCapabilities","class":"OCA\\CloudFederationAPI\\Capabilities","type":"->","args":[]},{"file":"/var/www/html/lib/private/AppFramework/Http/Dispatcher.php","line":200,"function":"discovery","class":"OC\\Core\\Controller\\OCMController","type":"->","args":[]},{"file":"/var/www/html/lib/private/AppFramework/Http/Dispatcher.php","line":114,"function":"executeController","class":"OC\\AppFramework\\Http\\Dispatcher","type":"->","args":[{"__class__":"OC\\Core\\Controller\\OCMController"},"discovery"]},{"file":"/var/www/html/lib/private/AppFramework/App.php","line":161,"function":"dispatch","class":"OC\\AppFramework\\Http\\Dispatcher","type":"->","args":[{"__class__":"OC\\Core\\Controller\\OCMController"},"discovery"]},{"file":"/var/www/html/lib/private/Route/Router.php","line":315,"function":"main","class":"OC\\AppFramework\\App","type":"::","args":["OC\\Core\\Controller\\OCMController","discovery",{"__class__":"OC\\AppFramework\\DependencyInjection\\DIContainer"},{"_route":"core.ocm.discovery"}]},{"file":"/var/www/html/lib/base.php","line":1061,"function":"match","class":"OC\\Route\\Router","type":"->","args":["/ocm-provider/"]},{"file":"/var/www/html/index.php","line":24,"function":"handleRequest","class":"OC","type":"::","args":[]}],"File":"/var/www/html/lib/private/Security/Crypto.php","Line":147},"message":"hash_hkdf(): Argument #2 ($key) cannot be empty in file '/var/www/html/lib/private/Security/Crypto.php' line 147","exception":[],"CustomMessage":"hash_hkdf(): Argument #2 ($key) cannot be empty in file '/var/www/html/lib/private/Security/Crypto.php' line 147"},"id":"68abf8d4e8756"}

Additional info

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    0. Needs triagePending check for reproducibility or if it fits our roadmap31-feedbackbug

    Type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions