5 Commits

Author SHA1 Message Date
dillard 040743d351 Credit fanategorius and Git-Usr123 forks in README 2026-09-11 17:52:59 +02:00
dillard 85890e12db Update README to reflect active fork status, drop stale Russian translation
Also backport OccController's getConfig() -> IConfig::class fix (deprecated
internal API -> stable OCP interface), spotted while comparing against
Git-Usr123/occweb.
2026-09-11 17:40:12 +02:00
dillard cd01a2fa17 Merge branch 'fix/fetch-return-type-php81' into deploy-nc01 2026-08-09 13:06:32 +02:00
dillard a4a8f9a4eb Fix missing admin check on OccController routes (security)
index(), cmd() and list() were accessible to any logged-in user.
The navigation menu already restricts visibility to admins, but the
routes themselves were unprotected — any authenticated user who knows
the URL could execute occ commands or list all available commands.

Fix: inject IGroupManager + IUserSession, add requireAdmin() helper,
call it at the start of all three public methods. Matches the pattern
already used in DbController.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-07-07 22:04:05 +02:00
dillard f681caca35 Fix OccOutput::fetch() return type for PHP 8.1+ compatibility
BufferedOutput::fetch() declares a string return type in Symfony 5+.
PHP 8.1 enforces return type compatibility with parent methods, causing
a fatal 500 error when the occweb page loads.

Fix: add ': string' return type to OccOutput::fetch().

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-07-07 21:25:56 +02:00
4 changed files with 48 additions and 135 deletions
+26 -7
View File
@@ -1,15 +1,34 @@
# ⚠️ Deprecated ⚠️ OCCWeb terminal
*Читать на [русском](README.ru.md).*
# OCCWeb terminal (maintained fork)
### A web terminal for admins to launch Nextcloud's occ commands
![occweb](https://github.com/Adphi/OCCWeb/raw/main/appinfo/screenshot.png)
## About this fork
## ⚠️ Deprecated ⚠️
As nextcloudd has no native support for asynchronous operations, due to the use of php, this aplication is deprecated, and will no longer support the Nextcloud' future versions (19+). I did not find a way to implemement true support for interactive and long running occ tasks in a web terminal whitout introducing addtional dependencies (through websockets, for example), the lack of true asynchronous occ operations can lead to serious alterations of voluminous instances.
[This issue](https://github.com/nextcloud/server/issues/16726) may give some hints on why I decided to not support this application anymore.
The original [Adphi/occweb](https://github.com/Adphi/occweb) was marked deprecated by its
author and is unmaintained. This fork tracks [fanategorius/occweb](https://github.com/fanategorius/occweb),
which picked up compatibility maintenance where Adphi left off, and adds SQL query mode,
security hardening (admin checks, CSRF/confirmation flows, transactional batches), and PHP
8.1+ compatibility fixes on top.
### Credits
- [Adphi/occweb](https://github.com/Adphi/occweb) — original author/project.
- [fanategorius/occweb](https://github.com/fanategorius/occweb) — the actively maintained
fork this repo is based on and tracks.
- [Git-Usr123/occweb](https://github.com/Git-Usr123/occweb) — independent fork; the
`OC::$server->getConfig()` → `OC::$server->get(\OCP\IConfig::class)` fix in
`OccController.php` was spotted there and backported here.
**This tool is still not the right place for big/risky operations.** It has no support for
asynchronous or long-running tasks — every command runs synchronously inside a single PHP
web request, so anything that takes a while (`occ files:scan` on a large instance, a Nextcloud
major-version `occ upgrade`, `occ maintenance:mode --on` workflows) can time out mid-operation
with no way to recover cleanly. Use a real shell (SSH + `occ` directly, or the guest-agent/
console) for major upgrades and other long-running or high-blast-radius operations; reserve
this terminal for routine day-to-day occ/SQL admin tasks. [This issue](https://github.com/nextcloud/server/issues/16726)
has background on why Nextcloud has no native async support for occ tasks.
## Install
@@ -110,4 +129,4 @@ This does not apply on a fresh `occ app:enable` install — that command sets
`installed_version` correctly on its own.
## TODOs:
See [open issues](https://github.com/Adphi/occweb/issues)
See [open issues](https://github.com/dillardblom/occweb/issues)
-126
View File
@@ -1,126 +0,0 @@
# ⚠️ Устарело ⚠️ OCCWeb terminal
*Read in [English](README.md).*
### Веб-терминал для администраторов для запуска occ-команд Nextcloud
![occweb](https://github.com/Adphi/OCCWeb/raw/main/appinfo/screenshot.png)
## ⚠️ Устарело ⚠️
Поскольку Nextcloud не имеет встроенной поддержки асинхронных операций
(из-за использования PHP), это приложение считается устаревшим и больше не
будет поддерживать будущие версии Nextcloud (19+). Автору не удалось найти
способ реализовать полноценную поддержку интерактивных и долгих occ-задач в
веб-терминале без введения дополнительных зависимостей (например, через
websockets), а отсутствие настоящей асинхронности может привести к серьёзным
проблемам на больших инсталляциях.
[Этот issue](https://github.com/nextcloud/server/issues/16726) объясняет,
почему разработчик решил больше не поддерживать это приложение.
## Установка
Сборка не нужна (чистый PHP + vanilla JS). Клонируйте прямо в `apps/`
целевого сервера и запустите установочный скрипт:
```bash
cd /var/www/nextcloud/apps
git clone https://github.com/fanategorius/occweb.git
bash occweb/install.sh
```
`install.sh` удаляет dev/CI-файлы, не нужные для работающей установки
(`tests/`, `.travis.yml`, `phpunit*.xml`, `composer.json`, `composer.lock`,
`Makefile`), выставляет `chown -R` на пользователя веб-сервера и выполняет
`occ app:enable`. По умолчанию считает, что Nextcloud лежит в
`/var/www/nextcloud`, а пользователь веб-сервера — `www-data`; если у вас
иначе, передайте своими аргументами:
```bash
bash occweb/install.sh /path/to/nextcloud custom-web-user
```
`occ app:enable` сам корректно проставит версию приложения в базе, поэтому
оговорки из раздела «Обновление кода на сервере» ниже к свежей установке не
относятся — они актуальны только когда приложение уже включено и вы
обновляете его на месте.
Перед установкой сверьте версию вашего Nextcloud с диапазоном в
`appinfo/info.xml` (`dependencies/nextcloud`, `min-version`/`max-version`)
— `occ app:enable` откажется включать приложение вне этого диапазона.
Учтите: `install.sh` удаляет файлы, отслеживаемые в git. Если планируете
дальше обновлять эту установку через `git pull`, а не пере-клонированием —
имейте в виду, что будущее изменение одного из удалённых файлов в апстриме
может привести к отказу `git pull` смёржить изменения. Git сам сообщит об
этом, и файл можно вернуть командой `git checkout -- <file>`.
## Режим SQL-запросов
Введите `sql` в терминале, чтобы переключиться в режим SQL-запросов и
выполнять произвольные SQL-запросы напрямую к базе данных Nextcloud (только
для администраторов). Запросы разделяются `;`. Используйте **Shift+Enter**
для перехода на новую строку и **Enter**, чтобы отправить весь блок одним
запросом — это важно для скриптов вида
`SET vars.x = 'value'; SELECT current_setting('vars.x');`, так как все
запросы, отправленные одним блоком, выполняются в рамках одного соединения
(сессии) с базой данных. Введите `occ`, чтобы вернуться в обычный режим
occ-команд.
⚠️ Для `DELETE`/`UPDATE` нет отмены — внимательно проверяйте, что вы
собираетесь выполнить, желательно сначала на некритичной записи/пользователе.
## ⚠️ Предупреждения ⚠️
- Это приложение не является настоящим интерактивным терминалом и не
поддерживает долгие задачи.
Поэтому на крупных инсталляциях команды вроде `occ files:scan` могут
завершаться по таймауту с ошибкой.
- Не используйте `occ maintenance:mode --on`, это очевидно...
- Шаблон `rename-user` — это **best-effort**, а не официально поддерживаемая
Nextcloud операция. Он обновляет только известные таблицы ядра
(`oc_users`, `oc_preferences`, `oc_group_user`, `oc_group_admin`,
`oc_ldap_user_mapping`, `oc_share`, `oc_mounts`, `oc_storages`), но **не**
трогает таблицы сторонних приложений (Talk, Calendar, Contacts, Mail,
двухфакторная аутентификация/WebAuthn и т.д.). Дополнительно нужно вручную
переименовать каталог данных пользователя на диске (`data/<старый> ->
data/<новый>`) при остановленном веб-сервере или в режиме обслуживания, а
затем выполнить `occ files:scan --all`. Сначала сделайте бэкап базы и
протестируйте на некритичном аккаунте.
## Обновление кода на сервере
После того как новый код скопирован/спуллен в `nextcloud/apps/occweb/`,
обязательно перезапустите PHP, иначе изменения не применятся. `occ
app:disable`/`app:enable` **не помогает** — эта команда не сбрасывает
opcode-кэш PHP, из-за чего может продолжать работать старая закэшированная
версия кода (характерный симптом — маршруты внезапно отвечают 404).
Перезапустите сам процесс PHP, например:
```bash
sudo systemctl restart php8.3-fpm # укажите свою версию PHP
sudo systemctl restart apache2 # если PHP работает как модуль Apache
```
### Если меняете `<version>` в `appinfo/info.xml`
Nextcloud хранит установленную версию каждого приложения в базе
(`installed_version` в `oc_appconfig`) отдельно от `<version>` в
`info.xml`. Если вы правите файлы на месте (копированием/`git pull`), а не
через App Store или `occ upgrade`, эти два значения расходятся — и
Nextcloud считает, что «инстансу нужен апгрейд», блокируя большинство
`occ`-команд за CLI-визардом обновления, хотя само ядро Nextcloud никак не
менялось. После бампа версии синхронизируйте её вручную:
```bash
sudo -u www-data php /var/www/nextcloud/occ config:app:set occweb installed_version --value="X.Y.Z"
```
(то же значение `X.Y.Z`, что и в новом `<version>`), затем перезапустите
PHP, как описано выше. На свежую установку через `occ app:enable` это не
распространяется — там версия проставляется корректно автоматически.
## Планы (TODO):
См. [открытые issues](https://github.com/Adphi/occweb/issues)
+21 -1
View File
@@ -9,6 +9,7 @@ use OC\MemoryInfo;
use OCP\IRequest;
use OCP\AppFramework\Http\TemplateResponse;
use OCP\AppFramework\Http\DataResponse;
use OCP\AppFramework\Http\JSONResponse;
use OCP\AppFramework\Controller;
use Symfony\Component\Console\Input\StringInput;
use Symfony\Component\Console\Output\OutputInterface;
@@ -31,7 +32,7 @@ class OccController extends Controller
$this->application = new Application(
OC::$server->get(\OCP\ServerVersion::class),
OC::$server->getConfig(),
OC::$server->get(\OCP\IConfig::class),
OC::$server->get(\OCP\EventDispatcher\IEventDispatcher::class),
new FakeRequest(),
$this->logger,
@@ -47,11 +48,28 @@ class OccController extends Controller
$this->symphonyApplication = $reflectionProperty->getValue($this->application);
}
private function requireAdmin(): ?JSONResponse
{
// Services via OC::$server zodat de constructor-signatuur ongewijzigd blijft
// en NC's DI-container (zonder application.php) de class kan resolven.
$userSession = OC::$server->get(\OCP\IUserSession::class);
$user = $userSession->getUser();
if ($user === null) {
return new JSONResponse(['error' => 'Not authenticated'], 401);
}
$groupManager = OC::$server->get(\OCP\IGroupManager::class);
if (!$groupManager->isAdmin($user->getUID())) {
return new JSONResponse(['error' => 'Admin privileges required'], 403);
}
return null;
}
/**
* @NoCSRFRequired
*/
public function index()
{
if ($err = $this->requireAdmin()) return $err;
return new TemplateResponse('occweb', 'index');
}
@@ -76,6 +94,7 @@ class OccController extends Controller
*/
public function cmd($command)
{
if ($err = $this->requireAdmin()) return $err;
$this->logger->debug($command);
$input = new StringInput($command);
$response = $this->run($input);
@@ -84,6 +103,7 @@ class OccController extends Controller
}
public function list() {
if ($err = $this->requireAdmin()) return $err;
$defs = $this->symphonyApplication->all();
$cmds = array();
foreach ($defs as $d) {
+1 -1
View File
@@ -35,7 +35,7 @@ class OccOutput extends BufferedOutput implements ConsoleOutputInterface
);
}
public function fetch()
public function fetch(): string
{
// Получаем основной буфер
$content = parent::fetch();