EC-CUBE / EC-CUBE/ec-cube2

Web サーバー権限に依存しないコンテンツ管理 — ec-cube2/cli への CLI 導線の追加(4系 EC-CUBE/ec-cube#7072 の 2系版)

Open
#1,436 0 comments 0 reactions 0 assignees View on GitHub
discussion enhancement
Dominant language
PHP
Stars
92
Forks
97
Avg merge
4d 2h
Merged PRs (30d)
9

Description

## 概要(Overview)

4系(EC-CUBE/ec-cube)で、デザイン管理などのファイル書き込みを Web サーバー権限から
SSH ログインユーザー権限の CLI へ移す設計を提案しています。

- EC-CUBE/ec-cube#7072 「[4.4] Web サーバー権限に依存しないコンテンツ管理 — CLI 導線と build/cache 分離の実装設計」

2系にも同じ課題があり、かつ **`ec-cube2/cli`(`composer.json` の require に `^1.4.3`)という土台が既にあります**。

**4系で仕様を固めてから 2系を実装する**流れとし、本 issue はその受け皿として作成します。
現時点では 2系側の調査結果と、共有すべき仕様の範囲を整理するものです。

なお、ファイル所有ユーザーと PHP 実行ユーザーの分離という前提は #841 と共通しています。

## 現状の調査結果

### `ec-cube2/cli` の構造

- Symfony Console + DI コンテナ(`config/services.yaml` + `AddConsoleCommandPass`)、65 ファイル
- **`Eccube2\Console\Application::appendConfigPath()` / `prependConfigPath()`** により、
外部から `services.yaml` を読み込ませてコマンドを追加できる拡張機構がある
- `Command` は薄く、処理は `Eccube2\Util\*` へ委譲する構成
- `Eccube2\Init::init()` で 2系本体をブートストラップ

### CLI のカバレッジ比較

| 領域 | 2系 `ec-cube2/cli` | 4系 |
|---|---|---|
| 設定パラメータ | `parameter:get` / `parameter:set`(`data/config/config.php`) | 無い(`.env` は管理画面のみ) |
| キャッシュ削除 | `cache:clear` | `cache:clear`(Symfony 標準) |
| プラグイン | `plugin:*` / `module:*` | `eccube:plugin:*` |
| テンプレート切替 | `template:{pc,mobile,smartphone}:{get,set}` | 無い(管理画面のみ) |
| バックアップ | `backup:create` / `restore` / `list` / `delete` | 無い |
| 管理者アカウント | `member:create` / `set-password` / `enable` / `disable` | 無い |
| 本体アップデート | `zip:download` / `update` / `info` | 無い |
| オーナーズストア | `owners-store:set-key` / `list` | 一部 |
| **ページ / ブロック / CSS / ヘッダーの内容編集** | **無い** | **無い** |
| **ファイル管理** | **無い** | **無い** |
| **権限診断** | **無い** | **無い** |

CLI のカバレッジは 2系のほうが広く、バックアップ・管理者アカウント作成・本体アップデートは
4系に無い機能です。一方で、**両系統で欠けているのは同じ 3 つ**(コンテンツ編集・ファイル管理・権限診断)で、
これが #7072 のスコープと一致します。

### 2系の書き込み経路は集約されている

デザイン管理からのファイル書き込みは `SC_Helper_FileManager_Ex::sfWriteFile()` の 1 本に集約されています。

| 機能 | 呼び出し元 |
|---|---|
| ページ編集(`tpl_data`) | `data/class/pages/admin/design/LC_Page_Admin_Design_MainEdit.php:246` |
| ページの PHP ファイル生成 | `data/class/pages/admin/design/LC_Page_Admin_Design_MainEdit.php:397` |
| CSS 編集 | `data/class/pages/admin/design/LC_Page_Admin_Design_CSS.php:189` |
| ヘッダー / フッター編集 | `data/class/pages/admin/design/LC_Page_Admin_Design_Header.php:169` |

4系は `dumpFile` / `file_put_contents` / `move` が各コントローラに散在しているため、
CLI へ切り出す観点では 2系のほうが構造的に有利です。
(ブロックの保存は `SC_Helper_Bloc_Ex` 経由で別経路のため、別途整理が必要です)

## 期待する内容(Expect) or 要望(Requirement)

### 1. 書き込み先を 3 レーンに分類する(2系版・要精査)

4系 #7072 と同じ考え方を 2系のディレクトリ構成へ適用します。以下は現時点の整理案です。

**レーン W — Web サーバー所有(書き込みが必要)**

| 定数 | パス |
|---|---|
| `CACHE_REALDIR` | `data/cache/` |
| `COMPILE_REALDIR` / `COMPILE_ADMIN_REALDIR` | `data/Smarty/templates_c/{template}/`, `data/Smarty/templates_c/admin/` |
| `LOG_REALFILE` / `PLUGIN_LOG_REALFILE` | `data/logs/site.log`, `data/logs/plugin.log` |
| `IMAGE_SAVE_REALDIR` | `html/upload/save_image/` |
| `PLUGIN_TEMP_REALDIR` | `html/upload/temp_plugin/` |
| `DOWNLOADS_TEMP_PLUGIN_*` | `data/downloads/tmp/...` |

**レーン S — SSH ユーザー所有(Web サーバーは読み取りのみ)**

| 定数 | パス |
|---|---|
| `SMARTY_TEMPLATES_REALDIR` | `data/Smarty/templates/` |
| `USER_REALDIR` | `html/user_data/` |
| `USER_TEMPLATE_REALDIR` | `html/user_data/packages/` |
| `PLUGIN_REALDIR` | `html/user_data/plugins/` |
| `PLUGIN_HTML_REALDIR` | `html/plugin/` |
| `CLASS_EX_REALDIR` | `data/class_extends/` |
| (設定ファイル) | `data/config/config.php` |
| `PLUGIN_UPLOAD_REALDIR` | `data/downloads/plugin/` |

**確認が必要な点**

- `COMPILE_REALDIR` は `data/class/SC_Initial.php:292-301` がリクエスト処理中に `mkdir` します。
Smarty の `compile_check` が有効であればテンプレート更新は自動反映されるため、
4系で必要になる build ディレクトリ分離に相当する対応は 2系では不要になる見込みです(実設定の確認が必要)。
- `PLUGIN_REALDIR` が `html/user_data/plugins/` と公開ディレクトリ配下にある点は、
4系の `app/Plugin`(非公開)と構成が異なるため、レーン分けの検討時に個別の判断が必要です。
- 複数箇所で `umask(0)` が実行されている件(#841)と合わせて整理する必要があります。

### 2. `ec-cube2/cli` へ追加するコマンド

4系 #7072 と同じ仕様に揃えます。

```
design:page:list|show|apply|remove dtb_pagelayout + data/Smarty/templates/**、生成 PHP
design:block:list|show|apply|remove dtb_bloc + テンプレート
design:css:show|apply CSS
design:header:show|apply ヘッダー / フッター
file:list|put|remove html/user_data/**
doctor:permissions 3 レーンの期待値と実際の所有者・権限の差分表示
```

実装は `Application::appendConfigPath()` による拡張機構を利用できるか、
`ec-cube2/cli` 本体へ追加するかを含めて検討します。

### 3. 4系と共有する仕様

**コードの共有は行いません。** `ec-cube2/cli` は PHP 5.3+ / Symfony Console 2.8〜5.4 を対象とし、
4系は PHP 8.2 / Symfony 7.4 を対象とするため互換性がなく、ライセンスも異なります
(`ec-cube2/cli` は LGPL-3.0、本体は GPL-2.0 / 商用デュアル)。

共有するのは **仕様(インターフェース契約)** です。

- コマンド名の体系(`<領域>:<対象>:<動詞>`)
- `apply` を冪等な upsert とする原則(`new` / `edit` に分けない)
- 標準入力の受け口(`--body=-`)
- `--dry-run` の差分表示形式
- `--format=json` の出力スキーマ
- 終了コードの意味(0 = 正常 / 1 = 失敗 / 2 = 完了したが手動操作が必要)
- 権限診断の 3 レーン分類と出力形式
- Web サーバーの実行ユーザー名をコードに固定値で持たず、
Web サーバーが生成するファイル(ログ等)の `fileowner()` から実測する方針

これにより、実装が別であっても**同じ手順書・同じデプロイスクリプト・同じ運用**を両系統で共有できます。

## 進め方

1. 4系 EC-CUBE/ec-cube#7072 の Phase 1〜3 を実装し、仕様を確定させる
2. 確定した仕様に沿って 2系へ実装する(本 issue)

4系のほうが制約が多いため(build / cache ディレクトリの分離、DB レコードとテンプレートファイルの対応、
Doctrine のエンティティプロキシ)、先に 4系で仕様を揉んだほうが 2系の設計が単純になります。

2系側で先行して着手できるものとして、以下があります。

- `Application::appendConfigPath()` が 2系本体側から利用できるかの確認
- 上記レーン分類の精査(特に `PLUGIN_REALDIR` と `umask(0)` の扱い)

## 関連情報 (Ref)

- EC-CUBE/ec-cube#7072 [4.4] Web サーバー権限に依存しないコンテンツ管理 — CLI 導線と build/cache 分離の実装設計
- #841 umask を改善する
- https://doc4.ec-cube.net/permission
- https://qiita.com/nanasess/items/19ef094309f50009c742
- https://zenn.dev/nanasess/articles/choice-hosting-services-of-eccube

Contributor guide

No contributing guide indexed for this repository

Research direction

Start with ec-cube2/cli’s Application::appendConfigPath(), prependConfigPath(), config/services.yaml, and AddConsoleCommandPass to verify how commands can be added. Inspect the listed write paths, SC_Helper_FileManager_Ex::sfWriteFile(), and the referenced design page callers, then compare them with issue #7072. The work is ready when the 2系 command scope, permission lanes, and shared interface contract are confirmed.

Written by the indexing model from the issue text.

Assessment

Tech stack
php, symfony
Domain
backend, cli
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Active
Clarity
Mostly clear
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.