mirror of https://github.com/jumpserver/jumpserver
				
				
				
			
		
			
				
	
	
		
			172 lines
		
	
	
		
			5.5 KiB
		
	
	
	
		
			Python
		
	
	
			
		
		
	
	
			172 lines
		
	
	
		
			5.5 KiB
		
	
	
	
		
			Python
		
	
	
# Generated by Django 3.1.14 on 2022-04-26 07:58
 | 
						|
import uuid
 | 
						|
 | 
						|
from django.db import migrations
 | 
						|
 | 
						|
failed_apps = []
 | 
						|
 | 
						|
 | 
						|
def get_prop_name_id(apps, app, category):
 | 
						|
    asset_model = apps.get_model('assets', 'Asset')
 | 
						|
    _id = app.id
 | 
						|
    id_exists = asset_model.objects.filter(id=_id).exists()
 | 
						|
    if id_exists:
 | 
						|
        _id = uuid.uuid4()
 | 
						|
    name = app.name
 | 
						|
    name_exists = asset_model.objects.filter(name=name).exists()
 | 
						|
    if name_exists:
 | 
						|
        name = category + '-' + app.name
 | 
						|
    return _id, name
 | 
						|
 | 
						|
 | 
						|
def migrate_database_to_asset(apps, *args):
 | 
						|
    node_model = apps.get_model('assets', 'Node')
 | 
						|
    app_model = apps.get_model('applications', 'Application')
 | 
						|
    db_model = apps.get_model('assets', 'Database')
 | 
						|
    platform_model = apps.get_model('assets', 'Platform')
 | 
						|
 | 
						|
    applications = app_model.objects.filter(category='db')
 | 
						|
    platforms = platform_model.objects.all().filter(internal=True).exclude(name='Redis6+')
 | 
						|
    platforms_map = {p.type: p for p in platforms}
 | 
						|
    print()
 | 
						|
 | 
						|
    for app in applications:
 | 
						|
        attrs = {'host': '', 'port': 0, 'database': ''}
 | 
						|
        _attrs = app.attrs or {}
 | 
						|
        attrs.update(_attrs)
 | 
						|
 | 
						|
        name = 'DB-{}'.format(app.name)
 | 
						|
        db = db_model(
 | 
						|
            id=app.id, name=name, address=attrs['host'],
 | 
						|
            protocols='{}/{}'.format(app.type, attrs['port']),
 | 
						|
            db_name=attrs['database'] or '',
 | 
						|
            platform=platforms_map[app.type],
 | 
						|
            org_id=app.org_id
 | 
						|
        )
 | 
						|
        try:
 | 
						|
            print("\t- Create database: ", app.name)
 | 
						|
            db.save()
 | 
						|
        except:
 | 
						|
            failed_apps.append(app)
 | 
						|
            pass
 | 
						|
 | 
						|
 | 
						|
def migrate_cloud_to_asset(apps, *args):
 | 
						|
    app_model = apps.get_model('applications', 'Application')
 | 
						|
    cloud_model = apps.get_model('assets', 'Cloud')
 | 
						|
    platform_model = apps.get_model('assets', 'Platform')
 | 
						|
 | 
						|
    applications = app_model.objects.filter(category='cloud')
 | 
						|
    platform = platform_model.objects.filter(type='k8s').first()
 | 
						|
    print()
 | 
						|
 | 
						|
    for app in applications:
 | 
						|
        attrs = app.attrs
 | 
						|
        print("\t- Create cloud: {}".format(app.name))
 | 
						|
        name = 'Cloud-{}'.format(app.name)
 | 
						|
        cloud = cloud_model(
 | 
						|
            id=app.id, name=name,
 | 
						|
            address=attrs.get('cluster', ''),
 | 
						|
            protocols='k8s/443', platform=platform,
 | 
						|
            org_id=app.org_id,
 | 
						|
        )
 | 
						|
 | 
						|
        try:
 | 
						|
            cloud.save()
 | 
						|
        except Exception as e:
 | 
						|
            failed_apps.append(cloud)
 | 
						|
            print("Error: ", e)
 | 
						|
 | 
						|
 | 
						|
def create_app_nodes(apps, org_id):
 | 
						|
    node_model = apps.get_model('assets', 'Node')
 | 
						|
 | 
						|
    child_pattern = r'^[0-9]+:[0-9]+$'
 | 
						|
    node_keys = node_model.objects.filter(org_id=org_id) \
 | 
						|
        .filter(key__regex=child_pattern) \
 | 
						|
        .values_list('key', flat=True)
 | 
						|
    if node_keys:
 | 
						|
        node_key_split = [key.split(':') for key in node_keys]
 | 
						|
        next_value = max([int(k[1]) for k in node_key_split]) + 1
 | 
						|
        parent_key = node_key_split[0][0]
 | 
						|
    else:
 | 
						|
        root_node = node_model.objects.filter(org_id=org_id) \
 | 
						|
            .filter(parent_key='', key__regex=r'^[0-9]+$') \
 | 
						|
            .exclude(key__startswith='-') \
 | 
						|
            .first()
 | 
						|
        if not root_node:
 | 
						|
            return
 | 
						|
        parent_key = root_node.key
 | 
						|
        next_value = 0
 | 
						|
 | 
						|
    next_key = '{}:{}'.format(parent_key, next_value)
 | 
						|
    name = 'Apps'
 | 
						|
    parent = node_model.objects.get(key=parent_key)
 | 
						|
    full_value = parent.full_value + '/' + name
 | 
						|
    defaults = {
 | 
						|
        'key': next_key, 'value': name, 'parent_key': parent_key,
 | 
						|
        'full_value': full_value, 'org_id': org_id
 | 
						|
    }
 | 
						|
    node, __ = node_model.objects.get_or_create(
 | 
						|
        defaults=defaults, value=name, org_id=org_id,
 | 
						|
        parent_key=parent_key
 | 
						|
    )
 | 
						|
    node.parent = parent
 | 
						|
    return node
 | 
						|
 | 
						|
 | 
						|
def migrate_to_nodes(apps, *args):
 | 
						|
    org_model = apps.get_model('orgs', 'Organization')
 | 
						|
    asset_model = apps.get_model('assets', 'Asset')
 | 
						|
    orgs = org_model.objects.all()
 | 
						|
 | 
						|
    # Todo: 优化一些
 | 
						|
    for org in orgs:
 | 
						|
        node = create_app_nodes(apps, org.id)
 | 
						|
        assets = asset_model.objects.filter(
 | 
						|
            platform__category__in=['remote_app', 'database', 'cloud'],
 | 
						|
            org_id=org.id
 | 
						|
        )
 | 
						|
        if not node:
 | 
						|
            continue
 | 
						|
        print("\t- Set node asset: ", node)
 | 
						|
        node.assets_amount = len(assets)
 | 
						|
        node.save()
 | 
						|
        node.assets.set(assets)
 | 
						|
        parent = node.parent
 | 
						|
        parent.assets_amount += len(assets)
 | 
						|
        parent.save()
 | 
						|
 | 
						|
 | 
						|
def migrate_ori_host_to_devices(apps, *args):
 | 
						|
    device_model = apps.get_model('assets', 'Device')
 | 
						|
    asset_model = apps.get_model('assets', 'Asset')
 | 
						|
    host_model = apps.get_model('assets', 'Host')
 | 
						|
    hosts_need_migrate_to_device = host_model.objects.filter(asset_ptr__platform__category='device')
 | 
						|
    assets = asset_model.objects.filter(id__in=hosts_need_migrate_to_device.values_list('asset_ptr_id', flat=True))
 | 
						|
    assets_map = {asset.id: asset for asset in assets}
 | 
						|
 | 
						|
    print("\t- Migrate ori host to device: ", len(hosts_need_migrate_to_device))
 | 
						|
    for host in hosts_need_migrate_to_device:
 | 
						|
        asset = assets_map.get(host.asset_ptr_id)
 | 
						|
        if not asset:
 | 
						|
            continue
 | 
						|
        device = device_model(asset_ptr_id=asset.id)
 | 
						|
        device.__dict__.update(asset.__dict__)
 | 
						|
        device.save()
 | 
						|
        host.delete(keep_parents=True)
 | 
						|
 | 
						|
 | 
						|
class Migration(migrations.Migration):
 | 
						|
    dependencies = [
 | 
						|
        ('assets', '0097_auto_20220426_1558'),
 | 
						|
        ('applications', '0020_auto_20220316_2028')
 | 
						|
    ]
 | 
						|
 | 
						|
    operations = [
 | 
						|
        migrations.RunPython(migrate_database_to_asset),
 | 
						|
        migrations.RunPython(migrate_cloud_to_asset),
 | 
						|
        migrations.RunPython(migrate_to_nodes),
 | 
						|
        migrations.RunPython(migrate_ori_host_to_devices),
 | 
						|
    ]
 |