This is a template repository for creating OpenEMR modules using OpenCoreEMR's architectural patterns and best practices.
- Symfony-inspired MVC architecture with Controllers, Services, and Twig templates
- Pre-configured code quality tools (PHPCS, PHPStan, Rector)
- Pre-commit hooks for automated code quality checks
- Comprehensive documentation for AI agents (see
CLAUDE.md) - Modern PHP 8.2+ with strict typing and best practices
- Proper dependency management with Composer
Click "Use this template" on GitHub or clone this repository:
git clone https://github.com/opencoreemr/oce-module-template.git {vendor-prefix}-module-{modulename}
cd {vendor-prefix}-module-{modulename}
rm -rf .git
git initcomposer installThe automated setup wizard will configure your module:
./bin/setupThis interactive wizard will:
- Ask if this is for internal OpenCoreEMR use (oce- prefix) or external/community use (oe- prefix)
- Prompt for your module name
- Ask for vendor name (if external use)
- Replace all placeholders throughout the codebase
- Optionally remove setup files when complete
For OpenCoreEMR Internal Use:
- Namespace:
OpenCoreEMR\Modules\{ModuleName} - Package:
opencoreemr/oce-module-{modulename}
For External/Community Use:
- Namespace:
YourVendor\Modules\{ModuleName}(orOpenEMR\Modules\{ModuleName}) - Package:
yourvendor/oe-module-{modulename}
If you prefer manual setup, edit these files to replace placeholders:
- Replace
{VendorName}with your vendor name (e.g.,OpenCoreEMRorYourOrg) - Replace
{vendor-prefix}withoce(internal) oroe(external) - Replace
{modulename}with your module name (e.g.,lab-integration) - Replace
{ModuleName}with PascalCase version (e.g.,LabIntegration) - Update
description,keywords, andauthors
version.php- Update header commentsphpcs.xml- Update ruleset namesrc/files - Update namespaces.composer-require-checker.json- Update symbol whitelist
pip install pre-commit
pre-commit installFollow the structure outlined in CLAUDE.md:
{vendor-prefix}-module-{modulename}/
├── public/
│ └── index.php # Main entry point
├── src/
│ ├── Bootstrap.php # Module initialization
│ ├── GlobalConfig.php # Configuration management
│ ├── Controller/ # Request handlers
│ ├── Service/ # Business logic
│ └── Exception/ # Custom exceptions
├── templates/ # Twig templates
├── table.sql # Database schema (optional)
└── openemr.bootstrap.php # Module loader
CLAUDE.md- Comprehensive architectural patterns and conventions for AI agentsDEVELOPMENT.md- Development workflow and guidelines (update this for your module)
public function dispatch(string $action, array $params): Response
{
return match ($action) {
'create' => $this->handleCreate($params),
'list' => $this->showList($params),
default => $this->showList($params),
};
}<?php
require_once __DIR__ . '/../../../../globals.php';
use {VendorName}\Modules\{ModuleName}\Bootstrap;
$kernel = $GLOBALS['kernel'];
$bootstrap = new Bootstrap($kernel->getEventDispatcher(), $kernel);
$controller = $bootstrap->getYourController();
$action = $_GET['action'] ?? 'default';
$response = $controller->dispatch($action, $_REQUEST);
$response->send();interface {ModuleName}ExceptionInterface extends \Throwable
{
public function getStatusCode(): int;
}
class {ModuleName}NotFoundException extends {ModuleName}Exception
{
public function getStatusCode(): int
{
return 404;
}
}All code must pass these checks before committing:
pre-commit run -aOr run individual checks:
composer phpcs # Code style
composer phpstan # Static analysis
composer rector # PHP compatibilityNote: The composer-require-checker hook will fail on the template until you add actual PHP code to src/ and public/. This is expected behavior for an empty template.
cd /path/to/openemr
composer require {vendorname}/{vendor-prefix}-module-{modulename}- Copy to
interface/modules/custom_modules/{vendor-prefix}-module-{modulename} - Navigate to Administration > Modules > Manage Modules
- Click Register, then Install, then Enable
- Issues: https://github.com/{vendorname}/{vendor-prefix}-module-{modulename}/issues
- Email: support@opencoreemr.com
GNU General Public License v3.0 or later
Developed by OpenCoreEMR Inc