Is it possible to restrict admin login only from localhost?

How to make rule for login page that if username == ‘admin’ and IP != ‘127.0.0.1’ then deny?

Seems like NextCloud itself does not offer it out of the box? But if I write it directly to index.php script then it gets overwritten with next NC update?

what’s the best way to implement such logic?

After some research I got half of the solution. Since I don’t know how to finish this, I post it here as draft so if someone is interested he can continue from where I left.

  1. Create /var/www/nextcloud/apps/block_remote_admin_login/appinfo/app.php with the following content:
<?php

namespace BlockRemoteAdminLogin\AppInfo;

use OCP\Authentication\Events\LoginStartedEvent;
use OCP\AppFramework\App;
use OCP\EventDispatcher\IEventDispatcher;

class Application extends App {
    public function __construct(array $urlParams = []) {
        parent::__construct("block_remote_admin_login", $urlParams);

        if($_SERVER["REQUEST_URI"]=="/nextcloud/index.php/login"
           && isset($_POST["user"])
           && $_POST["user"] == "admin"
           && $_SERVER["REMOTE_ADDR"]!="127.0.0.1")
        {
            die("Admin login is only allowed from localhost");
        }

        // TODO: nc_username cookie is not mandatory for Nextcloud
        // and therefore attack who steals cookies can bypass the following check by removing cookie nc_username.
        // However preventing the login itself will reduce the possibility that you have cookies for admin account laying around somewhere.
        if(isset($_COOKIE["nc_username"]) && $_COOKIE["nc_username"] == 'admin'){
            die("How did you even get that cookie? Admin login is only allowed from localhost.");
        }
    }
}

new Application();
  1. Create /var/www/nextcloud/apps/block_remote_admin_login/appinfo/info.xml with the following content:
<?xml version="1.0"?>
<info>
  <id>block_remote_admin_login</id>
  <name>Block Remote Admin Login</name>
  <description>Only allows 'admin' to log in from localhost</description>
  <version>1.0.0</version>
  <namespace>BlockRemoteAdminLogin</namespace>
  <category>custom</category>
  <dependencies>
    <nextcloud min-version="26" />
  </dependencies>
</info>
  1. Create /var/www/nextcloud/apps/block_remote_admin_login/composer.json with the following content (possibly not required will keep it just in case):
{
  "name": "yourname/block_remote_admin_login",
  "description": "Block admin login from outside localhost",
  "type": "project",
  "require": {
    "php": ">=7.4"
  },
  "autoload": {
    "psr-4": {
      "BlockRemoteAdminLogin\\": ""
    }
  }
}

Enable it with command while inside nextcloud dir:

sudo -u www-data php occ app:enable block_remote_admin_login

You can get pretty close using the allowed_admin_ranges parameter in >=v30:

1 Like

Thanks, adding allowed_admin_ranges helped. I will mark your reply as a solution because writing a custom code would mean that I would have maintain that code myself. Using allowed_admin_ranges instead will mean that someone else will maintain that code.

This topic was automatically closed 8 days after the last reply. New replies are no longer allowed.