New Session Handling design

Change-Id: I92ede5ca5d64ba6fb170963cea090cd843880f79
This commit is contained in:
Serg Melikyan 2013-05-26 19:33:57 +04:00
parent 218e0e78bd
commit 4b44d3ef22
10 changed files with 574 additions and 573 deletions

View File

@ -1,207 +1,207 @@
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import logging
from openstack_dashboard.api.base import url_for
from muranodashboard import settings
from muranoclient.v1.client import Client as murano_client
log = logging.getLogger(__name__)
def muranoclient(request):
url = getattr(settings, 'MURANO_API_URL', False)
if not url:
url = url_for(request, 'murano')
log.debug('muranoclient connection created using token "%s" and url "%s"'
% (request.user.token, url))
return murano_client(endpoint=url, token=request.user.token.token['id'])
def environment_create(request, parameters):
env = muranoclient(request).environments.create(parameters.get('name', ''))
log.debug('Environment::Create {0}'.format(env))
return env
def environment_delete(request, environment_id):
result = muranoclient(request).environments.delete(environment_id)
log.debug('Environment::Delete Id:{0}'.format(environment_id))
return result
def environment_get(request, environment_id):
env = muranoclient(request).environments.get(environment_id)
log.debug('Environment::Get {0}'.format(env))
return env
def environments_list(request):
log.debug('Environment::List')
return muranoclient(request).environments.list()
def request_session_id(request, environment_id):
session_id = None
container_name = "murano_session_for_env" + environment_id
env_session = request.session.get(container_name, [])
if len(env_session) > 0:
session_id = env_session.get('id', None)
return session_id
def get_session_id(request, environment_id):
container_name = "murano_session_for_env" + environment_id
session_id = request_session_id(request, environment_id)
if not session_id:
session_id = muranoclient(request).sessions\
.configure(environment_id).id
request.session[container_name] = {'id': session_id}
return session_id
def environment_deploy(request, environment_id):
session_id = request_session_id(request, environment_id)
if not session_id:
return "Sorry, nothing to deploy."
log.debug('Obtained session with Id: {0}'.format(session_id))
result = muranoclient(request).sessions.deploy(environment_id, session_id)
log.debug('Environment with Id: {0} deployed in session '
'with Id: {1}'.format(environment_id, session_id))
return result
def service_create(request, environment_id, parameters):
session_id = get_session_id(request, environment_id)
if parameters['service_type'] == 'Active Directory':
service = muranoclient(request)\
.activeDirectories\
.create(environment_id, session_id, parameters)
elif parameters['service_type'] == 'IIS':
service = muranoclient(request)\
.webServers.create(environment_id, session_id, parameters)
elif parameters['service_type'] == 'ASP.NET Application':
service = muranoclient(request)\
.aspNetApps.create(environment_id, session_id, parameters)
elif parameters['service_type'] == 'IIS Farm':
service = muranoclient(request)\
.webServerFarms.create(environment_id, session_id, parameters)
elif parameters['service_type'] == 'ASP.NET Farm':
service = muranoclient(request)\
.aspNetAppFarms.create(environment_id, session_id, parameters)
else:
raise NameError('Unknown service type ' + parameters['service_type'])
log.debug('Service::Create {0}'.format(service))
return service
def get_time(obj):
return obj.updated
def services_list(request, environment_id):
services = []
session_id = request_session_id(request, environment_id)
if session_id:
services = muranoclient(request).activeDirectories.\
list(environment_id, session_id)
services += muranoclient(request).webServers.\
list(environment_id, session_id)
services += muranoclient(request).aspNetApps.\
list(environment_id, session_id)
services += muranoclient(request).webServerFarms.\
list(environment_id, session_id)
services += muranoclient(request).aspNetAppFarms.\
list(environment_id, session_id)
for i in range(len(services)):
reports = muranoclient(request).sessions.\
reports(environment_id,
session_id,
services[i].id)
for report in reports:
services[i].operation = report.text
log.debug('Service::List')
return services
def get_active_directories(request, environment_id):
session_id = get_session_id(request, environment_id)
services = muranoclient(request).activeDirectories\
.list(environment_id, session_id)
log.debug('Service::Active Directories::List')
return services
def service_get(request, service_id):
environment_id = get_data_center_id_for_service(request, service_id)
services = services_list(request, environment_id)
for service in services:
if service.id == service_id:
log.debug('Service::Get {0}'.format(service))
return service
def get_data_center_id_for_service(request, service_id):
environments = environments_list(request)
for environment in environments:
services = services_list(request, environment.id)
for service in services:
if service.id == service_id:
return environment.id
def get_status_message_for_service(request, service_id):
environment_id = get_data_center_id_for_service(request, service_id)
session_id = get_session_id(request, environment_id)
reports = muranoclient(request).sessions.reports(environment_id,
session_id,
service_id)
result = 'Initialization.... \n'
for report in reports:
result += ' ' + str(report.text) + '\n'
return result
def service_delete(request, service_id):
log.debug('Service::Remove '
'SrvId: {0}'.format(service_id))
environment_id = get_data_center_id_for_service(request, service_id)
service = service_get(request, service_id)
session_id = get_session_id(request, environment_id)
if service.service_type == 'Active Directory':
muranoclient(request).activeDirectories.delete(environment_id,
session_id,
service_id)
elif service.service_type == 'IIS':
muranoclient(request).webServers.delete(environment_id,
session_id,
service_id)
elif service.service_type == 'ASP.NET Application':
muranoclient(request).aspNetApps.delete(environment_id,
session_id,
service_id)
# Copyright (c) 2013 Mirantis, Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import logging
import bunch
from openstack_dashboard.api.base import url_for
from muranodashboard import settings
from muranoclient.v1.client import Client
log = logging.getLogger(__name__)
def muranoclient(request):
url = getattr(settings, 'MURANO_API_URL')
if not url:
url = url_for(request, 'murano')
token_id = request.user.token.token['id']
log.debug('Murano::Client <Url: {0}, TokenId: {1}>'.format(url, token_id))
return Client(endpoint=url, token=token_id)
def get_env_id_for_service(request, service_id):
environments = environments_list(request)
for environment in environments:
services = services_list(request, environment.id)
for service in services:
if service.id == service_id:
return environment.id
def get_status_message_for_service(request, service_id):
environment_id = get_env_id_for_service(request, service_id)
session_id = Session.get(request, environment_id)
reports = muranoclient(request).sessions.reports(environment_id,
session_id,
service_id)
result = 'Initialization.... \n'
for report in reports:
result += ' ' + str(report.text) + '\n'
return result
class Session(object):
@staticmethod
def get_or_create(request, environment_id):
"""
Gets id from already opened session for specified environment,
otherwise opens new session and returns it's id
:param request:
:param environment_id:
:return: Session Id
"""
#We store opened sessions for each environment in dictionary per user
sessions = request.session.get('sessions', {})
if environment_id in sessions:
id = sessions[environment_id]
else:
id = muranoclient(request).sessions.configure(environment_id).id
sessions[environment_id] = id
request.session['sessions'] = sessions
return id
@staticmethod
def get(request, environment_id):
"""
Gets id from already opened session for specified environment,
otherwise returns None
:param request:
:param environment_id:
:return: Session Id
"""
#We store opened sessions for each environment in dictionary per user
sessions = request.session.get('sessions', {})
return sessions[environment_id] if environment_id in sessions else None
def environments_list(request):
log.debug('Environment::List')
environments = muranoclient(request).environments.list()
log.debug('Environment::List {0}'.format(environments))
return environments
def environment_create(request, parameters):
#name is required param
name = parameters['name']
log.debug('Environment::Create <Name: {0}>'.format(name))
env = muranoclient(request).environments.create(name)
log.debug('Environment::Create {0}'.format(env))
return env
def environment_delete(request, environment_id):
log.debug('Environment::Delete <Id: {0}>'.format(environment_id))
muranoclient(request).environments.delete(environment_id)
def environment_get(request, environment_id):
log.debug('Environment::Get <Id: {0}>'.format(environment_id))
env = muranoclient(request).environments.get(environment_id)
log.debug('Environment::Get {0}'.format(env))
return env
def environment_deploy(request, environment_id):
session_id = Session.get(request, environment_id)
log.debug('Session::Get <Id: {0}>'.format(session_id))
env = muranoclient(request).sessions.deploy(environment_id, session_id)
log.debug('Environment::Deploy <EnvId: {0}, SessionId: {1}>'
''.format(environment_id, session_id))
return env
def get_service_client(request, service_type):
if service_type == 'Active Directory':
return muranoclient(request).activeDirectories
elif service_type == 'IIS':
return muranoclient(request).webServers
elif service_type == 'ASP.NET Application':
return muranoclient(request).aspNetApps
elif service_type == 'IIS Farm':
return muranoclient(request).webServerFarms
elif service_type == 'ASP.NET Farm':
return muranoclient(request).aspNetAppFarms
else:
raise NameError('Unknown service type: {0}'.format(service_type))
def services_list(request, environment_id):
services = []
session_id = Session.get(request, environment_id)
get_environment = muranoclient(request).environments.get
environment = get_environment(environment_id, session_id)
for service, instances in environment.services.iteritems():
services += instances
log.debug('Service::List')
return [bunch.bunchify(srv) for srv in services]
def service_list_by_type(request, environment_id, service_type):
session_id = Session.get(request, environment_id)
service_client = get_service_client(request, service_type)
instances = service_client.list(environment_id, session_id)
log.debug('Service::Instances::List')
return instances
def service_create(request, environment_id, parameters):
session_id = Session.get_or_create(request, environment_id)
service_client = get_service_client(request, parameters['service_type'])
service_client.create(environment_id, session_id, parameters)
log.debug('Service::Create {0}'.format(service_client))
return service_client
def service_delete(request, service_id):
log.debug('Service::Delete <SrvId: {0}>'.format(service_id))
environment_id = get_env_id_for_service(request, service_id)
service = service_get(request, service_id)
session_id = Session.get_or_create(request, environment_id)
service_client = get_service_client(request, service.service_type)
service_client.delete(environment_id, service_id, session_id)
def service_get(request, service_id):
environment_id = get_env_id_for_service(request, service_id)
services = services_list(request, environment_id)
for service in services:
if service.id == service_id:
log.debug('Service::Get {0}'.format(service))
return service

View File

@ -1,151 +1,157 @@
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import logging
import string
from django import forms
from django.utils.translation import ugettext_lazy as _
import re
from muranodashboard.panel import api
log = logging.getLogger(__name__)
class PasswordField(forms.CharField):
# Setup the Field
def __init__(self, label, *args, **kwargs):
super(PasswordField, self).__init__(min_length=7, required=True,
label=label,
widget=forms.PasswordInput(
render_value=False),
*args, **kwargs)
def clean(self, value):
# Setup Our Lists of Characters and Numbers
characters = list(string.letters)
special_characters = '!@#$%^&*()_+|\/.,~?><:{}'
numbers = [str(i) for i in range(10)]
# Assume False until Proven Otherwise
numCheck = False
charCheck = False
specCharCheck = False
# Loop until we Match
for char in value:
if not charCheck:
if char in characters:
charCheck = True
if not specCharCheck:
if char in special_characters:
specCharCheck = True
if not numCheck:
if char in numbers:
numCheck = True
if numCheck and charCheck and specCharCheck:
break
if not numCheck or not charCheck or not specCharCheck:
raise forms.ValidationError(u'Your password must include at least \
one letter, at least one number and \
at least one special character.')
return super(PasswordField, self).clean(value)
class WizardFormServiceType(forms.Form):
ad_service = ('Active Directory', 'Active Directory')
iis_service = ('IIS', 'Internet Information Services')
asp_service = ('ASP.NET Application', 'ASP.NET Application')
iis_farm_service = ('IIS Farm', 'Internet Information Services Web Farm')
asp_farm_service = ('ASP.NET Farm', 'ASP.NET Application Web Farm')
service = forms.ChoiceField(label=_('Service Type'),
choices=[
ad_service,
iis_service,
asp_service,
iis_farm_service,
asp_farm_service
])
class WizardFormConfiguration(forms.Form):
'The functions for this class will dynamically create in views.py'
pass
class WizardFormADConfiguration(forms.Form):
dc_name = forms.CharField(label=_('Domain Name'),
required=True)
dc_count = forms.IntegerField(label=_('Instance Count'),
required=True,
min_value=1,
max_value=100,
initial=1)
adm_password = PasswordField(_('Administrator password'))
recovery_password = PasswordField(_('Recovery password'))
def __init__(self, request, *args, **kwargs):
super(WizardFormADConfiguration, self).__init__(*args, **kwargs)
class WizardFormIISConfiguration(forms.Form):
iis_name = forms.CharField(label=_('Service Name'),
required=True)
adm_password = PasswordField(_('Administrator password'))
iis_domain = forms.ChoiceField(label=_('Member of the Domain'),
required=False)
def __init__(self, request, *args, **kwargs):
super(WizardFormIISConfiguration, self).__init__(*args, **kwargs)
link = request.__dict__['META']['HTTP_REFERER']
environment_id = re.search('murano/(\w+)', link).group(0)[7:]
domains = api.get_active_directories(request, environment_id)
self.fields['iis_domain'].choices = [("", "")] + \
[(domain.name, domain.name)
for domain in domains]
class WebFarmExtension(forms.Form):
instance_count = forms.IntegerField(label=_('Instance Count'),
required=True,
min_value=1,
max_value=10000,
initial=1)
lb_port = forms.IntegerField(label=_('Load Balancer port'),
required=True,
min_value=1,
max_value=65536,
initial=80)
class WizardFormAspNetAppConfiguration(WizardFormIISConfiguration):
repository = forms.CharField(label=_('Git repository'),
required=True)
class WizardFormIISFarmConfiguration(WizardFormIISConfiguration, WebFarmExtension):
pass
class WizardFormAspNetFarmConfiguration(WizardFormAspNetAppConfiguration, WebFarmExtension):
pass
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import logging
import string
from django import forms
from django.utils.translation import ugettext_lazy as _
import re
from muranodashboard.panel import api
log = logging.getLogger(__name__)
class PasswordField(forms.CharField):
# Setup the Field
def __init__(self, label, *args, **kwargs):
super(PasswordField, self).__init__(min_length=7, required=True,
label=label,
widget=forms.PasswordInput(
render_value=False),
*args, **kwargs)
def clean(self, value):
# Setup Our Lists of Characters and Numbers
characters = list(string.letters)
special_characters = '!@#$%^&*()_+|\/.,~?><:{}'
numbers = [str(i) for i in range(10)]
# Assume False until Proven Otherwise
numCheck = False
charCheck = False
specCharCheck = False
# Loop until we Match
for char in value:
if not charCheck:
if char in characters:
charCheck = True
if not specCharCheck:
if char in special_characters:
specCharCheck = True
if not numCheck:
if char in numbers:
numCheck = True
if numCheck and charCheck and specCharCheck:
break
if not numCheck or not charCheck or not specCharCheck:
raise forms.ValidationError(u'Your password must include at least \
one letter, at least one number and \
at least one special character.')
return super(PasswordField, self).clean(value)
class WizardFormServiceType(forms.Form):
ad_service = ('Active Directory', 'Active Directory')
iis_service = ('IIS', 'Internet Information Services')
asp_service = ('ASP.NET Application', 'ASP.NET Application')
iis_farm_service = ('IIS Farm', 'Internet Information Services Web Farm')
asp_farm_service = ('ASP.NET Farm', 'ASP.NET Application Web Farm')
service = forms.ChoiceField(label=_('Service Type'),
choices=[
ad_service,
iis_service,
asp_service,
iis_farm_service,
asp_farm_service
])
class WizardFormConfiguration(forms.Form):
#The functions for this class will dynamically create in views.py
pass
class WizardFormADConfiguration(forms.Form):
dc_name = forms.CharField(label=_('Domain Name'),
required=True)
dc_count = forms.IntegerField(label=_('Instance Count'),
required=True,
min_value=1,
max_value=100,
initial=1)
adm_password = PasswordField(_('Administrator password'))
recovery_password = PasswordField(_('Recovery password'))
def __init__(self, request, *args, **kwargs):
super(WizardFormADConfiguration, self).__init__(*args, **kwargs)
class WizardFormIISConfiguration(forms.Form):
iis_name = forms.CharField(label=_('Service Name'),
required=True)
adm_password = PasswordField(_('Administrator password'))
iis_domain = forms.ChoiceField(label=_('Member of the Domain'),
required=False)
def __init__(self, request, *args, **kwargs):
super(WizardFormIISConfiguration, self).__init__(*args, **kwargs)
link = request.__dict__['META']['HTTP_REFERER']
environment_id = re.search('murano/(\w+)', link).group(0)[7:]
ad = 'Active Directory'
domains = api.service_list_by_type(request, environment_id, ad)
self.fields['iis_domain'].choices = [("", "")] + \
[(domain.name, domain.name)
for domain in domains]
class WebFarmExtension(forms.Form):
instance_count = forms.IntegerField(label=_('Instance Count'),
required=True,
min_value=1,
max_value=10000,
initial=1)
lb_port = forms.IntegerField(label=_('Load Balancer port'),
required=True,
min_value=1,
max_value=65536,
initial=80)
class WizardFormAspNetAppConfiguration(WizardFormIISConfiguration):
repository = forms.CharField(label=_('Git repository'),
required=True)
class WizardFormIISFarmConfiguration(WizardFormIISConfiguration,
WebFarmExtension):
pass
class WizardFormAspNetFarmConfiguration(WizardFormAspNetAppConfiguration,
WebFarmExtension):
pass

View File

@ -1,21 +1,20 @@
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import horizon
from panel import Panel
project = horizon.get_dashboard('project')
# Copyright (c) 2013 Mirantis, Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
import horizon
from panel import Panel
project = horizon.get_dashboard('project')
project.register(Panel)

View File

@ -1,26 +1,26 @@
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import horizon
from django.utils.translation import ugettext_lazy as _
from openstack_dashboard.dashboards.project import dashboard
class Panel(horizon.Panel):
name = _("Environments")
slug = 'murano'
dashboard.Project.register(Panel)
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import horizon
from django.utils.translation import ugettext_lazy as _
from openstack_dashboard.dashboards.project import dashboard
class Panel(horizon.Panel):
name = _("Environments")
slug = 'murano'
dashboard.Project.register(Panel)

View File

@ -145,7 +145,7 @@ class UpdateServiceRow(tables.Row):
class EnvironmentsTable(tables.DataTable):
name = tables.Column('name',
link=('horizon:project:murano:services'),
link='horizon:project:murano:services',
verbose_name=_('Name'))
status = tables.Column('status', verbose_name=_('Status'),

View File

@ -1,56 +1,56 @@
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
from django.utils.translation import ugettext_lazy as _
from horizon import exceptions
from horizon import tabs
import logging
from muranodashboard.panel import api
LOG = logging.getLogger(__name__)
class OverviewTab(tabs.Tab):
name = _("Service")
slug = "_service"
template_name = '_services.html'
def get_context_data(self, request):
data = self.tab_group.kwargs['service']
return {"service_name": data.name,
"service_status": data.status,
"service_type": data.service_type,
"service_domain": data.domain}
class LogsTab(tabs.Tab):
name = _("Logs")
slug = "_logs"
template_name = '_service_logs.html'
def get_context_data(self, request):
service = self.tab_group.kwargs['service']
reports = api.get_status_message_for_service(request, service.id)
return {"reports": reports}
class ServicesTabs(tabs.TabGroup):
slug = "services_details"
tabs = (OverviewTab, LogsTab)
sticky = True
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
from django.utils.translation import ugettext_lazy as _
from horizon import exceptions
from horizon import tabs
import logging
from muranodashboard.panel import api
LOG = logging.getLogger(__name__)
class OverviewTab(tabs.Tab):
name = _("Service")
slug = "_service"
template_name = '_services.html'
def get_context_data(self, request):
data = self.tab_group.kwargs['service']
return {"service_name": data.name,
"service_status": data.status,
"service_type": data.service_type,
"service_domain": data.domain}
class LogsTab(tabs.Tab):
name = _("Logs")
slug = "_logs"
template_name = '_service_logs.html'
def get_context_data(self, request):
service = self.tab_group.kwargs['service']
reports = api.get_status_message_for_service(request, service.id)
return {"reports": reports}
class ServicesTabs(tabs.TabGroup):
slug = "services_details"
tabs = (OverviewTab, LogsTab)
sticky = True

View File

@ -22,15 +22,9 @@ from .forms import WizardFormServiceType, WizardFormConfiguration
VIEW_MOD = 'openstack_dashboard.dashboards.project.murano.views'
urlpatterns = patterns(VIEW_MOD,
url(r'^environments$', IndexView.as_view(), name='index'),
url(r'^create$',
Wizard.as_view([WizardFormServiceType,
WizardFormConfiguration]),
name='create'),
url(r'^create_environment$', CreateEnvironmentView.as_view(),
name='create_environment'),
url(r'^(?P<environment_id>[^/]+)/services$',
Services.as_view(), name='services'),
url(r'^(?P<environment_id>[^/]+)/(?P<service_id>[^/]+)$',
DetailServiceView.as_view(),
name='service_details'))
url(r'^environments$', IndexView.as_view(), name='index'),
url(r'^create$', Wizard.as_view([WizardFormServiceType, WizardFormConfiguration]), name='create'),
url(r'^create_environment$', CreateEnvironmentView.as_view(), name='create_environment'),
url(r'^(?P<environment_id>[^/]+)/services$', Services.as_view(), name='services'),
url(r'^services/(?P<service_id>[^/]+)$', DetailServiceView.as_view(), name='service_details')
)

View File

@ -14,6 +14,7 @@
# limitations under the License.
import logging
from muranoclient.common.exceptions import CommunicationError
import re
from django.views import generic
@ -146,10 +147,10 @@ class IndexView(tables.DataTableView):
def get_data(self):
try:
environments = api.environments_list(self.request)
except:
except CommunicationError:
environments = []
exceptions.handle(self.request,
_('Unable to retrieve environments list.'))
messages.error(self.request, 'Could not connect to Murano API '
'Service, check connection details.')
return environments

View File

@ -1,96 +1,96 @@
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import json
import logging
import re
from django.utils.text import normalize_newlines
from django.utils.translation import ugettext as _
from horizon import exceptions
from horizon import forms
from horizon import workflows
from muranodashboard.panel import api
LOG = logging.getLogger(__name__)
class SelectProjectUserAction(workflows.Action):
project_id = forms.ChoiceField(label=_("Project"))
user_id = forms.ChoiceField(label=_("User"))
def __init__(self, request, *args, **kwargs):
super(SelectProjectUserAction, self).__init__(request, *args, **kwargs)
# Set our project choices
projects = [(tenant.id, tenant.name)
for tenant in request.user.authorized_tenants]
self.fields['project_id'].choices = projects
# Set our user options
users = [(request.user.id, request.user.username)]
self.fields['user_id'].choices = users
class Meta:
name = _("Project & User")
# Unusable permission so this is always hidden. However, we
# keep this step in the workflow for validation/verification purposes.
permissions = ("!",)
class SelectProjectUser(workflows.Step):
action_class = SelectProjectUserAction
class ConfigureEnvironmentAction(workflows.Action):
name = forms.CharField(label=_("Environment Name"), required=True)
class Meta:
name = _("Environment")
help_text_template = "_data_center_help.html"
class ConfigureEnvironment(workflows.Step):
action_class = ConfigureEnvironmentAction
contibutes = ('name',)
def contribute(self, data, context):
if data:
context['name'] = data.get('name', '')
return context
class CreateEnvironment(workflows.Workflow):
slug = "create"
name = _("Create Environment")
finalize_button_name = _("Create")
success_message = _('Created environment "%s".')
failure_message = _('Unable to create environment "%s".')
success_url = "horizon:project:murano:index"
default_steps = (SelectProjectUser, ConfigureEnvironment)
def format_status_message(self, message):
name = self.context.get('name', 'noname')
return message % name
def handle(self, request, context):
try:
api.environment_create(request, context)
return True
except:
exceptions.handle(request)
return False
# Copyright (c) 2013 Mirantis Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.
import json
import logging
import re
from django.utils.text import normalize_newlines
from django.utils.translation import ugettext as _
from horizon import exceptions
from horizon import forms
from horizon import workflows
from muranodashboard.panel import api
LOG = logging.getLogger(__name__)
class SelectProjectUserAction(workflows.Action):
project_id = forms.ChoiceField(label=_("Project"))
user_id = forms.ChoiceField(label=_("User"))
def __init__(self, request, *args, **kwargs):
super(SelectProjectUserAction, self).__init__(request, *args, **kwargs)
# Set our project choices
projects = [(tenant.id, tenant.name)
for tenant in request.user.authorized_tenants]
self.fields['project_id'].choices = projects
# Set our user options
users = [(request.user.id, request.user.username)]
self.fields['user_id'].choices = users
class Meta:
name = _("Project & User")
# Unusable permission so this is always hidden. However, we
# keep this step in the workflow for validation/verification purposes.
permissions = ("!",)
class SelectProjectUser(workflows.Step):
action_class = SelectProjectUserAction
class ConfigureEnvironmentAction(workflows.Action):
name = forms.CharField(label=_("Environment Name"), required=True)
class Meta:
name = _("Environment")
help_text_template = "_data_center_help.html"
class ConfigureEnvironment(workflows.Step):
action_class = ConfigureEnvironmentAction
contibutes = ('name',)
def contribute(self, data, context):
if data:
context['name'] = data.get('name', '')
return context
class CreateEnvironment(workflows.Workflow):
slug = "create"
name = _("Create Environment")
finalize_button_name = _("Create")
success_message = _('Created environment "%s".')
failure_message = _('Unable to create environment "%s".')
success_url = "horizon:project:murano:index"
default_steps = (SelectProjectUser, ConfigureEnvironment)
def format_status_message(self, message):
name = self.context.get('name', 'noname')
return message % name
def handle(self, request, context):
try:
api.environment_create(request, context)
return True
except:
exceptions.handle(request)
return False

View File

@ -3,4 +3,5 @@ Django>=1.4,<1.5
anyjson
#Fix for bug https://bugs.launchpad.net/python-keystoneclient/+bug/1116740
backports.ssl_match_hostname
requests==0.14.2
requests==0.14.2
bunch