[refactor] cleaning up uncloud_net for Wireguardvpn
This commit is contained in:
		
					parent
					
						
							
								074cffcbd7
							
						
					
				
			
			
				commit
				
					
						10d5a72c5a
					
				
			
		
					 82 changed files with 403 additions and 2180 deletions
				
			
		| 
						 | 
				
			
			@ -1,9 +1,6 @@
 | 
			
		|||
# Generated by Django 3.0.6 on 2020-08-01 16:38
 | 
			
		||||
# Generated by Django 3.1 on 2020-12-13 10:38
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
import django.contrib.postgres.fields.jsonb
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
| 
						 | 
				
			
			@ -11,23 +8,14 @@ class Migration(migrations.Migration):
 | 
			
		|||
    initial = True
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud_pay', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VM',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('vmid', models.IntegerField(primary_key=True, serialize=False)),
 | 
			
		||||
                ('data', django.contrib.postgres.fields.jsonb.JSONField()),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
                ('data', models.JSONField()),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,20 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.8 on 2020-08-01 23:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0003_auto_20200801_2332'),
 | 
			
		||||
        ('opennebula', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,23 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:53
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('opennebula', '0002_auto_20200801_2332'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='data',
 | 
			
		||||
            field=models.JSONField(),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,23 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 12:37
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0013_auto_20200809_1237'),
 | 
			
		||||
        ('opennebula', '0003_auto_20200808_1953'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:44
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('opennebula', '0004_auto_20200809_1237'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,25 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:58
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('opennebula', '0005_remove_vm_orders'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vm',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 20:01
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='ending_date',
 | 
			
		||||
            field=models.DateField(blank=True, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,27 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 20:09
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0010_auto_20201011_2009'),
 | 
			
		||||
        ('uncloud', '0002_auto_20201011_2001'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='billing_network',
 | 
			
		||||
            field=models.ForeignKey(default=0, on_delete=django.db.models.deletion.CASCADE, related_name='uncloudproviderbill', to='uncloud_net.uncloudnetwork'),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='referral_network',
 | 
			
		||||
            field=models.ForeignKey(default=0, on_delete=django.db.models.deletion.CASCADE, related_name='uncloudproviderreferral', to='uncloud_net.uncloudnetwork'),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							| 
						 | 
				
			
			@ -1,21 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-12 17:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0010_auto_20201011_2009'),
 | 
			
		||||
        ('uncloud', '0004_auto_20201011_2031'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='coupon_network',
 | 
			
		||||
            field=models.ForeignKey(default=0, on_delete=django.db.models.deletion.CASCADE, related_name='uncloudprovidercoupon', to='uncloud_net.uncloudnetwork'),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,40 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-25 19:31
 | 
			
		||||
 | 
			
		||||
import django.core.validators
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud', '0005_uncloudprovider_coupon_network'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='UncloudNetwork',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('network_address', models.GenericIPAddressField(unique=True)),
 | 
			
		||||
                ('network_mask', models.IntegerField(validators=[django.core.validators.MinValueValidator(0), django.core.validators.MaxValueValidator(128)])),
 | 
			
		||||
                ('description', models.CharField(max_length=256)),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='billing_network',
 | 
			
		||||
            field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='uncloudproviderbill', to='uncloud.uncloudnetwork'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='coupon_network',
 | 
			
		||||
            field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='uncloudprovidercoupon', to='uncloud.uncloudnetwork'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='uncloudprovider',
 | 
			
		||||
            name='referral_network',
 | 
			
		||||
            field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='uncloudproviderreferral', to='uncloud.uncloudnetwork'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
2
 | 
			
		||||
| 
						 | 
				
			
			@ -42,8 +42,8 @@ router.register(r'v1/service/generic', serviceviews.GenericServiceProductViewSet
 | 
			
		|||
 | 
			
		||||
 | 
			
		||||
# Net
 | 
			
		||||
router.register(r'v1/net/vpn', netviews.VPNNetworkViewSet, basename='vpnnetwork')
 | 
			
		||||
router.register(r'v1/admin/vpnreservation', netviews.VPNNetworkReservationViewSet, basename='vpnnetreservation')
 | 
			
		||||
#router.register(r'v1/net/vpn', netviews.VPNNetworkViewSet, basename='vpnnetwork')
 | 
			
		||||
#router.register(r'v1/admin/vpnreservation', netviews.VPNNetworkReservationViewSet, basename='vpnnetreservation')
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
# Pay
 | 
			
		||||
| 
						 | 
				
			
			@ -59,7 +59,7 @@ router.register(r'v1/admin/payment', payviews.AdminPaymentViewSet, basename='adm
 | 
			
		|||
router.register(r'v1/admin/order', payviews.AdminOrderViewSet, basename='admin/order')
 | 
			
		||||
router.register(r'v1/admin/vmhost', vmviews.VMHostViewSet)
 | 
			
		||||
router.register(r'v1/admin/vmcluster', vmviews.VMClusterViewSet)
 | 
			
		||||
router.register(r'v1/admin/vpnpool', netviews.VPNPoolViewSet)
 | 
			
		||||
#router.register(r'v1/admin/vpnpool', netviews.VPNPoolViewSet)
 | 
			
		||||
#router.register(r'v1/admin/opennebula', oneviews.VMViewSet, basename='opennebula')
 | 
			
		||||
 | 
			
		||||
# User/Account
 | 
			
		||||
| 
						 | 
				
			
			@ -77,7 +77,7 @@ urlpatterns = [
 | 
			
		|||
        description="uncloud API",
 | 
			
		||||
        version="1.0.0"
 | 
			
		||||
    ), name='openapi-schema'),
 | 
			
		||||
    path('vpn/create/', netviews.VPNCreateView.as_view(), name="vpncreate"),
 | 
			
		||||
    path('vpn/create/', netviews.WireGuardVPNCreateView.as_view(), name="vpncreate"),
 | 
			
		||||
    path('login/', authviews.LoginView.as_view(), name="login"),
 | 
			
		||||
    path('logout/', authviews.LogoutView.as_view(), name="logout"),
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,4 +1,4 @@
 | 
			
		|||
# Generated by Django 3.0.6 on 2020-08-01 16:38
 | 
			
		||||
# Generated by Django 3.1 on 2020-12-13 10:38
 | 
			
		||||
 | 
			
		||||
import django.contrib.auth.models
 | 
			
		||||
import django.contrib.auth.validators
 | 
			
		||||
| 
						 | 
				
			
			@ -12,7 +12,7 @@ class Migration(migrations.Migration):
 | 
			
		|||
    initial = True
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('auth', '0011_update_proxy_permissions'),
 | 
			
		||||
        ('auth', '0012_alter_user_first_name_max_length'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
| 
						 | 
				
			
			@ -24,7 +24,7 @@ class Migration(migrations.Migration):
 | 
			
		|||
                ('last_login', models.DateTimeField(blank=True, null=True, verbose_name='last login')),
 | 
			
		||||
                ('is_superuser', models.BooleanField(default=False, help_text='Designates that this user has all permissions without explicitly assigning them.', verbose_name='superuser status')),
 | 
			
		||||
                ('username', models.CharField(error_messages={'unique': 'A user with that username already exists.'}, help_text='Required. 150 characters or fewer. Letters, digits and @/./+/-/_ only.', max_length=150, unique=True, validators=[django.contrib.auth.validators.UnicodeUsernameValidator()], verbose_name='username')),
 | 
			
		||||
                ('first_name', models.CharField(blank=True, max_length=30, verbose_name='first name')),
 | 
			
		||||
                ('first_name', models.CharField(blank=True, max_length=150, verbose_name='first name')),
 | 
			
		||||
                ('last_name', models.CharField(blank=True, max_length=150, verbose_name='last name')),
 | 
			
		||||
                ('email', models.EmailField(blank=True, max_length=254, verbose_name='email address')),
 | 
			
		||||
                ('is_staff', models.BooleanField(default=False, help_text='Designates whether the user can log into this admin site.', verbose_name='staff status')),
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:53
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_auth', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='user',
 | 
			
		||||
            name='first_name',
 | 
			
		||||
            field=models.CharField(blank=True, max_length=150, verbose_name='first name'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,6 +1,7 @@
 | 
			
		|||
from django.contrib import admin
 | 
			
		||||
from .models import ReverseDNSEntry
 | 
			
		||||
 | 
			
		||||
from .models import *
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
for m in [ ReverseDNSEntry ]:
 | 
			
		||||
for m in [ ReverseDNSEntry, WireGuardVPNPool, WireGuardVPN ]:
 | 
			
		||||
    admin.site.register(m)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
							
								
								
									
										12
									
								
								uncloud_net/forms.py
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								uncloud_net/forms.py
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
				
			
			@ -0,0 +1,12 @@
 | 
			
		|||
from django import forms
 | 
			
		||||
 | 
			
		||||
from .models import *
 | 
			
		||||
from .selectors import *
 | 
			
		||||
 | 
			
		||||
class WireGuardVPNForm(forms.ModelForm):
 | 
			
		||||
    class Meta:
 | 
			
		||||
        model = WireGuardVPN
 | 
			
		||||
 | 
			
		||||
        network_size = forms.ChoiceField(choices=allowed_vpn_network_reservation_size)
 | 
			
		||||
 | 
			
		||||
        fields = [ "wireguard_public_key" ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,11 +1,9 @@
 | 
			
		|||
# Generated by Django 3.0.6 on 2020-08-01 16:38
 | 
			
		||||
# Generated by Django 3.1 on 2020-12-13 10:38
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
import django.contrib.postgres.fields.jsonb
 | 
			
		||||
import django.core.validators
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
import uuid
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
| 
						 | 
				
			
			@ -14,7 +12,6 @@ class Migration(migrations.Migration):
 | 
			
		|||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud_pay', '__first__'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
| 
						 | 
				
			
			@ -25,45 +22,31 @@ class Migration(migrations.Migration):
 | 
			
		|||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VPNPool',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('uuid', models.UUIDField(default=uuid.uuid4, editable=False, primary_key=True, serialize=False)),
 | 
			
		||||
                ('network', models.GenericIPAddressField(unique=True)),
 | 
			
		||||
                ('network_size', models.IntegerField(validators=[django.core.validators.MinValueValidator(0), django.core.validators.MaxValueValidator(128)])),
 | 
			
		||||
                ('subnetwork_size', models.IntegerField(validators=[django.core.validators.MinValueValidator(0), django.core.validators.MaxValueValidator(128)])),
 | 
			
		||||
                ('vpn_hostname', models.CharField(max_length=256)),
 | 
			
		||||
                ('wireguard_private_key', models.CharField(max_length=48)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VPNNetworkReservation',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('address', models.GenericIPAddressField(primary_key=True, serialize=False)),
 | 
			
		||||
                ('status', models.CharField(choices=[('used', 'used'), ('free', 'free')], default='used', max_length=256)),
 | 
			
		||||
                ('vpnpool', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_net.VPNPool')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VPNNetwork',
 | 
			
		||||
            name='WireGuardVPNPool',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('wireguard_public_key', models.CharField(max_length=48)),
 | 
			
		||||
                ('network', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to='uncloud_net.VPNNetworkReservation')),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
                ('network', models.GenericIPAddressField(unique=True)),
 | 
			
		||||
                ('network_mask', models.IntegerField(validators=[django.core.validators.MinValueValidator(0), django.core.validators.MaxValueValidator(128)])),
 | 
			
		||||
                ('subnetwork_mask', models.IntegerField(validators=[django.core.validators.MinValueValidator(0), django.core.validators.MaxValueValidator(128)])),
 | 
			
		||||
                ('vpn_server_hostname', models.CharField(max_length=256)),
 | 
			
		||||
                ('wireguard_private_key', models.CharField(max_length=48)),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='WireGuardVPN',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('address', models.GenericIPAddressField(primary_key=True, serialize=False)),
 | 
			
		||||
                ('wireguard_public_key', models.CharField(max_length=48)),
 | 
			
		||||
                ('vpnpool', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_net.wireguardvpnpool')),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='ReverseDNSEntry',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('ip_address', models.GenericIPAddressField(unique=True)),
 | 
			
		||||
                ('name', models.CharField(max_length=253)),
 | 
			
		||||
                ('owner', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,20 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.8 on 2020-08-01 23:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0003_auto_20200801_2332'),
 | 
			
		||||
        ('uncloud_net', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,28 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:53
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0002_auto_20200801_2332'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vpnnetworkreservation',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vpnpool',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,23 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 12:37
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0013_auto_20200809_1237'),
 | 
			
		||||
        ('uncloud_net', '0003_auto_20200808_1953'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:44
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0004_auto_20200809_1237'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,25 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:58
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0005_remove_vpnnetwork_orders'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnnetwork',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,22 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 19:20
 | 
			
		||||
 | 
			
		||||
import django.core.validators
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0006_auto_20200928_1858'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='UncloudNetwork',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('network_address', models.GenericIPAddressField()),
 | 
			
		||||
                ('network_mask', models.IntegerField(validators=[django.core.validators.MinValueValidator(0), django.core.validators.MaxValueValidator(128)])),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 19:24
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0007_uncloudnetwork'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='uncloudnetwork',
 | 
			
		||||
            name='network_address',
 | 
			
		||||
            field=models.GenericIPAddressField(unique=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,19 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 19:24
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0008_auto_20201011_1924'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='uncloudnetwork',
 | 
			
		||||
            name='description',
 | 
			
		||||
            field=models.CharField(default='', max_length=256),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,21 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 20:09
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_net', '0009_uncloudnetwork_description'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnnetworkreservation',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vpnpool',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,29 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-25 19:31
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud', '0006_auto_20201025_1931'),
 | 
			
		||||
        ('uncloud_net', '0010_auto_20201011_2009'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='ReverseDNSEntry',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('ip_address', models.GenericIPAddressField(unique=True)),
 | 
			
		||||
                ('name', models.CharField(max_length=253)),
 | 
			
		||||
                ('owner', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='UncloudNetwork',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -8,180 +8,39 @@ from django.core.exceptions import FieldError, ValidationError
 | 
			
		|||
 | 
			
		||||
from uncloud_pay.models import Order
 | 
			
		||||
 | 
			
		||||
class MACAdress(models.Model):
 | 
			
		||||
    default_prefix = 0x420000000000
 | 
			
		||||
 | 
			
		||||
class VPNPool(models.Model):
 | 
			
		||||
class WireGuardVPNPool(models.Model):
 | 
			
		||||
    """
 | 
			
		||||
    Network address pools from which VPNs can be created
 | 
			
		||||
    """
 | 
			
		||||
 | 
			
		||||
    uuid = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
 | 
			
		||||
 | 
			
		||||
    network = models.GenericIPAddressField(unique=True)
 | 
			
		||||
    network_size = models.IntegerField(validators=[MinValueValidator(0),
 | 
			
		||||
    network_mask = models.IntegerField(validators=[MinValueValidator(0),
 | 
			
		||||
                                                   MaxValueValidator(128)])
 | 
			
		||||
 | 
			
		||||
    subnetwork_size = models.IntegerField(validators=[
 | 
			
		||||
                                              MinValueValidator(0),
 | 
			
		||||
                                              MaxValueValidator(128)
 | 
			
		||||
                                          ])
 | 
			
		||||
 | 
			
		||||
    vpn_hostname = models.CharField(max_length=256)
 | 
			
		||||
    subnetwork_mask = models.IntegerField(validators=[
 | 
			
		||||
        MinValueValidator(0),
 | 
			
		||||
        MaxValueValidator(128)
 | 
			
		||||
    ])
 | 
			
		||||
 | 
			
		||||
    vpn_server_hostname = models.CharField(max_length=256)
 | 
			
		||||
    wireguard_private_key = models.CharField(max_length=48)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def num_maximum_networks(self):
 | 
			
		||||
        """
 | 
			
		||||
        sample:
 | 
			
		||||
        network_size = 40
 | 
			
		||||
        subnetwork_size = 48
 | 
			
		||||
        maximum_networks = 2^(48-40)
 | 
			
		||||
 | 
			
		||||
        2nd sample:
 | 
			
		||||
        network_size = 8
 | 
			
		||||
        subnetwork_size = 24
 | 
			
		||||
        maximum_networks = 2^(24-8)
 | 
			
		||||
        """
 | 
			
		||||
 | 
			
		||||
        return 2**(self.subnetwork_size - self.network_size)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def used_networks(self):
 | 
			
		||||
        return self.vpnnetworkreservation_set.filter(vpnpool=self, status='used')
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def free_networks(self):
 | 
			
		||||
        return self.vpnnetworkreservation_set.filter(vpnpool=self, status='free')
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def num_used_networks(self):
 | 
			
		||||
        return len(self.used_networks)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def num_free_networks(self):
 | 
			
		||||
        return self.num_maximum_networks - self.num_used_networks + len(self.free_networks)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def next_free_network(self):
 | 
			
		||||
        if self.num_free_networks == 0:
 | 
			
		||||
            # FIXME: use right exception
 | 
			
		||||
            raise Exception("No free networks")
 | 
			
		||||
 | 
			
		||||
        if len(self.free_networks) > 0:
 | 
			
		||||
            return self.free_networks[0].address
 | 
			
		||||
 | 
			
		||||
        if len(self.used_networks) > 0:
 | 
			
		||||
            """
 | 
			
		||||
            sample:
 | 
			
		||||
 | 
			
		||||
            pool = 2a0a:e5c1:200::/40
 | 
			
		||||
            last_used = 2a0a:e5c1:204::/48
 | 
			
		||||
 | 
			
		||||
            next:
 | 
			
		||||
            """
 | 
			
		||||
 | 
			
		||||
            last_net = ipaddress.ip_network(self.used_networks.last().address)
 | 
			
		||||
            last_net_ip = last_net[0]
 | 
			
		||||
 | 
			
		||||
            if last_net_ip.version == 6:
 | 
			
		||||
                offset_to_next = 2**(128 - self.subnetwork_size)
 | 
			
		||||
            elif last_net_ip.version == 4:
 | 
			
		||||
                offset_to_next = 2**(32 - self.subnetwork_size)
 | 
			
		||||
 | 
			
		||||
            next_net_ip = last_net_ip + offset_to_next
 | 
			
		||||
 | 
			
		||||
            return str(next_net_ip)
 | 
			
		||||
        else:
 | 
			
		||||
            # first network to be created
 | 
			
		||||
            return self.network
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def wireguard_config_filename(self):
 | 
			
		||||
        return '/etc/wireguard/{}.conf'.format(self.network)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def wireguard_config(self):
 | 
			
		||||
        wireguard_config = [
 | 
			
		||||
            """
 | 
			
		||||
[Interface]
 | 
			
		||||
ListenPort = 51820
 | 
			
		||||
PrivateKey = {privatekey}
 | 
			
		||||
""".format(privatekey=self.wireguard_private_key) ]
 | 
			
		||||
 | 
			
		||||
        peers = []
 | 
			
		||||
 | 
			
		||||
        for reservation in self.vpnnetworkreservation_set.filter(status='used'):
 | 
			
		||||
            public_key = reservation.vpnnetwork_set.first().wireguard_public_key
 | 
			
		||||
            peer_network = "{}/{}".format(reservation.address, self.subnetwork_size)
 | 
			
		||||
            owner = reservation.vpnnetwork_set.first().owner
 | 
			
		||||
 | 
			
		||||
            peers.append("""
 | 
			
		||||
# Owner: {owner}
 | 
			
		||||
[Peer]
 | 
			
		||||
PublicKey = {public_key}
 | 
			
		||||
AllowedIPs = {peer_network}
 | 
			
		||||
""".format(
 | 
			
		||||
    owner=owner,
 | 
			
		||||
    public_key=public_key,
 | 
			
		||||
    peer_network=peer_network))
 | 
			
		||||
 | 
			
		||||
        wireguard_config.extend(peers)
 | 
			
		||||
 | 
			
		||||
        return "\n".join(wireguard_config)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    def configure_wireguard_vpnserver(self):
 | 
			
		||||
        """
 | 
			
		||||
        This method is designed to run as a celery task and should
 | 
			
		||||
        not be called directly from the web
 | 
			
		||||
        """
 | 
			
		||||
 | 
			
		||||
        # subprocess, ssh
 | 
			
		||||
 | 
			
		||||
        pass
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class VPNNetworkReservation(models.Model):
 | 
			
		||||
class WireGuardVPN(models.Model):
 | 
			
		||||
    """
 | 
			
		||||
     This class tracks the used VPN networks. It will be deleted, when the product is cancelled.
 | 
			
		||||
     """
 | 
			
		||||
    vpnpool = models.ForeignKey(VPNPool,
 | 
			
		||||
    Created VPNNetworks
 | 
			
		||||
    """
 | 
			
		||||
    vpnpool = models.ForeignKey(WireGuardVPNPool,
 | 
			
		||||
                                 on_delete=models.CASCADE)
 | 
			
		||||
 | 
			
		||||
    address = models.GenericIPAddressField(primary_key=True)
 | 
			
		||||
 | 
			
		||||
    status = models.CharField(max_length=256,
 | 
			
		||||
                              default='used',
 | 
			
		||||
                              choices = (
 | 
			
		||||
                                  ('used', 'used'),
 | 
			
		||||
                                  ('free', 'free')
 | 
			
		||||
                              )
 | 
			
		||||
    )
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class VPNNetwork(models.Model):
 | 
			
		||||
    """
 | 
			
		||||
    A selected network. Used for tracking reservations / used networks
 | 
			
		||||
    """
 | 
			
		||||
    network = models.ForeignKey(VPNNetworkReservation,
 | 
			
		||||
                               on_delete=models.CASCADE,
 | 
			
		||||
                               editable=False)
 | 
			
		||||
 | 
			
		||||
    wireguard_public_key = models.CharField(max_length=48)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def recurring_price(self):
 | 
			
		||||
        return 120
 | 
			
		||||
 | 
			
		||||
################################################################################
 | 
			
		||||
 | 
			
		||||
    def delete(self, *args, **kwargs):
 | 
			
		||||
        self.network.status = 'free'
 | 
			
		||||
        self.network.save()
 | 
			
		||||
        super().save(*args, **kwargs)
 | 
			
		||||
        print("deleted {}".format(self))
 | 
			
		||||
 | 
			
		||||
class MACAdress(models.Model):
 | 
			
		||||
    default_prefix = 0x420000000000
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class ReverseDNSEntry(models.Model):
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,7 +1,9 @@
 | 
			
		|||
from django.db.models import Count
 | 
			
		||||
from django.db import transaction
 | 
			
		||||
from django.db.models import Count, F
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
from .models import *
 | 
			
		||||
 | 
			
		||||
@transaction.atomic
 | 
			
		||||
def get_suitable_pool(subnetwork_size):
 | 
			
		||||
    """
 | 
			
		||||
    Find suitable pools for a certain network size.
 | 
			
		||||
| 
						 | 
				
			
			@ -21,3 +23,20 @@ def get_suitable_pool(subnetwork_size):
 | 
			
		|||
        max_reservations=2**(F('subnetwork_size')-F('network_size'))).filter(
 | 
			
		||||
            num_reservations__lt=F('max_reservations'),
 | 
			
		||||
            subnetwork_size=subnetwork_size)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
def allowed_vpn_network_reservation_size():
 | 
			
		||||
    """
 | 
			
		||||
    Find all possible sizes of subnetworks that are available.
 | 
			
		||||
 | 
			
		||||
    Select all pools with free networks.
 | 
			
		||||
 | 
			
		||||
    Get their subnetwork sizes, reduce to a set
 | 
			
		||||
 | 
			
		||||
    """
 | 
			
		||||
 | 
			
		||||
    pools = VPNPool.objects.annotate(num_reservations=Count('vpnnetworkreservation'),
 | 
			
		||||
                                     max_reservations=2**(F('subnetwork_size')-F('network_size'))).filter(
 | 
			
		||||
                                         num_reservations__lt=F('max_reservations'))
 | 
			
		||||
 | 
			
		||||
    return set([ pool.subnetwork_size for pool in pools ])
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -6,95 +6,95 @@ from rest_framework import serializers
 | 
			
		|||
 | 
			
		||||
from .models import *
 | 
			
		||||
 | 
			
		||||
class VPNPoolSerializer(serializers.ModelSerializer):
 | 
			
		||||
    class Meta:
 | 
			
		||||
        model = VPNPool
 | 
			
		||||
        fields = '__all__'
 | 
			
		||||
# class WireGuardVPNPoolSerializer(serializers.ModelSerializer):
 | 
			
		||||
#     class Meta:
 | 
			
		||||
#         model = WireGuardVPNPool
 | 
			
		||||
#         fields = '__all__'
 | 
			
		||||
 | 
			
		||||
class VPNNetworkReservationSerializer(serializers.ModelSerializer):
 | 
			
		||||
    class Meta:
 | 
			
		||||
        model = VPNNetworkReservation
 | 
			
		||||
        fields = '__all__'
 | 
			
		||||
# class WireGuardVPNSerializer(serializers.ModelSerializer):
 | 
			
		||||
#     class Meta:
 | 
			
		||||
#         model = VPNNetworkReservation
 | 
			
		||||
#         fields = '__all__'
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class VPNNetworkSerializer(serializers.ModelSerializer):
 | 
			
		||||
    class Meta:
 | 
			
		||||
        model = VPNNetwork
 | 
			
		||||
        fields = '__all__'
 | 
			
		||||
# class VPNNetworkSerializer(serializers.ModelSerializer):
 | 
			
		||||
#     class Meta:
 | 
			
		||||
#         model = VPNNetwork
 | 
			
		||||
#         fields = '__all__'
 | 
			
		||||
 | 
			
		||||
    # This is required for finding the VPN pool, but does not
 | 
			
		||||
    # exist in the model
 | 
			
		||||
    network_size = serializers.IntegerField(min_value=0,
 | 
			
		||||
                                            max_value=128,
 | 
			
		||||
                                            write_only=True)
 | 
			
		||||
#     # This is required for finding the VPN pool, but does not
 | 
			
		||||
#     # exist in the model
 | 
			
		||||
#     network_size = serializers.IntegerField(min_value=0,
 | 
			
		||||
#                                             max_value=128,
 | 
			
		||||
#                                             write_only=True)
 | 
			
		||||
 | 
			
		||||
    def validate_wireguard_public_key(self, value):
 | 
			
		||||
        msg = _("Supplied key is not a valid wireguard public key")
 | 
			
		||||
#     def validate_wireguard_public_key(self, value):
 | 
			
		||||
#         msg = _("Supplied key is not a valid wireguard public key")
 | 
			
		||||
 | 
			
		||||
        """ FIXME: verify that this does not create broken wireguard config files,
 | 
			
		||||
        i.e. contains \n or similar!
 | 
			
		||||
        We might even need to be more strict to not break wireguard...
 | 
			
		||||
        """
 | 
			
		||||
#         """ FIXME: verify that this does not create broken wireguard config files,
 | 
			
		||||
#         i.e. contains \n or similar!
 | 
			
		||||
#         We might even need to be more strict to not break wireguard...
 | 
			
		||||
#         """
 | 
			
		||||
 | 
			
		||||
        try:
 | 
			
		||||
            base64.standard_b64decode(value)
 | 
			
		||||
        except Exception as e:
 | 
			
		||||
            raise serializers.ValidationError(msg)
 | 
			
		||||
#         try:
 | 
			
		||||
#             base64.standard_b64decode(value)
 | 
			
		||||
#         except Exception as e:
 | 
			
		||||
#             raise serializers.ValidationError(msg)
 | 
			
		||||
 | 
			
		||||
        if '\n' in value:
 | 
			
		||||
            raise serializers.ValidationError(msg)
 | 
			
		||||
#         if '\n' in value:
 | 
			
		||||
#             raise serializers.ValidationError(msg)
 | 
			
		||||
 | 
			
		||||
        return value
 | 
			
		||||
#         return value
 | 
			
		||||
 | 
			
		||||
    def validate(self, data):
 | 
			
		||||
#     def validate(self, data):
 | 
			
		||||
 | 
			
		||||
        # FIXME: filter for status = active or similar
 | 
			
		||||
        all_pools = VPNPool.objects.all()
 | 
			
		||||
        sizes = [ p.subnetwork_size for p in all_pools ]
 | 
			
		||||
#         # FIXME: filter for status = active or similar
 | 
			
		||||
#         all_pools = VPNPool.objects.all()
 | 
			
		||||
#         sizes = [ p.subnetwork_size for p in all_pools ]
 | 
			
		||||
 | 
			
		||||
        pools = VPNPool.objects.filter(subnetwork_size=data['network_size'])
 | 
			
		||||
#         pools = VPNPool.objects.filter(subnetwork_size=data['network_size'])
 | 
			
		||||
 | 
			
		||||
        if len(pools) == 0:
 | 
			
		||||
            msg = _("No pool available for networks with size = {}. Available are: {}".format(data['network_size'], sizes))
 | 
			
		||||
            raise serializers.ValidationError(msg)
 | 
			
		||||
#         if len(pools) == 0:
 | 
			
		||||
#             msg = _("No pool available for networks with size = {}. Available are: {}".format(data['network_size'], sizes))
 | 
			
		||||
#             raise serializers.ValidationError(msg)
 | 
			
		||||
 | 
			
		||||
        return data
 | 
			
		||||
#         return data
 | 
			
		||||
 | 
			
		||||
    def create(self, validated_data):
 | 
			
		||||
        """
 | 
			
		||||
        Creating a new vpnnetwork - there are a couple of race conditions,
 | 
			
		||||
        especially when run in parallel.
 | 
			
		||||
#     def create(self, validated_data):
 | 
			
		||||
#         """
 | 
			
		||||
#         Creating a new vpnnetwork - there are a couple of race conditions,
 | 
			
		||||
#         especially when run in parallel.
 | 
			
		||||
 | 
			
		||||
        What we should be doing:
 | 
			
		||||
#         What we should be doing:
 | 
			
		||||
 | 
			
		||||
        - create a reservation race free
 | 
			
		||||
        - map the reservation to a network (?)
 | 
			
		||||
        """
 | 
			
		||||
#         - create a reservation race free
 | 
			
		||||
#         - map the reservation to a network (?)
 | 
			
		||||
#         """
 | 
			
		||||
 | 
			
		||||
        pools = VPNPool.objects.filter(subnetwork_size=validated_data['network_size'])
 | 
			
		||||
#         pools = VPNPool.objects.filter(subnetwork_size=validated_data['network_size'])
 | 
			
		||||
 | 
			
		||||
        vpn_network = None
 | 
			
		||||
#         vpn_network = None
 | 
			
		||||
 | 
			
		||||
        for pool in pools:
 | 
			
		||||
            if pool.num_free_networks > 0:
 | 
			
		||||
                next_address = pool.next_free_network
 | 
			
		||||
#         for pool in pools:
 | 
			
		||||
#             if pool.num_free_networks > 0:
 | 
			
		||||
#                 next_address = pool.next_free_network
 | 
			
		||||
 | 
			
		||||
                reservation, created = VPNNetworkReservation.objects.update_or_create(
 | 
			
		||||
                    vpnpool=pool, address=next_address,
 | 
			
		||||
                    defaults = {
 | 
			
		||||
                        'status': 'used'
 | 
			
		||||
                    })
 | 
			
		||||
#                 reservation, created = VPNNetworkReservation.objects.update_or_create(
 | 
			
		||||
#                     vpnpool=pool, address=next_address,
 | 
			
		||||
#                     defaults = {
 | 
			
		||||
#                         'status': 'used'
 | 
			
		||||
#                     })
 | 
			
		||||
 | 
			
		||||
                vpn_network = VPNNetwork.objects.create(
 | 
			
		||||
                    owner=self.context['request'].user,
 | 
			
		||||
                    network=reservation,
 | 
			
		||||
                    wireguard_public_key=validated_data['wireguard_public_key']
 | 
			
		||||
                )
 | 
			
		||||
#                 vpn_network = VPNNetwork.objects.create(
 | 
			
		||||
#                     owner=self.context['request'].user,
 | 
			
		||||
#                     network=reservation,
 | 
			
		||||
#                     wireguard_public_key=validated_data['wireguard_public_key']
 | 
			
		||||
#                 )
 | 
			
		||||
 | 
			
		||||
                break
 | 
			
		||||
        if not vpn_network:
 | 
			
		||||
            # FIXME: use correct exception
 | 
			
		||||
            raise Exception("Did not find any free pool")
 | 
			
		||||
#                 break
 | 
			
		||||
#         if not vpn_network:
 | 
			
		||||
#             # FIXME: use correct exception
 | 
			
		||||
#             raise Exception("Did not find any free pool")
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
        return vpn_network
 | 
			
		||||
#         return vpn_network
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
							
								
								
									
										118
									
								
								uncloud_net/services.py
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										118
									
								
								uncloud_net/services.py
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
				
			
			@ -0,0 +1,118 @@
 | 
			
		|||
from django.db import transaction
 | 
			
		||||
from .models import *
 | 
			
		||||
 | 
			
		||||
@transaction.atomic
 | 
			
		||||
def create_vpn(*,
 | 
			
		||||
               public_key: str,
 | 
			
		||||
               network_size: int
 | 
			
		||||
               ) -> VPNNetwork:
 | 
			
		||||
 | 
			
		||||
    # Select suitable pool
 | 
			
		||||
    pools = VPNPool.objects.filter(subnetwork_size=network_size)
 | 
			
		||||
 | 
			
		||||
    # FIXME: exception - which?
 | 
			
		||||
    if not pools:
 | 
			
		||||
        return None
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    # Find all pools with the correct size
 | 
			
		||||
 | 
			
		||||
    # For each pool see if it has still space:
 | 
			
		||||
    # num network reversations < 2**(subnetwork_size-network_size)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    def next_free_network(self):
 | 
			
		||||
        if self.num_free_networks == 0:
 | 
			
		||||
            # FIXME: use right exception
 | 
			
		||||
            raise Exception("No free networks")
 | 
			
		||||
 | 
			
		||||
        if len(self.free_networks) > 0:
 | 
			
		||||
            return self.free_networks[0].address
 | 
			
		||||
 | 
			
		||||
        if len(self.used_networks) > 0:
 | 
			
		||||
            """
 | 
			
		||||
            sample:
 | 
			
		||||
 | 
			
		||||
            pool = 2a0a:e5c1:200::/40
 | 
			
		||||
            last_used = 2a0a:e5c1:204::/48
 | 
			
		||||
 | 
			
		||||
            next:
 | 
			
		||||
            """
 | 
			
		||||
 | 
			
		||||
            last_net = ipaddress.ip_network(self.used_networks.last().address)
 | 
			
		||||
            last_net_ip = last_net[0]
 | 
			
		||||
 | 
			
		||||
            if last_net_ip.version == 6:
 | 
			
		||||
                offset_to_next = 2**(128 - self.subnetwork_size)
 | 
			
		||||
            elif last_net_ip.version == 4:
 | 
			
		||||
                offset_to_next = 2**(32 - self.subnetwork_size)
 | 
			
		||||
 | 
			
		||||
            next_net_ip = last_net_ip + offset_to_next
 | 
			
		||||
 | 
			
		||||
            return str(next_net_ip)
 | 
			
		||||
        else:
 | 
			
		||||
            # first network to be created
 | 
			
		||||
            return self.network
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def wireguard_config_filename(self):
 | 
			
		||||
        return '/etc/wireguard/{}.conf'.format(self.network)
 | 
			
		||||
 | 
			
		||||
    @property
 | 
			
		||||
    def wireguard_config(self):
 | 
			
		||||
        wireguard_config = [
 | 
			
		||||
            """
 | 
			
		||||
[Interface]
 | 
			
		||||
ListenPort = 51820
 | 
			
		||||
PrivateKey = {privatekey}
 | 
			
		||||
""".format(privatekey=self.wireguard_private_key) ]
 | 
			
		||||
 | 
			
		||||
        peers = []
 | 
			
		||||
 | 
			
		||||
        for reservation in self.vpnnetworkreservation_set.filter(status='used'):
 | 
			
		||||
            public_key = reservation.vpnnetwork_set.first().wireguard_public_key
 | 
			
		||||
            peer_network = "{}/{}".format(reservation.address, self.subnetwork_size)
 | 
			
		||||
            owner = reservation.vpnnetwork_set.first().owner
 | 
			
		||||
 | 
			
		||||
            peers.append("""
 | 
			
		||||
# Owner: {owner}
 | 
			
		||||
[Peer]
 | 
			
		||||
PublicKey = {public_key}
 | 
			
		||||
AllowedIPs = {peer_network}
 | 
			
		||||
""".format(
 | 
			
		||||
    owner=owner,
 | 
			
		||||
    public_key=public_key,
 | 
			
		||||
    peer_network=peer_network))
 | 
			
		||||
 | 
			
		||||
        wireguard_config.extend(peers)
 | 
			
		||||
 | 
			
		||||
        return "\n".join(wireguard_config)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    def configure_wireguard_vpnserver(self):
 | 
			
		||||
        """
 | 
			
		||||
        This method is designed to run as a celery task and should
 | 
			
		||||
        not be called directly from the web
 | 
			
		||||
        """
 | 
			
		||||
 | 
			
		||||
        # subprocess, ssh
 | 
			
		||||
 | 
			
		||||
        pass
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    def num_maximum_networks(self):
 | 
			
		||||
        """
 | 
			
		||||
        sample:
 | 
			
		||||
        network_size = 40
 | 
			
		||||
        subnetwork_size = 48
 | 
			
		||||
        maximum_networks = 2^(48-40)
 | 
			
		||||
 | 
			
		||||
        2nd sample:
 | 
			
		||||
        network_size = 8
 | 
			
		||||
        subnetwork_size = 24
 | 
			
		||||
        maximum_networks = 2^(24-8)
 | 
			
		||||
        """
 | 
			
		||||
 | 
			
		||||
        return 2**(self.subnetwork_mask - self.network_mask)
 | 
			
		||||
| 
						 | 
				
			
			@ -5,19 +5,9 @@
 | 
			
		|||
  <div class="row">
 | 
			
		||||
    <div class="col">
 | 
			
		||||
      <h1>
 | 
			
		||||
      <h1>Generate new prefix</h1>
 | 
			
		||||
      <h1>Create a VPN Network</h1>
 | 
			
		||||
      <p>
 | 
			
		||||
        A new random prefix will be generated for you.
 | 
			
		||||
      </p>
 | 
			
		||||
 | 
			
		||||
      <p>
 | 
			
		||||
        All ULA prefixes are /48 networks. Simply add the first IP address
 | 
			
		||||
        (without any netmask, for instance fd23:2323:2323::).
 | 
			
		||||
 | 
			
		||||
        You can choose the name of your liking and an organization name.
 | 
			
		||||
      </p>
 | 
			
		||||
      <p>
 | 
			
		||||
        ULA prefixes are always subnets of the fd00::/8 network.
 | 
			
		||||
        Create a new wireguard based VPN network.
 | 
			
		||||
      </p>
 | 
			
		||||
 | 
			
		||||
    </div>
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -9,45 +9,41 @@ from rest_framework import viewsets, permissions
 | 
			
		|||
 | 
			
		||||
from .models      import *
 | 
			
		||||
from .serializers import *
 | 
			
		||||
from .selectors   import *
 | 
			
		||||
from .forms       import *
 | 
			
		||||
 | 
			
		||||
# class VPNPoolViewSet(viewsets.ModelViewSet):
 | 
			
		||||
#     serializer_class = VPNPoolSerializer
 | 
			
		||||
#     permission_classes = [permissions.IsAdminUser]
 | 
			
		||||
#     queryset = VPNPool.objects.all()
 | 
			
		||||
 | 
			
		||||
# class VPNNetworkReservationViewSet(viewsets.ModelViewSet):
 | 
			
		||||
#     serializer_class = VPNNetworkReservationSerializer
 | 
			
		||||
#     permission_classes = [permissions.IsAdminUser]
 | 
			
		||||
#     queryset = VPNNetworkReservation.objects.all()
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class VPNPoolViewSet(viewsets.ModelViewSet):
 | 
			
		||||
    serializer_class = VPNPoolSerializer
 | 
			
		||||
    permission_classes = [permissions.IsAdminUser]
 | 
			
		||||
    queryset = VPNPool.objects.all()
 | 
			
		||||
# class VPNNetworkViewSet(viewsets.ModelViewSet):
 | 
			
		||||
#     serializer_class = VPNNetworkSerializer
 | 
			
		||||
#     permission_classes = [permissions.IsAuthenticated]
 | 
			
		||||
 | 
			
		||||
class VPNNetworkReservationViewSet(viewsets.ModelViewSet):
 | 
			
		||||
    serializer_class = VPNNetworkReservationSerializer
 | 
			
		||||
    permission_classes = [permissions.IsAdminUser]
 | 
			
		||||
    queryset = VPNNetworkReservation.objects.all()
 | 
			
		||||
#     def get_queryset(self):
 | 
			
		||||
#         if self.request.user.is_superuser:
 | 
			
		||||
#             obj = VPNNetwork.objects.all()
 | 
			
		||||
#         else:
 | 
			
		||||
#             obj = VPNNetwork.objects.filter(owner=self.request.user)
 | 
			
		||||
 | 
			
		||||
#         return obj
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class VPNNetworkViewSet(viewsets.ModelViewSet):
 | 
			
		||||
    serializer_class = VPNNetworkSerializer
 | 
			
		||||
#    permission_classes = [permissions.IsAdminUser]
 | 
			
		||||
    permission_classes = [permissions.IsAuthenticated]
 | 
			
		||||
 | 
			
		||||
    def get_queryset(self):
 | 
			
		||||
        if self.request.user.is_superuser:
 | 
			
		||||
            obj = VPNNetwork.objects.all()
 | 
			
		||||
        else:
 | 
			
		||||
            obj = VPNNetwork.objects.filter(owner=self.request.user)
 | 
			
		||||
 | 
			
		||||
        return obj
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class VPNCreateView(LoginRequiredMixin, SuccessMessageMixin, CreateView):
 | 
			
		||||
    model = VPNNetwork
 | 
			
		||||
class WireGuardVPNCreateView(LoginRequiredMixin, SuccessMessageMixin, CreateView):
 | 
			
		||||
    model = WireGuardVPN
 | 
			
		||||
 | 
			
		||||
    login_url = '/login/'
 | 
			
		||||
    success_url = '/'
 | 
			
		||||
    success_message = "%(the_prefix)s/48 was created successfully"
 | 
			
		||||
    success_message = "%(network) was created successfully"
 | 
			
		||||
 | 
			
		||||
    gen_method = "undef"
 | 
			
		||||
 | 
			
		||||
    fields = [ "wireguard_public_key" ]
 | 
			
		||||
    form_class = WireGuardVPNForm
 | 
			
		||||
 | 
			
		||||
    def get_success_message(self, cleaned_data):
 | 
			
		||||
        return self.success_message % dict(cleaned_data,
 | 
			
		||||
| 
						 | 
				
			
			@ -55,5 +51,5 @@ class VPNCreateView(LoginRequiredMixin, SuccessMessageMixin, CreateView):
 | 
			
		|||
 | 
			
		||||
    def get_context_data(self, **kwargs):
 | 
			
		||||
        context = super().get_context_data(**kwargs)
 | 
			
		||||
        context['method'] = self.gen_method
 | 
			
		||||
        context['available_sizes'] = 2
 | 
			
		||||
        return context
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.8 on 2020-08-01 22:08
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='organization',
 | 
			
		||||
            field=models.CharField(blank=True, max_length=100, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,33 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.8 on 2020-08-01 23:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0002_auto_20200801_2208'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='vatrate',
 | 
			
		||||
            old_name='stop_date',
 | 
			
		||||
            new_name='ending_date',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='vatrate',
 | 
			
		||||
            old_name='start_date',
 | 
			
		||||
            new_name='starting_date',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='bill',
 | 
			
		||||
            name='ending_date',
 | 
			
		||||
            field=models.DateTimeField(),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='billrecord',
 | 
			
		||||
            name='quantity',
 | 
			
		||||
            field=models.DecimalField(decimal_places=10, max_digits=19),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:53
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0003_auto_20200801_2332'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='one_time_price',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:54
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0004_remove_order_one_time_price'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            old_name='recurring_price',
 | 
			
		||||
            new_name='price',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:57
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0005_auto_20200808_1954'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billrecord',
 | 
			
		||||
            name='quantity',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 20:20
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0006_remove_billrecord_quantity'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='bill',
 | 
			
		||||
            name='bill_records',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,16 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 20:36
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0007_remove_bill_bill_records'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='OrderRecord',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,22 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 21:13
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0008_delete_orderrecord'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='bill',
 | 
			
		||||
            name='valid',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='bill',
 | 
			
		||||
            name='is_final',
 | 
			
		||||
            field=models.BooleanField(default=False),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,65 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 08:56
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud_pay', '0009_auto_20200808_2113'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='depends_on',
 | 
			
		||||
            field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='parent_of', to='uncloud_pay.order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='replaces',
 | 
			
		||||
            field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='replaced_by', to='uncloud_pay.order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='SampleRecurringProductOneTimeFee',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('order', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='SampleRecurringProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('order', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='SampleOneTimeProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('order', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,19 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 10:24
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0010_auto_20200809_0856'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='bill',
 | 
			
		||||
            name='billing_address',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.billingaddress'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,19 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 10:26
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0011_bill_billing_address'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='bill',
 | 
			
		||||
            name='billing_address',
 | 
			
		||||
            field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.billingaddress'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,40 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 12:37
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0012_auto_20200809_1026'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,33 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-25 19:15
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0013_auto_20200809_1237'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='ot_price',
 | 
			
		||||
            field=models.IntegerField(default=5),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='rc_price',
 | 
			
		||||
            field=models.IntegerField(default=10),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='ot_price',
 | 
			
		||||
            field=models.IntegerField(default=5),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='rc_price',
 | 
			
		||||
            field=models.IntegerField(default=10),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,25 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:44
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0014_auto_20200825_1915'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,65 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:58
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud_pay', '0015_auto_20200928_1844'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='sampleonetimeproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='samplerecurringproductonetimefee',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='Product',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('config', models.JSONField()),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,19 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:04
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0016_auto_20200928_1858'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='config',
 | 
			
		||||
            field=models.JSONField(default={}),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,20 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:08
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0017_order_config'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='product',
 | 
			
		||||
            field=models.ForeignKey(default=0, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.product'),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:14
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0018_order_product'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,29 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:15
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0019_remove_product_owner'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='description',
 | 
			
		||||
            field=models.CharField(default='', max_length=1024),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='name',
 | 
			
		||||
            field=models.CharField(default='', max_length=256),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,23 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0020_auto_20200928_1915'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='default_currency',
 | 
			
		||||
            field=models.CharField(choices=[('CHF', 'Swiss Franc'), ('EUR', 'Euro'), ('USD', 'US Dollar')], default='CHF', max_length=32),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='default_recurring_period',
 | 
			
		||||
            field=models.IntegerField(choices=[(31536000, 'Per 365 days'), (2592000, 'Per 30 days'), (604800, 'Per Week'), (86400, 'Per Day'), (3600, 'Per Hour'), (60, 'Per Minute'), (1, 'Per Second'), (0, 'Onetime')], default=2592000),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0021_auto_20200928_1932'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            old_name='default_currency',
 | 
			
		||||
            new_name='currency',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:44
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0022_auto_20200928_1932'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RenameField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            old_name='price',
 | 
			
		||||
            new_name='one_time_price',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,24 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 19:45
 | 
			
		||||
 | 
			
		||||
import django.core.validators
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0023_auto_20200928_1944'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='currency',
 | 
			
		||||
            field=models.CharField(choices=[('CHF', 'Swiss Franc'), ('EUR', 'Euro'), ('USD', 'US Dollar')], default='CHF', max_length=32),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='recurring_price',
 | 
			
		||||
            field=models.DecimalField(decimal_places=2, default=0.0, max_digits=10, validators=[django.core.validators.MinValueValidator(0)]),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,19 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 20:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0024_auto_20200928_1945'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='billrecord',
 | 
			
		||||
            name='is_recurring_record',
 | 
			
		||||
            field=models.BooleanField(default=False),
 | 
			
		||||
            preserve_default=False,
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 20:42
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0025_billrecord_is_recurring_record'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='should_be_billed',
 | 
			
		||||
            field=models.BooleanField(default=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,41 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-06 13:19
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0026_order_should_be_billed'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='RecurringPeriod',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('name', models.CharField(max_length=100, unique=True)),
 | 
			
		||||
                ('duration_seconds', models.IntegerField(unique=True)),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='SampleOneTimeProduct',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='SampleRecurringProduct',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='SampleRecurringProductOneTimeFee',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='order',
 | 
			
		||||
            name='recurring_period',
 | 
			
		||||
            field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.recurringperiod'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='default_recurring_period',
 | 
			
		||||
            field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.recurringperiod'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,36 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-06 15:29
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0027_auto_20201006_1319'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='default_recurring_period',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='ProductToRecurringPeriod',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('is_default', models.BooleanField(default=False)),
 | 
			
		||||
                ('product', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.product')),
 | 
			
		||||
                ('recurring_period', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.recurringperiod')),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='recurring_periods',
 | 
			
		||||
            field=models.ManyToManyField(through='uncloud_pay.ProductToRecurringPeriod', to='uncloud_pay.RecurringPeriod'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddConstraint(
 | 
			
		||||
            model_name='producttorecurringperiod',
 | 
			
		||||
            constraint=models.UniqueConstraint(condition=models.Q(is_default=True), fields=('recurring_period', 'product'), name='one_default_recurring_period_per_product'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,18 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-06 15:40
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0028_auto_20201006_1529'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='name',
 | 
			
		||||
            field=models.CharField(max_length=256, unique=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,21 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-06 16:40
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0029_auto_20201006_1540'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveConstraint(
 | 
			
		||||
            model_name='producttorecurringperiod',
 | 
			
		||||
            name='one_default_recurring_period_per_product',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddConstraint(
 | 
			
		||||
            model_name='producttorecurringperiod',
 | 
			
		||||
            constraint=models.UniqueConstraint(condition=models.Q(is_default=True), fields=('product',), name='one_default_recurring_period_per_product'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,17 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-06 16:55
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0030_auto_20201006_1640'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AddConstraint(
 | 
			
		||||
            model_name='producttorecurringperiod',
 | 
			
		||||
            constraint=models.UniqueConstraint(fields=('product', 'recurring_period'), name='recurring_period_once_per_product'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,23 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 15:42
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0031_auto_20201006_1655'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='UncloudProvider',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('valid_from', models.DateField()),
 | 
			
		||||
                ('valid_to', models.DateField(blank=True)),
 | 
			
		||||
                ('billing_address', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.billingaddress')),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,20 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 20:03
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0032_uncloudprovider'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='product',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.DeleteModel(
 | 
			
		||||
            name='UncloudProvider',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,37 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-10-11 20:31
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0033_auto_20201011_2003'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='city',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='country',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='name',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='organization',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='postal_code',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='billingaddress',
 | 
			
		||||
            name='street',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							| 
						 | 
				
			
			@ -1,52 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.6 on 2020-08-01 16:38
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
import django.contrib.postgres.fields.jsonb
 | 
			
		||||
import django.core.validators
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    initial = True
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_vm', '__first__'),
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud_pay', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='MatrixServiceProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('domain', models.CharField(default='domain.tld', max_length=255)),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMProduct')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='GenericServiceProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('custom_description', models.TextField()),
 | 
			
		||||
                ('custom_recurring_price', models.DecimalField(decimal_places=2, default=0.0, max_digits=10, validators=[django.core.validators.MinValueValidator(0)])),
 | 
			
		||||
                ('custom_one_time_price', models.DecimalField(decimal_places=2, default=0.0, max_digits=10, validators=[django.core.validators.MinValueValidator(0)])),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,25 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.8 on 2020-08-01 23:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0003_auto_20200801_2332'),
 | 
			
		||||
        ('uncloud_service', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,23 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:53
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_service', '0002_auto_20200801_2332'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,32 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 12:37
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0013_auto_20200809_1237'),
 | 
			
		||||
        ('uncloud_service', '0003_auto_20200808_1953'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,21 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:44
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_service', '0004_auto_20200809_1237'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,37 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:58
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_service', '0005_auto_20200928_1844'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='genericserviceproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='matrixserviceproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,7 +1,6 @@
 | 
			
		|||
# Generated by Django 3.0.6 on 2020-08-01 16:38
 | 
			
		||||
# Generated by Django 3.1 on 2020-12-13 10:38
 | 
			
		||||
 | 
			
		||||
from django.conf import settings
 | 
			
		||||
import django.contrib.postgres.fields.jsonb
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -12,7 +11,6 @@ class Migration(migrations.Migration):
 | 
			
		|||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        migrations.swappable_dependency(settings.AUTH_USER_MODEL),
 | 
			
		||||
        ('uncloud_pay', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
| 
						 | 
				
			
			@ -20,7 +18,7 @@ class Migration(migrations.Migration):
 | 
			
		|||
            name='VMCluster',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('name', models.CharField(max_length=128, unique=True)),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
| 
						 | 
				
			
			@ -31,7 +29,7 @@ class Migration(migrations.Migration):
 | 
			
		|||
            name='VMDiskImageProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('name', models.CharField(max_length=256)),
 | 
			
		||||
                ('is_os_image', models.BooleanField(default=False)),
 | 
			
		||||
                ('is_public', models.BooleanField(default=False, editable=False)),
 | 
			
		||||
| 
						 | 
				
			
			@ -51,13 +49,13 @@ class Migration(migrations.Migration):
 | 
			
		|||
            name='VMHost',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('extra_data', models.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('hostname', models.CharField(max_length=253, unique=True)),
 | 
			
		||||
                ('physical_cores', models.IntegerField(default=0)),
 | 
			
		||||
                ('usable_cores', models.IntegerField(default=0)),
 | 
			
		||||
                ('usable_ram_in_gb', models.FloatField(default=0)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='PENDING', max_length=32)),
 | 
			
		||||
                ('vmcluster', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMCluster')),
 | 
			
		||||
                ('vmcluster', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmcluster')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
| 
						 | 
				
			
			@ -67,35 +65,21 @@ class Migration(migrations.Migration):
 | 
			
		|||
            name='VMProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('name', models.CharField(blank=True, max_length=32, null=True)),
 | 
			
		||||
                ('cores', models.IntegerField()),
 | 
			
		||||
                ('ram_in_gb', models.FloatField()),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
                ('vmcluster', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMCluster')),
 | 
			
		||||
                ('vmhost', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMHost')),
 | 
			
		||||
                ('vmcluster', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmcluster')),
 | 
			
		||||
                ('vmhost', models.ForeignKey(blank=True, editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmhost')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VMSnapshotProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('gb_ssd', models.FloatField(editable=False)),
 | 
			
		||||
                ('gb_hdd', models.FloatField(editable=False)),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='snapshots', to='uncloud_vm.VMProduct')),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='snapshots', to='uncloud_vm.vmproduct')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VMNetworkCard',
 | 
			
		||||
| 
						 | 
				
			
			@ -103,35 +87,25 @@ class Migration(migrations.Migration):
 | 
			
		|||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('mac_address', models.BigIntegerField()),
 | 
			
		||||
                ('ip_address', models.GenericIPAddressField(blank=True, null=True)),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMProduct')),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmproduct')),
 | 
			
		||||
            ],
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VMDiskProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
 | 
			
		||||
                ('extra_data', django.contrib.postgres.fields.jsonb.JSONField(blank=True, editable=False, null=True)),
 | 
			
		||||
                ('status', models.CharField(choices=[('PENDING', 'Pending'), ('AWAITING_PAYMENT', 'Awaiting payment'), ('BEING_CREATED', 'Being created'), ('SCHEDULED', 'Scheduled'), ('ACTIVE', 'Active'), ('MODIFYING', 'Modifying'), ('DELETED', 'Deleted'), ('DISABLED', 'Disabled'), ('UNUSABLE', 'Unusable')], default='AWAITING_PAYMENT', max_length=32)),
 | 
			
		||||
                ('size_in_gb', models.FloatField(blank=True)),
 | 
			
		||||
                ('disk_type', models.CharField(choices=[('ceph/ssd', 'Ceph Ssd'), ('ceph/hdd', 'Ceph Hdd'), ('local/ssd', 'Local Ssd'), ('local/hdd', 'Local Hdd')], default='ceph/ssd', max_length=20)),
 | 
			
		||||
                ('image', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMDiskImageProduct')),
 | 
			
		||||
                ('order', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order')),
 | 
			
		||||
                ('owner', models.ForeignKey(editable=False, on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMProduct')),
 | 
			
		||||
                ('image', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmdiskimageproduct')),
 | 
			
		||||
                ('vm', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmproduct')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.CreateModel(
 | 
			
		||||
            name='VMWithOSProduct',
 | 
			
		||||
            fields=[
 | 
			
		||||
                ('vmproduct_ptr', models.OneToOneField(auto_created=True, on_delete=django.db.models.deletion.CASCADE, parent_link=True, primary_key=True, serialize=False, to='uncloud_vm.VMProduct')),
 | 
			
		||||
                ('primary_disk', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.VMDiskProduct')),
 | 
			
		||||
                ('vmproduct_ptr', models.OneToOneField(auto_created=True, on_delete=django.db.models.deletion.CASCADE, parent_link=True, primary_key=True, serialize=False, to='uncloud_vm.vmproduct')),
 | 
			
		||||
                ('primary_disk', models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_vm.vmdiskproduct')),
 | 
			
		||||
            ],
 | 
			
		||||
            options={
 | 
			
		||||
                'abstract': False,
 | 
			
		||||
            },
 | 
			
		||||
            bases=('uncloud_vm.vmproduct',),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,30 +0,0 @@
 | 
			
		|||
# Generated by Django 3.0.8 on 2020-08-01 23:32
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
import django.db.models.deletion
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0003_auto_20200801_2332'),
 | 
			
		||||
        ('uncloud_vm', '0001_initial'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
            field=models.ForeignKey(null=True, on_delete=django.db.models.deletion.CASCADE, to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,43 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-08 19:53
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_vm', '0002_auto_20200801_2332'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmcluster',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmdiskimageproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmhost',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AlterField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
            field=models.JSONField(blank=True, editable=False, null=True),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,41 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-08-09 12:37
 | 
			
		||||
 | 
			
		||||
from django.db import migrations, models
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_pay', '0013_auto_20200809_1237'),
 | 
			
		||||
        ('uncloud_vm', '0003_auto_20200808_1953'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='order',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.AddField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
            field=models.ManyToManyField(to='uncloud_pay.Order'),
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,25 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:44
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_vm', '0004_auto_20200809_1237'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='orders',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
| 
						 | 
				
			
			@ -1,49 +0,0 @@
 | 
			
		|||
# Generated by Django 3.1 on 2020-09-28 18:58
 | 
			
		||||
 | 
			
		||||
from django.db import migrations
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class Migration(migrations.Migration):
 | 
			
		||||
 | 
			
		||||
    dependencies = [
 | 
			
		||||
        ('uncloud_vm', '0005_auto_20200928_1844'),
 | 
			
		||||
    ]
 | 
			
		||||
 | 
			
		||||
    operations = [
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmdiskproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='extra_data',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='owner',
 | 
			
		||||
        ),
 | 
			
		||||
        migrations.RemoveField(
 | 
			
		||||
            model_name='vmsnapshotproduct',
 | 
			
		||||
            name='status',
 | 
			
		||||
        ),
 | 
			
		||||
    ]
 | 
			
		||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue