This commit is contained in:
Vyacheslav Anzhiganov 2016-06-11 21:28:46 +03:00
parent 030f26c903
commit 858bfa3661
9 changed files with 541 additions and 497 deletions

View file

@ -1,23 +1,12 @@
# coding: utf-8 # coding: utf-8
from uuid import uuid4 from flask import Blueprint, jsonify, g
from flask import Blueprint, jsonify, request, g
from flask_httpauth import HTTPBasicAuth from flask_httpauth import HTTPBasicAuth
from SWSCloudCore.controllers.datacenters import ControllerDataCenters
from SWSCloudCore.controllers.ips import ControllerIps
from SWSCloudCore.controllers.plans import ControllerPlans
from SWSCloudCore.controllers.containers import ControllerContainers
from SWSCloudCore.controllers.vms import ControllerVMS
from SWSCloudCore.controllers.users import ControllerAPI from SWSCloudCore.controllers.users import ControllerAPI
from SWSCloudCore.controllers.users import ControllerUsers from SWSCloudCore.controllers.users import ControllerUsers
from SWSCloudCore.controllers.users import ControllerSSHKey
from SWSCloudCore.controllers.billing import ControllerBilling
from SWSCloudCore.controllers.common import ControllerCommon, ControllerMessagesEmail
from SWSCloudCore.controllers.containers import ControllerContainersStatisticsState, ControllerContainersStatistics
from SWSCloudCore.controllers.tasks import ControllerTasks
api = Blueprint('api', __name__, url_prefix='/api/v1') api = Blueprint('api', __name__, url_prefix='')
auth = HTTPBasicAuth() auth = HTTPBasicAuth()
""" """
@ -44,487 +33,3 @@ def index():
:return: :return:
""" """
return jsonify(user_id=g.user_id) return jsonify(user_id=g.user_id)
@api.route('/datacenters/')
@auth.login_required
def datacenters_index():
"""
get containers list
curl -X http://localhost:5000/api/v1/datacenters/ -u <email>:<secret>
:return:
"""
dc_list = ControllerDataCenters().get()
return jsonify(total=dc_list.get('total'), items=dc_list.get('items'))
@api.route('/pricing/vms/')
@auth.login_required
def pricing_vms():
"""
get pricing list
curl -X http://localhost:5000/api/v1/pricing/vms/ -u <email>:<secret>
:return:
"""
return jsonify(pricing=ControllerPlans().get_plans(status='active'))
@api.route('/pricing/containers/')
@auth.login_required
def pricing_containers():
"""
get pricing list
curl -X GET http://localhost:5000/api/v1/pricing/containers/ -u <email>:<secret>
:return:
"""
return jsonify(pricing=100)
@api.route('/containers/', methods=['GET'])
@auth.login_required
def containers_list():
"""
curl -X GET http://localhost:5000/api/v1/containers/ -u <email>:<secret>
:return:
"""
# get containers list
containers = ControllerContainers(g.user_id).get_items()
#
return jsonify(total=containers['total'], items=containers['items'])
@api.route('/containers/', methods=['POST'])
@auth.login_required
def container_create():
"""
curl -X POST http://localhost:5000/api/v1/containers/ -u <email>:<secret> -d "datacenter_id=123"
:return:
"""
# Check exists data center
if not ControllerDataCenters().exists(request.form.get('datacenter')):
return jsonify(message='datacenter not exists')
# Check money
if ControllerBilling().get(g.user_id) <= 0:
return jsonify(message='no money')
# select server from selected region with available ip-addresses
# select IP
select_ip = ControllerIps().getfree(request.form.get('datacenter'))
# mark ip as busy (taken)
ControllerIps().setbusy(select_ip.id)
# generate password for container user
password = ControllerCommon().generate_password(size=14)
user_ssh = ControllerSSHKey(g.user_id)
new_container = dict(
container_id=str(uuid4()),
datacenter_id=str(select_ip.datacenter.id),
server_id=str(select_ip.server.id),
ipv4=select_ip.ipv4,
ipv6=select_ip.ipv6,
ipv4_gateway=select_ip.ipv4_gateway,
ipv6_gateway=select_ip.ipv6_gateway,
username='ubuntu',
password=password,
ssh_key='',
)
# SSH key
if user_ssh.check():
new_container['ssh_key'] = user_ssh.get()
# create container record in database
# status 4: creation
status = 4
container_create = ControllerContainers(g.user_id).create(
new_container['container_id'],
new_container['datacenter_id'],
new_container['server_id'],
new_container['ipv4'],
new_container['ipv6'],
status
)
# create default state data
ControllerContainersStatisticsState().set(new_container['container_id'], dict())
if container_create:
# create task for create new container
ControllerTasks(g.user_id).create(
new_container['datacenter_id'],
new_container['server_id'],
'container_create',
0,
container_id=new_container['container_id'],
ipv4=new_container['ipv4'],
ipv6=new_container['ipv6'],
ipv4_gateway=new_container['ipv4_gateway'],
ipv6_gateway=new_container['ipv6_gateway'],
username=new_container['username'],
password=new_container['password'],
ssh_key=new_container['ssh_key']
)
# send mail message with recovery code
message_parts = []
if new_container['ipv4']:
message_parts.append(u"IPv4: %s" % new_container['ipv4'])
if new_container['ipv6']:
message_parts.append(u"IPv6: %s" % new_container['ipv6'])
message_parts.append(u"Пользователь: %s" % new_container['username'])
message_parts.append(u"Пароль: %s" % new_container['password'])
if new_container['ssh_key']:
message_parts.append(u"SSH ключ: добавлен")
message = '<br/>\n'.join(message_parts)
subject = u'GoCloud.ru: Новый контейнер'
lead = u"""Поздравляем с новым контейнером."""
callout = u"""
Для входа в личный кабинет воспользуйтесь
<a href="https://gocloud.ru/account/login">страницей авторизации</a>.
"""
user_data = ControllerUsers(g.user_id).get()
email = ControllerMessagesEmail()
email.send(title=subject, to=user_data.email, lead=lead, message=message, callout=callout)
#
return jsonify(message='ok')
@api.route('/container/<uuid:container_id>', methods=['DELETE'])
@auth.login_required
def container_delete(container_id):
"""
curl -X DELETE http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret> -d "container_id=<uuid:container_id>"
:return:
"""
containers = ControllerContainers(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not containers.check_exists_item(container_id):
return jsonify(message='container_not_exists')
# get container details
container_details = ControllerContainers(g.user_id).get_item(container_id)
# Обновляем статус "5" для правила
containers.set_status(container_id, 5)
# Создание задания
ControllerTasks(g.user_id).create(
container_details.datacenter.id,
container_details.server.id,
'container_delete',
0,
container_id=container_id
)
# TODO: send email container was deleted about
return jsonify(status=0, message='container has been deleted')
@api.route('/container/<uuid:container_id>', methods=['GET'])
@auth.login_required
def container_info(container_id):
"""
curl -X GET http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret>
:return:
"""
# init
containers = ControllerContainers(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not containers.check_exists_item(container_id):
return jsonify(message='container_not_found')
# get container details
container_details = containers.get_item(container_id)
# print ControllerContainersStatisticsState().get(container_id)
statistics = list()
for s in ControllerContainersStatistics(container_id).size_get(1):
created = s.created
statistics.append({
'year': created.strftime('%Y'),
'month': created.strftime('%m'),
'day': created.strftime('%d'),
'hour': created.strftime('%H'),
'minute': created.strftime('%M'),
'data': s.memory
})
# return
return jsonify(container=container_details, stats_memory=statistics)
@api.route('/container/<uuid:container_id>', methods=['POST'])
@auth.login_required
def container_actions(container_id):
"""
curl -X POST http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret> -d "status=inactive"
curl -X POST http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret> -d "action=active"
:return:
"""
containers = ControllerContainers(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not containers.check_exists_item(container_id):
return jsonify(message='container_not_found')
# get container details
container_details = containers.get_item(container_id)
if request.form.get('status') == "inactive":
containers.set_status(container_id, 3)
# Создание задания
ControllerTasks(g.user_id).create(
container_details.datacenter.id,
container_details.server.id,
'container_stop',
0,
container_id=container_id
)
elif request.form.get('status') == 'active':
balance = ControllerBilling().get(g.user_id)
if balance <= 0:
return jsonify(message='no money')
containers.set_status(container_id, 2)
# Создание задания
ControllerTasks(g.user_id).create(
container_details.datacenter.id,
container_details.server.id,
'container_start',
0,
container_id=container_details.id
)
return jsonify(message='ok')
else:
return jsonify(status=1, message='require action')
@api.route('/vms/')
@auth.login_required
def vms_list():
"""
get virtual servers list
curl -X POST http://localhost:5000/api/v1/vms/ -u <email>:<secret>
:return:
"""
return jsonify(vms=ControllerVMS(g.user_id).get_items())
@api.route('/vms', methods=['POST'])
@auth.login_required
def vms_create():
"""
curl -XPOST /api/v1/vms/ -u <email>:<secret> -d 'plan=<uuid>&datacenter=<uuid>'
:return:
"""
user_balance = ControllerBilling().get(g.user_id)
user_ssh = ControllerSSHKey(g.user_id)
controller_plans = ControllerPlans()
# check user money
if user_balance <= 0:
return jsonify(message='no money')
new_vm = dict()
new_vm['vm_id'] = str(uuid4())
# check exists plan
if not controller_plans.exists(request.form.get('plan')):
return jsonify(message='plan not exists')
# load plan details
plan_details = controller_plans.plan_get(request.form.get('plan'))
new_vm['plan'] = request.form.get('plan')
# select server from selected region with available ip-addresses
# select IP
select_ip = ControllerIps().getfree(request.form.get('datacenter'))
# mark ip as busy (taken)
ControllerIps().setbusy(select_ip.id)
# generate password for container user
new_vm['password'] = ControllerCommon().generate_password(size=14)
new_vm['hostname'] = ControllerCommon().generate_password(size=7)
new_vm['datacenter_id'] = str(select_ip.datacenter.id)
new_vm['server_id'] = str(select_ip.server.id)
new_vm['platform'] = 'x86_64'
new_vm['ipv4'] = select_ip.ipv4
new_vm['ipv6'] = select_ip.ipv6
new_vm['ipv4_gateway'] = select_ip.ipv4_gateway
new_vm['ipv6_gateway'] = select_ip.ipv6_gateway
# TODO: remove hardcore
new_vm['dns1'] = '8.8.8.8'
new_vm['dns2'] = '8.8.4.4'
new_vm['cores'] = plan_details.cores
new_vm['storage'] = plan_details.storage
new_vm['swap'] = plan_details.swap
new_vm['memory'] = plan_details.memory
new_vm['os_name'] = 'ubuntu'
new_vm['os_suite'] = 'trusty'
# sshkey
new_vm['ssh_key'] = None
if user_ssh.check():
new_vm['ssh_key'] = user_ssh.get()
# create container record in database
# status 4: creation
status = 4
container_create = ControllerVMS(g.user_id).create(
vm_id=new_vm['vm_id'],
datacenter_id=new_vm['datacenter_id'],
server_id=new_vm['server_id'],
hostname=new_vm['hostname'],
ipv4=new_vm['ipv4'],
ipv6=new_vm['ipv6'],
plan=new_vm['plan'],
platform=new_vm['platform'],
os_name=new_vm['os_name'],
os_suite=new_vm['os_suite'],
status=status
)
# create default state data
# ControllerContainersStatisticsState().set(new_container['container_id'], dict())
if container_create:
# create task for create new container
ControllerTasks(g.user_id).create(
new_vm['datacenter_id'],
new_vm['server_id'],
'vm_create',
0,
vm_id=new_vm['vm_id'],
ipv4=new_vm['ipv4'],
ipv4_gateway=new_vm['ipv4_gateway'],
ipv6=new_vm['ipv6'],
ipv6_gateway=new_vm['ipv6_gateway'],
password=new_vm['password'],
hostname=new_vm['hostname'],
platform=new_vm['platform'],
# TODO: remove hardcore
dns1=new_vm['dns1'],
dns2=new_vm['dns2'],
cores=new_vm['cores'],
storage=new_vm['storage'],
swap=new_vm['swap'],
memory=new_vm['memory'],
os_name=new_vm['os_name'],
os_suite=new_vm['os_suite'],
ssh_key=new_vm['ssh_key'],
)
# send mail message with recovery code
message_parts = []
if new_vm['ipv4']:
message_parts.append(u"IPv4: %s" % new_vm['ipv4'])
if new_vm['ipv6']:
message_parts.append(u"IPv6: %s" % new_vm['ipv6'])
message_parts.append(u"Пользователь: %s" % 'root')
# message_parts.append(u"Пользователь: %s" % new_vm['username'])
message_parts.append(u"Пароль: %s" % new_vm['password'])
if new_vm['ssh_key']:
message_parts.append(u"SSH ключ: добавлен")
message = '<br/>\n'.join(message_parts)
subject = u'GoCloud.ru: Новый виртуальный сервер'
lead = u"""Поздравляем с новым виртуальным сервером."""
callout = u"""
Для входа в личный кабинет воспользуйтесь
<a href="https://gocloud.ru/account/login">страницей авторизации</a>.
"""
user_data = ControllerUsers(g.user_id).get()
email = ControllerMessagesEmail()
email.send(title=subject, to=user_data.email, lead=lead, message=message, callout=callout)
return jsonify(status=0, message='ok',
user='root', password=new_vm['password'], ipv4=new_vm['ipv4'],
public_ssh_key='added' if new_vm['ssh_key'] else 'empty')
else:
# mark ip as free
ControllerIps().setfree(select_ip.id)
return jsonify(status=1, message='fail')
@api.route('/vms/<uuid:vm_id>', methods=['POST'])
@auth.login_required
def vm_actions(vm_id):
"""
"""
# init ...
vm = ControllerVMS(g.user_id)
# get container details
vm_details = vm.get(vm_id=vm_id)
if request.form.get('action') == "start":
if ControllerBilling().get(g.user_id) <= 0:
return jsonify(message='no money')
vm.set_status(vm_id, 2)
# Создание задания
ControllerTasks(g.user_id).create(
datacenter_id=vm_details.datacenter.id,
server_id=vm_details.server.id,
task='vm_start',
status=0,
vm_id=vm_details.id
)
if request.form.get('action') == "restart":
return jsonify(message='not supported')
if request.form.get('action') == "stop":
vm.status_set(vm_id, 3)
# Создание задания
ControllerTasks(g.user_id).create(
vm_details.datacenter.id,
vm_details.server.id,
'vm_stop',
0,
vm_id=vm_id
)
@api.route('/vms/<uuid:vm_id>', methods=['DELETE'])
@auth.login_required
def vm_delete(vm_id):
"""
Удаление виртуального сервера
:param vm_id:
:return:
"""
#
vms = ControllerVMS(g.user_id)
tasks = ControllerTasks(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not vms.exists(vm_id):
return jsonify(message='not exists')
# get container details
vm_details = vms.get(vm_id)
# Обновляем статус "5" для правила
vms.set_status(vm_id, 5)
# Создание задания
tasks.create(
datacenter_id=vm_details.datacenter.id,
server_id=vm_details.server.id,
task='vm_delete',
status=0,
vm_id=vm_id,
# hostname=vm_details.hostname
)
return jsonify(status=0, message='ok')

View file

@ -0,0 +1,238 @@
# coding: utf-8
from uuid import uuid4
from flask import Blueprint, jsonify, request, g
from SWSCloudAPI.API import auth
from SWSCloudCore.controllers.datacenters import ControllerDataCenters
from SWSCloudCore.controllers.ips import ControllerIps
from SWSCloudCore.controllers.users import ControllerUsers
from SWSCloudCore.controllers.users import ControllerSSHKey
from SWSCloudCore.controllers.billing import ControllerBilling
from SWSCloudCore.controllers.common import ControllerCommon, ControllerMessagesEmail
from SWSCloudCore.controllers.tasks import ControllerTasks
from SWSCloudCore.controllers.containers import (
ControllerContainers, ControllerContainersStatistics, ControllerContainersStatisticsState)
api_v1_containers = Blueprint('containers', __name__, url_prefix='/containers')
@api_v1_containers.route('/', methods=['GET'])
@auth.login_required
def containers_list():
"""
curl -X GET http://localhost:5000/api/v1/containers/ -u <email>:<secret>
:return:
"""
# get containers list
containers = ControllerContainers(g.user_id).get_items()
#
return jsonify(total=containers['total'], items=containers['items'])
@api_v1_containers.route('/', methods=['POST'])
@auth.login_required
def container_create():
"""
curl -X POST http://localhost:5000/api/v1/containers/ -u <email>:<secret> -d "datacenter_id=123"
:return:
"""
# Check exists data center
if not ControllerDataCenters().exists(request.form.get('datacenter')):
return jsonify(message='datacenter not exists')
# Check money
if ControllerBilling().get(g.user_id) <= 0:
return jsonify(message='no money')
# select server from selected region with available ip-addresses
# select IP
select_ip = ControllerIps().getfree(request.form.get('datacenter'))
# mark ip as busy (taken)
ControllerIps().setbusy(select_ip.id)
# generate password for container user
password = ControllerCommon().generate_password(size=14)
user_ssh = ControllerSSHKey(g.user_id)
new_container = dict(
container_id=str(uuid4()),
datacenter_id=str(select_ip.datacenter.id),
server_id=str(select_ip.server.id),
ipv4=select_ip.ipv4,
ipv6=select_ip.ipv6,
ipv4_gateway=select_ip.ipv4_gateway,
ipv6_gateway=select_ip.ipv6_gateway,
username='ubuntu',
password=password,
ssh_key='',
)
# SSH key
if user_ssh.check():
new_container['ssh_key'] = user_ssh.get()
# create container record in database
# status 4: creation
status = 4
container_create = ControllerContainers(g.user_id).create(
new_container['container_id'],
new_container['datacenter_id'],
new_container['server_id'],
new_container['ipv4'],
new_container['ipv6'],
status
)
# create default state data
ControllerContainersStatisticsState().set(new_container['container_id'], dict())
if container_create:
# create task for create new container
ControllerTasks(g.user_id).create(
new_container['datacenter_id'],
new_container['server_id'],
'container_create',
0,
container_id=new_container['container_id'],
ipv4=new_container['ipv4'],
ipv6=new_container['ipv6'],
ipv4_gateway=new_container['ipv4_gateway'],
ipv6_gateway=new_container['ipv6_gateway'],
username=new_container['username'],
password=new_container['password'],
ssh_key=new_container['ssh_key']
)
# send mail message with recovery code
message_parts = []
if new_container['ipv4']:
message_parts.append(u"IPv4: %s" % new_container['ipv4'])
if new_container['ipv6']:
message_parts.append(u"IPv6: %s" % new_container['ipv6'])
message_parts.append(u"Пользователь: %s" % new_container['username'])
message_parts.append(u"Пароль: %s" % new_container['password'])
if new_container['ssh_key']:
message_parts.append(u"SSH ключ: добавлен")
message = '<br/>\n'.join(message_parts)
subject = u'GoCloud.ru: Новый контейнер'
lead = u"""Поздравляем с новым контейнером."""
callout = u"""
Для входа в личный кабинет воспользуйтесь
<a href="https://gocloud.ru/account/login">страницей авторизации</a>.
"""
user_data = ControllerUsers(g.user_id).get()
email = ControllerMessagesEmail()
email.send(title=subject, to=user_data.email, lead=lead, message=message, callout=callout)
#
return jsonify(message='ok')
@api_v1_containers.route('/container/<uuid:container_id>', methods=['DELETE'])
@auth.login_required
def container_delete(container_id):
"""
curl -X DELETE http://gocloud.ru/api/v1/container/<uuid:container_id> -u <email>:<secret> -d "container_id=<uuid:container_id>"
:return:
"""
containers = ControllerContainers(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not containers.check_exists_item(container_id):
return jsonify(message='container_not_exists')
# get container details
container_details = ControllerContainers(g.user_id).get_item(container_id)
# Обновляем статус "5" для правила
containers.set_status(container_id, 5)
# Создание задания
ControllerTasks(g.user_id).create(
container_details.datacenter.id,
container_details.server.id,
'container_delete',
0,
container_id=container_id
)
# TODO: send email container was deleted about
return jsonify(status=0, message='container has been deleted')
@api_v1_containers.route('/<uuid:container_id>', methods=['GET'])
@auth.login_required
def container_info(container_id):
"""
curl -X GET http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret>
:return:
"""
# init
containers = ControllerContainers(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not containers.check_exists_item(container_id):
return jsonify(message='container_not_found')
# get container details
container_details = containers.get_item(container_id)
# print ControllerContainersStatisticsState().get(container_id)
statistics = list()
for s in ControllerContainersStatistics(container_id).size_get(1):
created = s.created
statistics.append({
'year': created.strftime('%Y'),
'month': created.strftime('%m'),
'day': created.strftime('%d'),
'hour': created.strftime('%H'),
'minute': created.strftime('%M'),
'data': s.memory
})
# return
return jsonify(container=container_details, stats_memory=statistics)
@api_v1_containers.route('/<uuid:container_id>', methods=['POST'])
@auth.login_required
def container_actions(container_id):
"""
curl -X POST http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret> -d "status=inactive"
curl -X POST http://localhost:5000/api/v1/container/<uuid:container_id> -u <email>:<secret> -d "action=active"
:return:
"""
containers = ControllerContainers(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not containers.check_exists_item(container_id):
return jsonify(message='container_not_found')
# get container details
container_details = containers.get_item(container_id)
if request.form.get('status') == "inactive":
containers.set_status(container_id, 3)
# Создание задания
ControllerTasks(g.user_id).create(
container_details.datacenter.id,
container_details.server.id,
'container_stop',
0,
container_id=container_id
)
elif request.form.get('status') == 'active':
balance = ControllerBilling().get(g.user_id)
if balance <= 0:
return jsonify(message='no money')
containers.set_status(container_id, 2)
# Создание задания
ControllerTasks(g.user_id).create(
container_details.datacenter.id,
container_details.server.id,
'container_start',
0,
container_id=container_details.id
)
return jsonify(message='ok')
else:
return jsonify(status=1, message='require action')

View file

@ -0,0 +1,20 @@
# coding: utf-8
from flask import Blueprint, jsonify
from SWSCloudAPI.API import auth
from SWSCloudCore.controllers.datacenters import ControllerDataCenters
api_v1_datacenters = Blueprint('datacenters', __name__, url_prefix='/datacenters')
@api_v1_datacenters.route('/', methods=['GET'])
@auth.login_required
def index():
"""
get containers list
curl -X http://localhost:5000/api/v1/datacenters/ -u <email>:<secret>
:return:
"""
dc_list = ControllerDataCenters().get()
return jsonify(total=dc_list.get('total'), items=dc_list.get('items'))

View file

@ -0,0 +1,29 @@
# coding: utf-8
from flask import Blueprint, jsonify
from SWSCloudAPI.API import auth
from SWSCloudCore.controllers.plans import ControllerPlans
api_v1_pricing = Blueprint('pricing', __name__, url_prefix='/pricing')
@api_v1_pricing.route('/pricing/vms/')
@auth.login_required
def pricing_vms():
"""
get pricing list
curl -X http://localhost:5000/api/v1/pricing/vms/ -u <email>:<secret>
:return:
"""
return jsonify(pricing=ControllerPlans().get_plans(status='active'))
@api_v1_pricing.route('/pricing/containers/')
@auth.login_required
def pricing_containers():
"""
get pricing list
curl -X GET http://localhost:5000/api/v1/pricing/containers/ -u <email>:<secret>
:return:
"""
return jsonify(pricing=100)

243
SWSCloudAPI/API/vms.py Normal file
View file

@ -0,0 +1,243 @@
# coding: utf-8
from uuid import uuid4
from flask import Blueprint, jsonify, request, g
from SWSCloudAPI.API import auth
from SWSCloudCore.controllers.ips import ControllerIps
from SWSCloudCore.controllers.plans import ControllerPlans
from SWSCloudCore.controllers.users import ControllerUsers
from SWSCloudCore.controllers.users import ControllerSSHKey
from SWSCloudCore.controllers.billing import ControllerBilling
from SWSCloudCore.controllers.common import ControllerCommon, ControllerMessagesEmail
from SWSCloudCore.controllers.tasks import ControllerTasks
from SWSCloudCore.controllers.vms import ControllerVMS
api_v1_vms = Blueprint('vms', __name__, url_prefix='/vms')
@api_v1_vms.route('/', methods=['GET'])
@auth.login_required
def vms_list():
"""
get virtual servers list
curl -X POST http://localhost:5000/api/v1/vms/ -u <email>:<secret>
:return:
"""
return jsonify(vms=ControllerVMS(g.user_id).get_items())
@api_v1_vms.route('/', methods=['POST'])
@auth.login_required
def vms_create():
"""
curl -XPOST /api/v1/vms/ -u <email>:<secret> -d 'plan=<uuid>&datacenter=<uuid>'
:return:
"""
user_balance = ControllerBilling().get(g.user_id)
user_ssh = ControllerSSHKey(g.user_id)
controller_plans = ControllerPlans()
# check user money
if user_balance <= 0:
return jsonify(message='no money')
new_vm = dict()
new_vm['vm_id'] = str(uuid4())
# check exists plan
if not controller_plans.exists(request.form.get('plan')):
return jsonify(message='plan not exists')
# load plan details
plan_details = controller_plans.plan_get(request.form.get('plan'))
new_vm['plan'] = request.form.get('plan')
# select server from selected region with available ip-addresses
# select IP
select_ip = ControllerIps().getfree(request.form.get('datacenter'))
# mark ip as busy (taken)
ControllerIps().setbusy(select_ip.id)
# generate password for container user
new_vm['password'] = ControllerCommon().generate_password(size=14)
new_vm['hostname'] = ControllerCommon().generate_password(size=7)
new_vm['datacenter_id'] = str(select_ip.datacenter.id)
new_vm['server_id'] = str(select_ip.server.id)
new_vm['platform'] = 'x86_64'
new_vm['ipv4'] = select_ip.ipv4
new_vm['ipv6'] = select_ip.ipv6
new_vm['ipv4_gateway'] = select_ip.ipv4_gateway
new_vm['ipv6_gateway'] = select_ip.ipv6_gateway
# TODO: remove hardcore
new_vm['dns1'] = '8.8.8.8'
new_vm['dns2'] = '8.8.4.4'
new_vm['cores'] = plan_details.cores
new_vm['storage'] = plan_details.storage
new_vm['swap'] = plan_details.swap
new_vm['memory'] = plan_details.memory
new_vm['os_name'] = 'ubuntu'
new_vm['os_suite'] = 'trusty'
# sshkey
new_vm['ssh_key'] = None
if user_ssh.check():
new_vm['ssh_key'] = user_ssh.get()
# create container record in database
# status 4: creation
status = 4
container_create = ControllerVMS(g.user_id).create(
vm_id=new_vm['vm_id'],
datacenter_id=new_vm['datacenter_id'],
server_id=new_vm['server_id'],
hostname=new_vm['hostname'],
ipv4=new_vm['ipv4'],
ipv6=new_vm['ipv6'],
plan=new_vm['plan'],
platform=new_vm['platform'],
os_name=new_vm['os_name'],
os_suite=new_vm['os_suite'],
status=status
)
# create default state data
# ControllerContainersStatisticsState().set(new_container['container_id'], dict())
if container_create:
# create task for create new container
ControllerTasks(g.user_id).create(
new_vm['datacenter_id'],
new_vm['server_id'],
'vm_create',
0,
vm_id=new_vm['vm_id'],
ipv4=new_vm['ipv4'],
ipv4_gateway=new_vm['ipv4_gateway'],
ipv6=new_vm['ipv6'],
ipv6_gateway=new_vm['ipv6_gateway'],
password=new_vm['password'],
hostname=new_vm['hostname'],
platform=new_vm['platform'],
# TODO: remove hardcore
dns1=new_vm['dns1'],
dns2=new_vm['dns2'],
cores=new_vm['cores'],
storage=new_vm['storage'],
swap=new_vm['swap'],
memory=new_vm['memory'],
os_name=new_vm['os_name'],
os_suite=new_vm['os_suite'],
ssh_key=new_vm['ssh_key'],
)
# send mail message with recovery code
message_parts = []
if new_vm['ipv4']:
message_parts.append(u"IPv4: %s" % new_vm['ipv4'])
if new_vm['ipv6']:
message_parts.append(u"IPv6: %s" % new_vm['ipv6'])
message_parts.append(u"Пользователь: %s" % 'root')
# message_parts.append(u"Пользователь: %s" % new_vm['username'])
message_parts.append(u"Пароль: %s" % new_vm['password'])
if new_vm['ssh_key']:
message_parts.append(u"SSH ключ: добавлен")
message = '<br/>\n'.join(message_parts)
subject = u'GoCloud.ru: Новый виртуальный сервер'
lead = u"""Поздравляем с новым виртуальным сервером."""
callout = u"""
Для входа в личный кабинет воспользуйтесь
<a href="https://gocloud.ru/account/login">страницей авторизации</a>.
"""
user_data = ControllerUsers(g.user_id).get()
email = ControllerMessagesEmail()
email.send(title=subject, to=user_data.email, lead=lead, message=message, callout=callout)
return jsonify(status=0, message='ok',
user='root', password=new_vm['password'], ipv4=new_vm['ipv4'],
public_ssh_key='added' if new_vm['ssh_key'] else 'empty')
else:
# mark ip as free
ControllerIps().setfree(select_ip.id)
return jsonify(status=1, message='fail')
@api_v1_vms.route('/<uuid:vm_id>', methods=['POST'])
@auth.login_required
def vm_actions(vm_id):
"""
"""
# init ...
vm = ControllerVMS(g.user_id)
# get container details
vm_details = vm.get(vm_id=vm_id)
if request.form.get('action') == "start":
if ControllerBilling().get(g.user_id) <= 0:
return jsonify(message='no money')
vm.set_status(vm_id, 2)
# Создание задания
ControllerTasks(g.user_id).create(
datacenter_id=vm_details.datacenter.id,
server_id=vm_details.server.id,
task='vm_start',
status=0,
vm_id=vm_details.id
)
if request.form.get('action') == "restart":
return jsonify(message='not supported')
if request.form.get('action') == "stop":
vm.status_set(vm_id, 3)
# Создание задания
ControllerTasks(g.user_id).create(
vm_details.datacenter.id,
vm_details.server.id,
'vm_stop',
0,
vm_id=vm_id
)
@api_v1_vms.route('/vms/<uuid:vm_id>', methods=['DELETE'])
@auth.login_required
def vm_delete(vm_id):
"""
Удаление виртуального сервера
:param vm_id:
:return:
"""
#
vms = ControllerVMS(g.user_id)
tasks = ControllerTasks(g.user_id)
# check the user have a selected rule
# if user not have a container then redirect to the container list
if not vms.exists(vm_id):
return jsonify(message='not exists')
# get container details
vm_details = vms.get(vm_id)
# Обновляем статус "5" для правила
vms.set_status(vm_id, 5)
# Создание задания
tasks.create(
datacenter_id=vm_details.datacenter.id,
server_id=vm_details.server.id,
task='vm_delete',
status=0,
vm_id=vm_id,
# hostname=vm_details.hostname
)
return jsonify(status=0, message='ok')

View file

@ -2,16 +2,25 @@
from flask import Flask, g, jsonify from flask import Flask, g, jsonify
from SWSCloudAPI.API import api from SWSCloudAPI.API import api
from SWSCloudAPI.API.vms import api_v1_vms
from SWSCloudAPI.API.containers import api_v1_containers
from SWSCloudAPI.API.datacenters import api_v1_datacenters
from SWSCloudAPI.API.pricing import api_v1_pricing
from SWSCloudCore import models from SWSCloudCore import models
from SWSCloudCore.models import database from SWSCloudCore.models import database
from SWSCloudCore.config import config from SWSCloudCore.config import config
app = Flask(__name__) app = Flask(__name__)
app.config["APPLICATION_ROOT"] = "/api/v1"
# app.config['SERVER_NAME'] = settings.get('Application', 'SERVER_NAME') # app.config['SERVER_NAME'] = settings.get('Application', 'SERVER_NAME')
app.config['DEBUG'] = config.getboolean('Application', 'DEBUG') app.config['DEBUG'] = config.getboolean('Application', 'DEBUG')
app.config['SECRET_KEY'] = config.get("Application", "SECRET_KEY") app.config['SECRET_KEY'] = config.get("Application", "SECRET_KEY")
app.register_blueprint(api) app.register_blueprint(api)
app.register_blueprint(api_v1_vms)
app.register_blueprint(api_v1_containers)
app.register_blueprint(api_v1_pricing)
app.register_blueprint(api_v1_datacenters)
@app.errorhandler(404) @app.errorhandler(404)