AtoM AHG Framework - System Flows¶
Version: 2.8.2 Last Updated: February 2026
0. Heratio Dual-Mode Request Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β HERATIO DUAL-MODE REQUEST FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β ββββββββββββ β
β β Client β β
β β (Browser)β β
β ββββββ¬ββββββ β
β β HTTP Request β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β NGINX β β
β β β β
β β ββββββββββββββββββββββββββββββββ βββββββββββββββββββββββββββββββββββ β β
β β β heratio.conf (if installed) β β Standard AtoM config β β β
β β β β β β β β
β β β /ingest/* β heratio.php β β / β index.php β β β
β β β /admin/ahg-* β heratio.php β β /informationobj β index.php β β β
β β β /display/* β heratio.php β β /actor β index.php β β β
β β β /privacy/* β heratio.php β β /repository β index.php β β β
β β β /research/* β heratio.php β β /user β index.php β β β
β β β (~40 plugin patterns) β β (all base AtoM) β β β
β β ββββββββββββββββ¬ββββββββββββββββ ββββββββββββββββ¬βββββββββββββββββββ β β
β ββββββββββββββββββββΌβββββββββββββββββββββββββββββββββββΌββββββββββββββββββββββ β
β β β β
β βββββββββββββββ ββββββββββββββββ β
β βΌ βΌ β
β ββββββββββββββββββββββββββ ββββββββββββββββββββββββββββββ β
β β HERATIO ENTRY POINT β β SYMFONY ENTRY POINT β β
β β heratio.php β β index.php β β
β β β β β β
β β 1. Check kill-switch β β sfContext::getInstance() β β
β β 2. Boot Kernel β β dispatch() β β
β β 3. Middleware stack β β (unchanged AtoM) β β
β β 4. Route dispatch β β β β
β βββββββββββββ¬βββββββββββββ ββββββββββββββββ¬ββββββββββββββ β
β β β β
β βΌ βΌ β
β ββββββββββββββββββββββββββ ββββββββββββββββββββββββββββββ β
β β HERATIO MIDDLEWARE β β SYMFONY FILTER CHAIN β β
β β β β β β
β β 1. SessionMiddleware β β securityFilter β β
β β 2. AuthMiddleware β β accessFilter β β
β β 3. SettingsMiddleware β β cacheFilter β β
β β 4. CspMiddleware β β executionFilter β β
β β 5. MetaMiddleware β β β β
β β 6. LimitsMiddleware β β β β
β βββββββββββββ¬βββββββββββββ ββββββββββββββββ¬ββββββββββββββ β
β β β β
β βΌ βΌ β
β ββββββββββββββββββββββββββ ββββββββββββββββββββββββββββββ β
β β ACTION BRIDGE β β SYMFONY ACTION β β
β β β β β β
β β Dispatches to one of: β β sfAction->execute() β β
β β β’ AhgController β β Propel ORM β β
β β β’ AhgActions (Blade) β β sfView rendering β β
β β β’ sfActions (Bridge) β β β β
β βββββββββββββ¬βββββββββββββ ββββββββββββββββ¬ββββββββββββββ β
β β β β
β βΌ βΌ β
β ββββββββββββββββββββββββββ ββββββββββββββββββββββββββββββ β
β β RENDERING β β RENDERING β β
β β β β β β
β β BladeRenderer β β sfPHPView β β
β β heratio.blade.php β β layout.php β β
β β (master layout) β β (theme layout) β β
β β + 8 partials β β β β
β βββββββββββββ¬βββββββββββββ ββββββββββββββββ¬ββββββββββββββ β
β β β β
β ββββββββββββββββββββββ¬ββββββββββββββββββββββββββββ β
β βΌ β
β βββββββββββββββ β
β β Client β β HTML Response β
β βββββββββββββββ β
β β
β KILL-SWITCH: Remove .heratio_enabled file β ALL routes go to index.php β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
1. Request Processing Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β HTTP REQUEST FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β ββββββββββββ β
β β Client β β
β β (Browser)β β
β ββββββ¬ββββββ β
β β HTTP Request β
β β GET /informationobject/browse β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β NGINX β β
β β β β
β β location / { fastcgi_pass php-fpm; } β β
β β location /plugins/ { alias /path/to/plugins/; } β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β PHP-FPM 8.3 β β
β β β β
β β index.php β sfContext::getInstance() β dispatch() β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β SYMFONY 1.x FRONT CONTROLLER β β
β β β β
β β 1. Load config/ProjectConfiguration.class.php β β
β β 2. Call setup() β loadPluginsFromDatabase() β β
β β 3. Bootstrap atom-framework β β
β β 4. Query atom_plugin for enabled plugins β β
β β 5. Enable plugins via $this->enablePlugins() β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β ROUTING β β
β β β β
β β apps/qubit/config/routing.yml β β
β β + plugin routing.yml files β β
β β β β
β β /informationobject/browse β informationobject/browseAction β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β FILTER CHAIN β β
β β β β
β β βββββββββββββββββββ β β
β β β securityFilter β βββ ahgSecurityClearancePlugin β β
β β β (check access) β Verifies user clearance vs record class β β
β β ββββββββββ¬βββββββββ β β
β β βΌ β β
β β βββββββββββββββββββ β β
β β β accessFilter β βββ Core AtoM ACL β β
β β β (check ACL) β Verifies group permissions β β
β β ββββββββββ¬βββββββββ β β
β β βΌ β β
β β βββββββββββββββββββ β β
β β β cacheFilter β β β
β β ββββββββββ¬βββββββββ β β
β β βΌ β β
β β βββββββββββββββββββ β β
β β β executionFilter β βββ Runs the action β β
β β βββββββββββββββββββ β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β ACTION EXECUTION β β
β β β β
β β plugins/ahgDisplayPlugin/modules/informationobject/ β β
β β actions/browseAction.class.php β β
β β β β
β β class browseAction extends sfAction { β β
β β public function execute($request) { β β
β β // Query via Propel (core AtoM) β β
β β $records = QubitInformationObject::getAll(); β β
β β β β
β β // Query via Laravel (extension data) β β
β β $conditions = DB::table('condition_assessment') β β
β β ->whereIn('object_id', $ids)->get(); β β
β β β β
β β // Trigger hooks for panels β β
β β $panels = AhgHooks::trigger('browse.panels'); β β
β β } β β
β β } β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β TEMPLATE RENDERING β β
β β β β
β β Layout: plugins/ahgThemeB5Plugin/templates/layout.php β β
β β Template: plugins/ahgDisplayPlugin/modules/.../browseSuccess.php β β
β β β β
β β Template includes: β β
β β β’ Sector-specific labels via AhgSectorProfile::getLabel() β β
β β β’ Registered panels via AhgPanels::forPosition() β β
β β β’ Capability checks via AhgCapabilities::has() β β
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β ββββββββββββ β
β β Client β βββ HTML Response β
β ββββββββββββ β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
2. Plugin Installation Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β PLUGIN INSTALLATION FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β $ php bin/atom extension:install ahgPrivacyPlugin β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 1. ExtensionManager::install() β β
β β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β β
β β β Check if plugin exists locally β β β
β β β β β β
β β β if (!file_exists($pluginsPath/$name)) { β β β
β β β // Fetch from GitHub via PluginFetcher β β β
β β β $fetcher->clone($repoUrl, $pluginsPath); β β β
β β β } β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 2. Read extension.json β β
β β β β
β β { β β
β β "name": "ahgPrivacyPlugin", β β
β β "version": "1.2.0", β β
β β "category": "compliance", β β
β β "dependencies": ["ahgCorePlugin"], β β
β β "database": { β β
β β "install": "database/install.sql", β β
β β "migrations": "database/migrations/" β β
β β } β β
β β } β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 3. Check dependencies β β
β β β β
β β foreach ($dependencies as $dep) { β β
β β if (!$this->isEnabled($dep)) { β β
β β $this->enable($dep); // Enable dependency first β β
β β } β β
β β } β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 4. Run database migrations β β
β β β β
β β MigrationHandler::runInstall($plugin) β β
β β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β β
β β β // Execute database/install.sql β β β
β β β CREATE TABLE privacy_breach (...); β β β
β β β CREATE TABLE privacy_consent (...); β β β
β β β CREATE TABLE privacy_sar_request (...); β β β
β β β β β β
β β β // Run migrations in order β β β
β β β 001_initial.sql β β β
β β β 002_add_breach_columns.sql β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 5. Create symlink (if not exists) β β
β β β β
β β ln -s /path/to/atom-ahg-plugins/ahgPrivacyPlugin β β
β β /path/to/atom/plugins/ahgPrivacyPlugin β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 6. Register in atom_plugin table β β
β β β β
β β INSERT INTO atom_plugin ( β β
β β name, class_name, version, category, β β
β β is_enabled, is_core, is_locked, load_order β β
β β ) VALUES ( β β
β β 'ahgPrivacyPlugin', 'ahgPrivacyPluginConfiguration', β β
β β '1.2.0', 'compliance', 1, 0, 0, 50 β β
β β ); β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 7. Clear Symfony cache β β
β β β β
β β rm -rf cache/* β β
β β php symfony cc β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β β Plugin ahgPrivacyPlugin installed and enabled β β
β β β β
β β Restart PHP-FPM for changes to take effect: β β
β β $ sudo systemctl restart php8.3-fpm β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
3. Audit Trail Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β AUDIT TRAIL FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β User Action: Edit record β β
β β POST /informationobject/edit/123 β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β Action: editAction.class.php β β
β β β β
β β // Get original values β β
β β $original = $record->toArray(); β β
β β β β
β β // Apply changes β β
β β $record->title = $request->getParameter('title'); β β
β β $record->save(); β β
β β β β
β β // Calculate diff β β
β β $changes = array_diff_assoc($record->toArray(), $original); β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β AhgHooks::trigger('record.updated', $record, $changes) β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β ahgAuditTrailPlugin listener β β
β β β β
β β AhgHooks::register('record.updated', function($record, $changes) { β β
β β β β
β β // Create audit log entry β β
β β DB::table('audit_log')->insert([ β β
β β 'user_id' => sfContext::getInstance()->getUser()->getId(), β β
β β 'object_id' => $record->id, β β
β β 'object_type' => get_class($record), β β
β β 'action' => 'update', β β
β β 'module' => 'informationobject', β β
β β 'changes' => json_encode($changes), β β
β β 'ip_address' => $_SERVER['REMOTE_ADDR'], β β
β β 'user_agent' => $_SERVER['HTTP_USER_AGENT'], β β
β β 'created_at' => date('Y-m-d H:i:s'), β β
β β ]); β β
β β β β
β β // Create detail records for each changed field β β
β β foreach ($changes as $field => $value) { β β
β β DB::table('audit_log_detail')->insert([...]); β β
β β } β β
β β }); β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β Database State β β
β β β β
β β audit_log β β
β β ββββββ¬ββββββββββ¬ββββββββββββ¬βββββββββ¬βββββββββββββββββββββββββββββ β β
β β β id β user_id β object_id β action β changes β β β
β β ββββββΌββββββββββΌββββββββββββΌβββββββββΌβββββββββββββββββββββββββββββ€ β β
β β β 42 β 5 β 123 β update β {"title":{"old":"... β β β
β β ββββββ΄ββββββββββ΄ββββββββββββ΄βββββββββ΄βββββββββββββββββββββββββββββ β β
β β β β
β β audit_log_detail β β
β β ββββββ¬βββββββββββββββ¬βββββββββββββ¬ββββββββββββββββ¬ββββββββββββββ β β
β β β id β audit_log_id β field_name β old_value β new_value β β β
β β ββββββΌβββββββββββββββΌβββββββββββββΌββββββββββββββββΌββββββββββββββ€ β β
β β β 98 β 42 β title β Old Title β New Title β β β
β β ββββββ΄βββββββββββββββ΄βββββββββββββ΄ββββββββββββββββ΄ββββββββββββββ β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
β Audit Log Viewer: Admin β Audit Trail β
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β Filter: [User βΌ] [Action βΌ] [Module βΌ] [Date Range] [Search] β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€ β
β β Time β User β Action β Record β Changes β β
β ββββββββββββββββΌββββββββββββΌβββββββββΌββββββββββββββββββββββΌβββββββββββββββ€ β
β β 10:45:23 β jsmith β UPDATE β Document ABC-123 β title, date β β
β β 10:42:11 β admin β CREATE β Collection XYZ β - β β
β β 10:38:05 β jsmith β VIEW β Photo Album β - β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
4. IIIF Manifest Generation Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β IIIF MANIFEST GENERATION FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β Request: GET /iiif/manifest/123 β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 1. Check cache β β
β β β β
β β $cached = DB::table('iiif_manifest') β β
β β ->where('object_id', 123) β β
β β ->where('updated_at', '>', $record->updated_at) β β
β β ->first(); β β
β β β β
β β if ($cached) return json_decode($cached->manifest_json); β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β Cache miss β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 2. Load record and digital objects β β
β β β β
β β $record = QubitInformationObject::getById(123); β β
β β $digitalObjects = $record->getDigitalObjects(); β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 3. Build IIIF Presentation 3.0 manifest β β
β β β β
β β { β β
β β "@context": "http://iiif.io/api/presentation/3/context.json", β β
β β "id": "https://example.org/iiif/manifest/123", β β
β β "type": "Manifest", β β
β β "label": { "en": ["Record Title"] }, β β
β β "metadata": [ β β
β β { "label": {"en":["Creator"]}, "value": {"en":["John Doe"]} } β β
β β ], β β
β β "items": [ β β
β β { β β
β β "id": "https://example.org/iiif/canvas/123-1", β β
β β "type": "Canvas", β β
β β "width": 4000, β β
β β "height": 3000, β β
β β "items": [...] β β
β β } β β
β β ] β β
β β } β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 4. Add annotations (if available) β β
β β β β
β β // OCR text β β
β β $ocr = DB::table('iiif_ocr_text')->where('object_id', 123)->first(); β β
β β if ($ocr) { β β
β β manifest.annotations = OcrService::generateAnnotationPage(); β β
β β } β β
β β β β
β β // Transcriptions β β
β β $transcription = TranscriptionService::get(123); β β
β β if ($transcription) { β β
β β manifest.supplementing = ... β β
β β } β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 5. Apply access restrictions β β
β β β β
β β if (AhgCapabilities::has('security')) { β β
β β $classification = SecurityService::getClassification(123); β β
β β if ($classification->level > 0) { β β
β β manifest.services = [ β β
β β { "@type": "AuthCookieService1", ... } β β
β β ]; β β
β β } β β
β β } β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 6. Cache and return β β
β β β β
β β DB::table('iiif_manifest')->updateOrInsert( β β
β β ['object_id' => 123], β β
β β ['manifest_json' => json_encode($manifest), ...] β β
β β ); β β
β β β β
β β return Response::json($manifest) β β
β β ->header('Access-Control-Allow-Origin', '*') β β
β β ->header('Content-Type', 'application/ld+json'); β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
β Viewer Integration: β
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β <div id="mirador"> β β
β β <script> β β
β β Mirador.viewer({ β β
β β id: 'mirador', β β
β β windows: [{ β β
β β manifestId: 'https://example.org/iiif/manifest/123' β β
β β }] β β
β β }); β β
β β </script> β β
β β </div> β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
5. AI/NER Processing Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β NER PROCESSING FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β Trigger: User clicks "Extract Entities" or batch job runs β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 1. Collect text content β β
β β β β
β β $text = $record->getScopeAndContent() . β β
β β $record->getArchivalHistory() . β β
β β $record->getTitle(); β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 2. Send to Python NER service β β
β β β β
β β // atom-ahg-python/src/atom_ahg/resources/ner.py β β
β β β β
β β import spacy β β
β β nlp = spacy.load("en_core_web_lg") β β
β β β β
β β doc = nlp(text) β β
β β entities = [] β β
β β for ent in doc.ents: β β
β β entities.append({ β β
β β 'text': ent.text, β β
β β 'type': ent.label_, # PERSON, ORG, GPE, DATE β β
β β 'start': ent.start_char, β β
β β 'end': ent.end_char, β β
β β 'confidence': ent.kb_id_ β β
β β }) β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 3. Process entities β β
β β β β
β β Entities found: β β
β β ββββββββββββββββββββββ¬βββββββββββ¬βββββββββββββββββββββββββββββββββ β β
β β β Text β Type β Action β β β
β β ββββββββββββββββββββββΌβββββββββββΌβββββββββββββββββββββββββββββββββ€ β β
β β β John Smith β PERSON β Link to/create actor record β β β
β β β Acme Corporation β ORG β Link to/create actor record β β β
β β β Cape Town β GPE β Link to place authority β β β
β β β 15 March 1952 β DATE β Parse and validate date β β β
β β ββββββββββββββββββββββ΄βββββββββββ΄βββββββββββββββββββββββββββββββββ β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 4. User review (optional) β β
β β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β β
β β β Entity Suggestions β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€ β β
β β β β John Smith (PERSON) β Create new actor β β β
β β β β Acme Corporation (ORG) β Link to existing: Acme Corp Ltd β β β
β β β β Cape Town (PLACE) β [Reject - already linked] β β β
β β β β 15 March 1952 (DATE) β Add to dates field β β β
β β β β β β
β β β [Apply Selected] [Reject All] β β β
β β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β β
β ββββββββββββββββββββββββββββββββββββββ¬βββββββββββββββββββββββββββββββββββββ β
β β β
β βΌ β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β 5. Apply changes β β
β β β β
β β // Create actor if not exists β β
β β $actor = QubitActor::getByName('John Smith') β β
β β ?? QubitActor::create(['authorized_form_of_name' => 'John Smith']); β β
β β β β
β β // Link to record β β
β β QubitRelation::create([ β β
β β 'subject_id' => $record->id, β β
β β 'object_id' => $actor->id, β β
β β 'type_id' => QubitTerm::NAME_ACCESS_POINT_ID β β
β β ]); β β
β β β β
β β // Log extraction β β
β β DB::table('ner_extraction_log')->insert([...]); β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
6. Ingest Pipeline Flow¶
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β INGEST PIPELINE FLOW β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β STEP 1 STEP 2 STEP 3 STEP 4 STEP 5 β
β CONFIGURE ββββΊ UPLOAD ββββΊ MAP & ENRICH βββΊ VALIDATE ββββΊ PREVIEW β
β (sector, (CSV/ZIP/ (auto-map, (required (tree view, β
β standard, EAD, dir) metadata, fields, approval) β
β options) profiles) checksums) β
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββΊ STEP 6 β
β COMMIT β
β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β COMMIT FLOW (Background Job) β β
β β β β
β β Browser ββPOSTβββΊ Action βββΊ Create ingest_job (status=queued) β β
β β β β β
β β ββββΊ nohup php symfony ingest:commit --job-id=X & β β
β β β β β
β β ββββΊ Return page (AJAX polling starts) β β
β β β β
β β CLI Task βββΊ Mark running βββΊ For each row: β β
β β ββ Create InformationObject β β
β β ββ Create DigitalObject (if DO path) β β
β β ββ Generate derivatives β β
β β ββ Run AI processing (NER/OCR/etc) β β
β β β β
β β βββΊ Build SIP package βββΊ Build AIP βββΊ Build DIP β β
β β βββΊ Update search index β β
β β βββΊ Generate manifest CSV β β
β β βββΊ Mark completed β β
β β β β
β β Browser βββpoll every 2sβββΊ /ingest/ajax/job-status?job_id=X β β
β β βββΊ Show progress bar βββΊ On complete: show report card β β
β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ β
β β
β ROLLBACK: Deletes created IOs + DOs + packages, restores session state β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
Part of the AtoM AHG Framework - v2.8.2