993eb223bf7d7d16ae575b9061cf57c7ee2952bb
[laas.git] / src / api / serializers / booking_serializer.py
1 ##############################################################################
2 # Copyright (c) 2018 Parker Berberian, Sawyer Bergeron, and others.
3 #
4 # All rights reserved. This program and the accompanying materials
5 # are made available under the terms of the Apache License, Version 2.0
6 # which accompanies this distribution, and is available at
7 # http://www.apache.org/licenses/LICENSE-2.0
8 ##############################################################################
9
10
11 from rest_framework import serializers
12
13 from resource_inventory.models import (
14     ResourceConfiguration,
15     CpuProfile,
16     DiskProfile,
17     InterfaceProfile,
18     RamProfile,
19     Image,
20     Interface
21 )
22
23
24 class BookingField(serializers.Field):
25
26     def to_representation(self, booking):
27         """
28         Take in a booking object.
29
30         Returns a dictionary of primitives representing that booking
31         """
32         ser = {}
33         ser['id'] = booking.id
34         # main loop to grab relevant info out of booking
35         host_configs = {}  # mapping hostname -> config
36         networks = {}  # mapping vlan id -> network_hosts
37         for host in booking.resource.hosts.all():
38             host_configs[host.name] = ResourceConfiguration.objects.get(host=host.template)
39             if "jumphost" not in ser and host_configs[host.name].opnfvRole.name.lower() == "jumphost":
40                 ser['jumphost'] = host.name
41             # host is a Host model
42             for i in range(len(host.interfaces.all())):
43                 interface = host.interfaces.all()[i]
44                 # interface is an Interface model
45                 for vlan in interface.config.all():
46                     # vlan is Vlan model
47                     if vlan.id not in networks:
48                         networks[vlan.id] = []
49                     net_host = {"hostname": host.name, "tagged": vlan.tagged, "interface": i}
50                     networks[vlan.id].append(net_host)
51         # creates networking object of proper form
52         networking = []
53         for vlanid in networks:
54             network = {}
55             network['vlan_id'] = vlanid
56             network['hosts'] = networks[vlanid]
57
58         ser['networking'] = networking
59
60         # creates hosts object of correct form
61         hosts = []
62         for hostname in host_configs:
63             host = {"hostname": hostname}
64             host['deploy_image'] = True  # TODO?
65             image = host_configs[hostname].image
66             host['image'] = {
67                 "name": image.name,
68                 "lab_id": image.lab_id,
69                 "dashboard_id": image.id
70             }
71             hosts.append(host)
72
73         ser['hosts'] = hosts
74
75         return ser
76
77     def to_internal_value(self, data):
78         """
79         Take in a dictionary of primitives, and return a booking object.
80
81         This is not going to be implemented or allowed.
82         If someone needs to create a booking through the api,
83         they will send a different booking object
84         """
85         return None
86
87
88 class BookingSerializer(serializers.Serializer):
89
90     booking = BookingField()
91
92
93 # Host Type stuff, for inventory
94 class CPUSerializer(serializers.ModelSerializer):
95     class Meta:
96         model = CpuProfile
97         fields = ('cores', 'architecture', 'cpus')
98
99
100 class DiskSerializer(serializers.ModelSerializer):
101     class Meta:
102         model = DiskProfile
103         fields = ('size', 'media_type', 'name')
104
105
106 class InterfaceProfileSerializer(serializers.ModelSerializer):
107     class Meta:
108         model = InterfaceProfile
109         fields = ('speed', 'name')
110
111
112 class RamSerializer(serializers.ModelSerializer):
113     class Meta:
114         model = RamProfile
115         fields = ('amount', 'channels')
116
117
118 class HostTypeSerializer(serializers.Serializer):
119     name = serializers.CharField(max_length=200)
120     ram = RamSerializer()
121     interface = InterfaceProfileSerializer()
122     description = serializers.CharField(max_length=1000)
123     disks = DiskSerializer()
124     cpu = CPUSerializer()
125
126
127 # the rest of the inventory stuff
128 class NetworkSerializer(serializers.Serializer):
129     cidr = serializers.CharField(max_length=200)
130     gateway = serializers.IPAddressField(max_length=200)
131     vlan = serializers.IntegerField()
132
133
134 class ImageSerializer(serializers.ModelSerializer):
135     lab_id = serializers.IntegerField()
136     id = serializers.IntegerField(source="dashboard_id")
137     name = serializers.CharField(max_length=50)
138     description = serializers.CharField(max_length=200)
139
140     class Meta:
141         model = Image
142
143
144 class InterfaceField(serializers.Field):
145     def to_representation(self, interface):
146         pass
147
148     def to_internal_value(self, data):
149         """Take in a serialized interface and creates an Interface model."""
150         mac = data['mac']
151         bus_address = data['busaddr']
152         switch_name = data['switchport']['switch_name']
153         port_name = data['switchport']['port_name']
154         # TODO config??
155         return Interface.objects.create(
156             mac_address=mac,
157             bus_address=bus_address,
158             switch_name=switch_name,
159             port_name=port_name
160         )
161
162
163 class InventoryHostSerializer(serializers.Serializer):
164     hostname = serializers.CharField(max_length=100)
165     host_type = serializers.CharField(max_length=100)
166     interfaces = InterfaceField()
167
168
169 class InventorySerializer(serializers.Serializer):
170     hosts = InventoryHostSerializer()
171     networks = NetworkSerializer()
172     images = ImageSerializer()
173     host_types = HostTypeSerializer()