7 dokumentów w .paul/codebase/ — overview, stack, architecture, conventions, testing, integrations, concerns (CRITICAL→LOW). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
5.0 KiB
5.0 KiB
Coding Conventions
Generated: 2026-04-26
File Naming
| Layer | Convention | Example |
|---|---|---|
| Legacy (admin/front) | class.{ClassName}.php |
class.Articles.php |
| Domain repositories | {ClassName}.php (PSR-4) |
ArticlesRepository.php |
| Shared services | {ClassName}.php (PSR-4) |
CacheHandler.php |
| Templates | {feature-name}.php |
articles/list.php |
Naming Conventions
| Element | Legacy code | New Domain code |
|---|---|---|
| Methods | snake_case |
camelCase |
| Classes | PascalCase |
PascalCase |
| Properties | $camelCase |
$camelCase |
| Constants | UPPER_CASE |
UPPER_CASE |
| Namespaces | lowercase (admin\, front\) |
PascalCase (Domain\, Shared\) |
Class Patterns
Controls (request handlers) — static methods only
namespace admin\controls;
class Articles {
public static function article_delete() {
global $user;
if (!admin\factory\Users::check_privileges('articles', $user['id']))
return \S::alert('Brak uprawnień');
admin\factory\Articles::article_delete(\S::get('article_id'));
}
}
Factories — @deprecated wrappers, static methods, delegate to repo
namespace admin\factory;
/** @deprecated Wrapper — używaj \Domain\Articles\ArticlesRepository przez DI */
class Articles {
private static function repo(): \Domain\Articles\ArticlesRepository {
global $mdb;
return new \Domain\Articles\ArticlesRepository($mdb);
}
public static function article_delete($id): bool {
return self::repo()->deleteArticle((int)$id);
}
}
Domain Repositories — constructor DI, camelCase, typed returns
namespace Domain\Articles;
class ArticlesRepository {
private $db;
public function __construct($db) { $this->db = $db; }
// -------------------------------------------------------------------------
// Odczyt (Read)
// -------------------------------------------------------------------------
public function find(int $id): ?array {
return $this->db->get('pp_articles', '*', ['id' => $id]) ?: null;
}
// -------------------------------------------------------------------------
// Zapis / usuwanie (Write / Delete)
// -------------------------------------------------------------------------
public function deleteArticle(int $id): bool {
$this->db->delete('pp_articles', ['id' => $id]);
return true;
}
}
View classes — static rendering
namespace admin\view;
class Articles {
public static function list($articles) {
$tpl = new \Tpl;
$tpl->articles = $articles;
return $tpl->render('articles/list');
}
}
PHPDoc Style
Polish-language descriptions are standard in this project:
/**
* Prosta lista autorów
* @return array|bool
*/
public function authorsList() { ... }
/**
* Zapis autora (insert lub update)
* @param int $authorId
* @param string $author
* @return object|bool
*/
public function authorSave(int $authorId, string $author) { ... }
Section separators in larger classes:
// -------------------------------------------------------------------------
// Odczyt (Read operations)
// -------------------------------------------------------------------------
Return Patterns
| Pattern | Usage |
|---|---|
?array |
Single record lookup (null = not found) |
array (possibly []) |
List queries — ?: [] fallback |
bool |
Write/delete operations |
int |
Codes: 1 = OK, 0 = bad credentials, -1 = blocked |
void |
Side-effect-only writes |
['status' => 'ok'/'error', 'msg' => '...'] |
AJAX JSON responses |
Error Handling
- Repositories return
null/false/[]for "not found", don't throw ImageManipulatoruses typed exceptions (\InvalidArgumentException,\RuntimeException)- AJAX endpoints:
json_encode(['status' => 'ok/error', 'msg' => '...']) - Error suppression with
@is used in legacy code (avoid in new code)
Database Access via Medoo
Always use parameterized Medoo methods — never string concatenation with string values:
// Good
$this->db->get('pp_articles', '*', ['id' => $id]);
$this->db->select('pp_articles', '*', ['ORDER' => ['created' => 'DESC']]);
$this->db->update('pp_articles', ['status' => 1], ['id' => $id]);
$this->db->insert('pp_articles', ['title' => $title, 'slug' => $slug]);
// Acceptable (integer cast only)
$this->db->query("SELECT ... WHERE id = " . (int)$id)->fetchAll();
// Never
$this->db->query("SELECT ... WHERE slug = '" . $slug . "'"); // SQL injection risk
Global Helper Facade (\S::)
Legacy code uses \S::method() — new code should use \Shared\Helpers\Helpers::method() directly or inject the dependency. Migrate \S:: calls opportunistically but don't block on it.
Template Rendering
$tpl = new \Tpl; // or: new \Shared\Tpl\Tpl
$tpl->variable = $value; // assign template variables
return $tpl->render('module/template-name'); // checks templates_user/ first, then templates/