From 880cfbf1ba7d53ea203901bb7e90acfe131b7220 Mon Sep 17 00:00:00 2001 From: Mark Hanna Date: Thu, 30 Apr 2026 08:17:53 -0600 Subject: [PATCH 1/3] add 12 to info files --- civicrm.info.yml | 2 +- modules/civicrmtheme/civicrmtheme.info.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/civicrm.info.yml b/civicrm.info.yml index a5e1eb8..1f92368 100644 --- a/civicrm.info.yml +++ b/civicrm.info.yml @@ -2,4 +2,4 @@ name: CiviCRM Core type: module description: 'Constituent Relationship Management system. Allows sites to manage contacts, relationships and groups, and track contact activities, contributions, memberships and events.' package: CiviCRM -core_version_requirement: ^9 || ^10 || ^11 +core_version_requirement: ^9 || ^10 || ^11 || ^12 diff --git a/modules/civicrmtheme/civicrmtheme.info.yml b/modules/civicrmtheme/civicrmtheme.info.yml index a877165..a208884 100644 --- a/modules/civicrmtheme/civicrmtheme.info.yml +++ b/modules/civicrmtheme/civicrmtheme.info.yml @@ -2,6 +2,6 @@ name: CiviCRM Theme type: module description: 'Define alternate themes for CiviCRM.' package: CiviCRM -core_version_requirement: ^9 || ^10 || ^11 +core_version_requirement: ^9 || ^10 || ^11 || ^12 dependencies: - civicrm From 1874094c030580013c10fa20a13f841a6d13debf Mon Sep 17 00:00:00 2001 From: Mark Hanna Date: Fri, 1 May 2026 09:55:24 -0600 Subject: [PATCH 2/3] prototype moving install and runtime requirements to object oriented location for Drupal 12 --- civicrm.install | 75 -------------- src/Hook/CivicrmRequirementsHook.php | 98 +++++++++++++++++++ .../CivicrmInstallRequirements.php | 93 ++++++++++++++++++ 3 files changed, 191 insertions(+), 75 deletions(-) create mode 100644 src/Hook/CivicrmRequirementsHook.php create mode 100644 src/Install/Requirements/CivicrmInstallRequirements.php diff --git a/civicrm.install b/civicrm.install index d8c8167..45701db 100644 --- a/civicrm.install +++ b/civicrm.install @@ -43,81 +43,6 @@ function civicrm_uninstall() { $setup->uninstallDatabase(); } -/** - * Implements hook_requirements(). - */ -function civicrm_requirements($phase) { - $requirements = []; - - $civicrm_base = _civicrm_find_civicrm(); - - // Introduced in 11.2, and then compatibility layer removed in 11.3, so we - // have to support both. - if (class_exists('\Drupal\Core\Extension\Requirement\RequirementSeverity')) { - $severityMap = [ - 'info' => \Drupal\Core\Extension\Requirement\RequirementSeverity::OK, - 'warning' => \Drupal\Core\Extension\Requirement\RequirementSeverity::Warning, - 'error' => \Drupal\Core\Extension\Requirement\RequirementSeverity::Error, - ]; - } - else { - $severityMap = [ - 'info' => REQUIREMENT_OK, - 'warning' => REQUIREMENT_WARNING, - 'error' => REQUIREMENT_ERROR, - ]; - } - - if ($civicrm_base) { - $requirements['civicrm.location'] = [ - 'title' => 'CiviCRM location', - 'severity' => $severityMap['info'], - 'description' => 'CiviCRM core directory', - ]; - } - else { - $requirements['civicrm.location'] = [ - 'title' => 'CiviCRM location', - 'severity' => $severityMap['error'], - 'description' => 'CiviCRM must be installed via composer.', - ]; - return $requirements; - } - - /** @var \Civi\Setup $setup */ - $setup = _civicrm_setup(); - if ($phase === 'install' && !$setup->checkAuthorized()->isAuthorized()) { - $requirements['civicrm.checkAuthorized'] = [ - 'title' => 'CiviCRM Installation Not Authorized', - 'description' => 'The current user does not have sufficient permissions to perform installation.', - 'severity' => $severityMap['warning'], - ]; - return $requirements; - } - - $sections = [ - 'system' => 'CiviCRM: System', - 'database' => 'CiviCRM: Database', - 'other' => 'CiviCRM: Other', - ]; - - if ($phase !== 'runtime') { - foreach ($setup->checkRequirements()->getMessages() as $msg) { - $section = isset($sections[$msg['section']]) ? $sections[$msg['section']] : $sections['other']; - $key = 'civicrm.' . $msg['section'] . '.' . $msg['name']; - $requirements[$key] = [ - 'title' => $section . ': ' . $msg['message'], - 'description' => $section . ': ' . $msg['message'], - 'severity' => $severityMap[$msg['severity']], - ]; - } - } - - ksort($requirements); - - return $requirements; -} - /** * @return \Civi\Setup */ diff --git a/src/Hook/CivicrmRequirementsHook.php b/src/Hook/CivicrmRequirementsHook.php new file mode 100644 index 0000000..6ab7e02 --- /dev/null +++ b/src/Hook/CivicrmRequirementsHook.php @@ -0,0 +1,98 @@ +getPath('civicrm')) { + $possible_paths[] = $path; + } + $possible_paths[] = 'vendor/civicrm/civicrm-core'; + $possible_paths[] = '../vendor/civicrm/civicrm-core'; + + foreach ($possible_paths as $path) { + if (file_exists($path . '/CRM/Core/ClassLoader.php')) { + $civicrm_base = \Drupal::service('file_system')->realpath($path); + break; + } + } + + $severityMap = [ + 'info' => RequirementSeverity::OK, + 'warning' => RequirementSeverity::Warning, + 'error' => RequirementSeverity::Error, + ]; + + if ($civicrm_base) { + $requirements['civicrm.location'] = [ + 'title' => 'CiviCRM location', + 'severity' => $severityMap['info'], + 'description' => 'CiviCRM core directory', + ]; + } + else { + $requirements['civicrm.location'] = [ + 'title' => 'CiviCRM location', + 'severity' => $severityMap['error'], + 'description' => 'CiviCRM must be installed via composer.', + ]; + return $requirements; + } + + // Modification of _civicrm_setup() + // Move to a service? + if (defined('CIVI_SETUP')) { + /** @var \Civi\Setup $setup */ + $setup = \Civi\Setup::instance(); + } + else { + if ($civicrm_base) { + require_once $civicrm_base . '/CRM/Core/ClassLoader.php'; + \CRM_Core_ClassLoader::singleton()->register(); + + \Civi\Setup::assertProtocolCompatibility(1.0); + \Civi\Setup::init([ + 'cms' => 'Drupal8', + 'srcPath' => $civicrm_base, + ]); + /** @var \Civi\Setup $setup */ + $setup = \Civi\Setup::instance(); + } + } + + $sections = [ + 'system' => 'CiviCRM: System', + 'database' => 'CiviCRM: Database', + 'other' => 'CiviCRM: Other', + ]; + + foreach ($setup->checkRequirements()->getMessages() as $msg) { + $section = isset($sections[$msg['section']]) ? $sections[$msg['section']] : $sections['other']; + $key = 'civicrm.' . $msg['section'] . '.' . $msg['name']; + $requirements[$key] = [ + 'title' => $section . ': ' . $msg['message'], + 'description' => $section . ': ' . $msg['message'], + 'severity' => $severityMap[$msg['severity']], + ]; + } + + ksort($requirements); + return $requirements; + } +} diff --git a/src/Install/Requirements/CivicrmInstallRequirements.php b/src/Install/Requirements/CivicrmInstallRequirements.php new file mode 100644 index 0000000..efe85d7 --- /dev/null +++ b/src/Install/Requirements/CivicrmInstallRequirements.php @@ -0,0 +1,93 @@ +getPath('civicrm')) { + $possible_paths[] = $path; + } + $possible_paths[] = 'vendor/civicrm/civicrm-core'; + $possible_paths[] = '../vendor/civicrm/civicrm-core'; + + foreach ($possible_paths as $path) { + if (file_exists($path . '/CRM/Core/ClassLoader.php')) { + $civicrm_base = \Drupal::service('file_system')->realpath($path); + break; + } + } + + // Introduced in 11.2, and then compatibility layer removed in 11.3, so we + // have to support both. + $severityMap = [ + 'info' => RequirementSeverity::OK, + 'warning' => RequirementSeverity::Warning, + 'error' => RequirementSeverity::Error, + ]; + + if ($civicrm_base) { + $requirements['civicrm.location'] = [ + 'title' => 'CiviCRM location', + 'severity' => $severityMap['info'], + 'description' => 'CiviCRM core directory', + ]; + } + else { + $requirements['civicrm.location'] = [ + 'title' => 'CiviCRM location', + 'severity' => $severityMap['error'], + 'description' => 'CiviCRM must be installed via composer.', + ]; + return $requirements; + } + + // Modification of _civicrm_setup() + // Move to a service? + if (defined('CIVI_SETUP')) { + /** @var \Civi\Setup $setup */ + $setup = \Civi\Setup::instance(); + } + else { + if ($civicrm_base) { + require_once $civicrm_base . '/CRM/Core/ClassLoader.php'; + \CRM_Core_ClassLoader::singleton()->register(); + + \Civi\Setup::assertProtocolCompatibility(1.0); + \Civi\Setup::init([ + 'cms' => 'Drupal8', + 'srcPath' => $civicrm_base, + ]); + /** @var \Civi\Setup $setup */ + $setup = \Civi\Setup::instance(); + } + } + + if (!$setup->checkAuthorized()->isAuthorized()) { + $requirements['civicrm.checkAuthorized'] = [ + 'title' => 'CiviCRM Installation Not Authorized', + 'description' => 'The current user does not have sufficient permissions to perform installation.', + 'severity' => $severityMap['warning'], + ]; + return $requirements; + } + + ksort($requirements); + + return $requirements; + } + +} From 9b2a7ed567d0a626669b7f57d7666f2cbf3b914b Mon Sep 17 00:00:00 2001 From: Mark Hanna Date: Mon, 11 May 2026 16:45:41 -0600 Subject: [PATCH 3/3] loop through requirements in installation requirements plugin --- .../CivicrmInstallRequirements.php | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/src/Install/Requirements/CivicrmInstallRequirements.php b/src/Install/Requirements/CivicrmInstallRequirements.php index efe85d7..284f24b 100644 --- a/src/Install/Requirements/CivicrmInstallRequirements.php +++ b/src/Install/Requirements/CivicrmInstallRequirements.php @@ -85,6 +85,24 @@ public static function getRequirements(): array { return $requirements; } + $sections = [ + 'system' => 'CiviCRM: System', + 'database' => 'CiviCRM: Database', + 'other' => 'CiviCRM: Other', + ]; + + + foreach ($setup->checkRequirements()->getMessages() as $msg) { + $section = isset($sections[$msg['section']]) ? $sections[$msg['section']] : $sections['other']; + $key = 'civicrm.' . $msg['section'] . '.' . $msg['name']; + $requirements[$key] = [ + 'title' => $section . ': ' . $msg['message'], + 'description' => $section . ': ' . $msg['message'], + 'severity' => $severityMap[$msg['severity']], + ]; + } + + ksort($requirements); return $requirements;