🔍 Code Extractor

function migrate_review_assignments

Maturity: 60

Migrates legacy review data from direct REVIEWED_BY relationships to a new ReviewerAssignment node model in a Neo4j graph database.

File:
/tf/active/vicechatdev/CDocs single class/db/schema_manager.py
Lines:
274 - 343
Complexity:
moderate

Purpose

This function performs a one-time data migration to transform an older review system structure where ReviewCycle nodes had direct REVIEWED_BY relationships to User nodes, into a new model using intermediate ReviewerAssignment nodes. This allows for more flexible reviewer management with additional metadata like status, role, sequence order, and timestamps. The migration is idempotent and only processes reviews that haven't been migrated yet.

Source Code

def migrate_review_assignments(driver: Driver) -> Dict[str, Any]:
    """
    Migrate review data to the new reviewer assignment model.
    
    Args:
        driver: Neo4j driver instance
        
    Returns:
        Dict containing migration results
    """
    try:
        with driver.session() as session:
            # Check for reviews with direct reviewer relationships that need migration
            result = session.run(
                """
                MATCH (r:ReviewCycle)-[:REVIEWED_BY]->(u:User)
                WHERE NOT EXISTS((r)-[:HAS_REVIEWER]->(:ReviewerAssignment))
                RETURN count(r) as count
                """
            )
            record = result.single()
            
            if not record or record["count"] == 0:
                return {
                    "success": True,
                    "message": "No reviews need migration",
                    "migrated_count": 0
                }
            
            # Perform migration for each old review
            migration_query = """
            MATCH (r:ReviewCycle)-[rel:REVIEWED_BY]->(u:User)
            WHERE NOT EXISTS((r)-[:HAS_REVIEWER]->(:ReviewerAssignment))
            WITH r, u, rel
            
            // Create a reviewer assignment for each direct reviewer
            CREATE (ra:ReviewerAssignment {
                UID: apoc.create.uuid(),
                reviewer_uid: u.UID,
                user_uid: u.UID,
                reviewer_name: u.Name,
                user_name: u.Name,
                status: 'PENDING',
                role: 'Reviewer',
                assigned_at: datetime(),
                sequence_order: 0,
                review_cycle_uid: r.UID
            })
            CREATE (r)-[:HAS_REVIEWER]->(ra)
            
            RETURN count(ra) as migrated
            """
            
            result = session.run(migration_query)
            record = result.single()
            
            return {
                "success": True,
                "message": f"Successfully migrated {record['migrated']} reviewer assignments",
                "migrated_count": record["migrated"]
            }
            
    except Exception as e:
        logger.error(f"Error migrating reviewer assignments: {e}")
        logger.error(traceback.format_exc())
        return {
            "success": False,
            "message": f"Error: {str(e)}",
            "migrated_count": 0
        }

Parameters

Name Type Default Kind
driver Driver - positional_or_keyword

Parameter Details

driver: A Neo4j Driver instance used to establish database connections and execute Cypher queries. Must be a valid, connected Neo4j driver object that has access to the database containing ReviewCycle and User nodes.

Return Value

Type: Dict[str, Any]

Returns a dictionary with three keys: 'success' (boolean indicating if migration completed without errors), 'message' (string describing the outcome), and 'migrated_count' (integer representing the number of reviewer assignments created). On success with no data to migrate, migrated_count is 0. On error, success is False and message contains the error description.

Dependencies

  • neo4j
  • CDocs
  • logging
  • uuid
  • traceback
  • typing
  • datetime

Required Imports

from neo4j import Driver
from typing import Dict, Any
import logging
import traceback
from CDocs import guard_execution

Usage Example

from neo4j import GraphDatabase
from typing import Dict, Any
import logging

# Setup logger
logger = logging.getLogger(__name__)

# Create Neo4j driver
driver = GraphDatabase.driver(
    'bolt://localhost:7687',
    auth=('neo4j', 'password')
)

try:
    # Run migration
    result = migrate_review_assignments(driver)
    
    if result['success']:
        print(f"Migration successful: {result['message']}")
        print(f"Migrated {result['migrated_count']} assignments")
    else:
        print(f"Migration failed: {result['message']}")
finally:
    driver.close()

Best Practices

  • Ensure Neo4j APOC plugin is installed before running this migration as it uses apoc.create.uuid()
  • The function is decorated with guard_execution(cooldown_ms=5000) which prevents rapid repeated executions - respect this cooldown period
  • The migration is idempotent - it checks for existing ReviewerAssignment nodes before migrating, so it's safe to run multiple times
  • Always check the 'success' field in the returned dictionary before assuming migration completed successfully
  • Monitor the 'migrated_count' to verify expected number of assignments were created
  • The function does not delete old REVIEWED_BY relationships - consider cleanup in a separate operation if needed
  • Ensure adequate database transaction timeout settings for large datasets as this creates nodes in a single transaction
  • Review logs after migration as errors are logged with full stack traces for debugging
  • Test on a backup or development database before running in production
  • The function creates ReviewerAssignment nodes with default status='PENDING' and sequence_order=0 - adjust if different defaults are needed

Similar Components

AI-powered semantic similarity - components with related functionality:

  • function update_review_comment_relationships 78.3% similar

    Migrates Neo4j ReviewComment nodes to use explicit parent/child relationships (PARENT_COMMENT and HAS_REPLY) based on existing parent_comment_uid properties.

    From: /tf/active/vicechatdev/CDocs single class/db/schema_manager.py
  • function migrate_approval_cycles 73.5% similar

    Migrates legacy Approval nodes and their related structures to the new ApprovalCycle model in a Neo4j graph database, creating ApprovalCycle nodes and ApproverAssignment nodes while maintaining relationships with DocumentVersion nodes.

    From: /tf/active/vicechatdev/CDocs/db/schema_manager.py
  • function migrate_approval_data 71.4% similar

    Migrates legacy single-step approval records in Neo4j to a new multi-step approval model by creating ApprovalStep nodes and Approver nodes with proper relationships.

    From: /tf/active/vicechatdev/CDocs/db/schema_manager.py
  • function migrate_approval_data_v1 70.5% similar

    Migrates legacy single-step approval records in Neo4j to a new multi-step approval model by creating ApprovalStep nodes and Approver nodes with proper relationships.

    From: /tf/active/vicechatdev/CDocs single class/db/schema_manager.py
  • class ReviewerAssignment 62.3% similar

    Model class representing a reviewer assignment within a review cycle, managing reviewer information, status, decisions, and lifecycle of review assignments.

    From: /tf/active/vicechatdev/CDocs single class/models/review.py
← Back to Browse