diff --git a/apps/assets/api.py b/apps/assets/api.py
index 334a7842e..aadebbd93 100644
--- a/apps/assets/api.py
+++ b/apps/assets/api.py
@@ -12,10 +12,12 @@ from django.shortcuts import get_object_or_404
from common.mixins import IDInFilterMixin
from common.utils import get_object_or_none, signer
-from .hands import IsSuperUser, IsAppUser, IsValidUser, get_user_granted_assets
+from .hands import IsSuperUser, IsAppUser, IsValidUser, \
+ get_user_granted_assets, push_users
from .models import AssetGroup, Asset, IDC, SystemUser, AdminUser
from . import serializers
from .tasks import update_assets_hardware_info
+from .utils import test_admin_user_connective_manual
class AssetViewSet(IDInFilterMixin, BulkModelViewSet):
@@ -97,6 +99,16 @@ class SystemUserUpdateApi(generics.RetrieveUpdateAPIView):
serializer_class = serializers.AssetUpdateSystemUserSerializer
permission_classes = (IsSuperUser,)
+ def patch(self, request, *args, **kwargs):
+ asset = self.get_object()
+ old_system_users = set(asset.system_users.all())
+ response = super(SystemUserUpdateApi, self).patch(request, *args, **kwargs)
+ system_users_new = set(asset.system_users.all())
+ system_users = system_users_new - old_system_users
+ system_users = [system_user._to_secret_json() for system_user in system_users]
+ push_users.delay([asset], system_users)
+ return response
+
class SystemUserUpdateAssetsApi(generics.RetrieveUpdateAPIView):
queryset = SystemUser.objects.all()
@@ -110,19 +122,6 @@ class SystemUserUpdateAssetGroupApi(generics.RetrieveUpdateAPIView):
permission_classes = (IsSuperUser,)
-# class IDCAssetsApi(generics.ListAPIView):
-# model = IDC
-# serializer_class = serializers.AssetSerializer
-#
-# def get(self, request, *args, **kwargs):
-# filter_kwargs = {self.lookup_field: self.kwargs[self.lookup_field]}
-# self.object = get_object_or_404(self.model, **filter_kwargs)
-# return super(IDCAssetsApi, self).get(request, *args, **kwargs)
-#
-# def get_queryset(self):
-# return self.object.assets.all()
-
-
class AssetListUpdateApi(IDInFilterMixin, ListBulkCreateUpdateDestroyAPIView):
queryset = Asset.objects.all()
serializer_class = serializers.AssetSerializer
@@ -154,5 +153,22 @@ class AssetRefreshHardwareView(generics.RetrieveAPIView):
def retrieve(self, request, *args, **kwargs):
asset_id = kwargs.get('pk')
asset = get_object_or_404(Asset, pk=asset_id)
- update_assets_hardware_info([asset])
- return super(AssetRefreshHardwareView, self).retrieve(request, *args, **kwargs)
+ summary = update_assets_hardware_info([asset])
+ if len(summary['failed']) == 0:
+ return super(AssetRefreshHardwareView, self).retrieve(request, *args, **kwargs)
+ else:
+ return Response('', status=502)
+
+
+class AssetAdminUserTestView(AssetRefreshHardwareView):
+ queryset = Asset.objects.all()
+ permission_classes = (IsSuperUser,)
+
+ def retrieve(self, request, *args, **kwargs):
+ asset_id = kwargs.get('pk')
+ asset = get_object_or_404(Asset, pk=asset_id)
+ result = test_admin_user_connective_manual([asset])
+ if result:
+ return Response('1')
+ else:
+ return Response('0', status=502)
diff --git a/apps/assets/hands.py b/apps/assets/hands.py
index a504019e5..7d9986156 100644
--- a/apps/assets/hands.py
+++ b/apps/assets/hands.py
@@ -14,4 +14,5 @@
from users.utils import AdminUserRequiredMixin
from users.permissions import IsAppUser, IsSuperUser, IsValidUser
from users.models import User, UserGroup
-from perms.utils import get_user_granted_assets
\ No newline at end of file
+from perms.utils import get_user_granted_assets
+from perms.tasks import push_users
\ No newline at end of file
diff --git a/apps/assets/models/asset.py b/apps/assets/models/asset.py
index 8a6d0bad6..02da386b0 100644
--- a/apps/assets/models/asset.py
+++ b/apps/assets/models/asset.py
@@ -76,7 +76,7 @@ class Asset(models.Model):
platform = models.CharField(max_length=128, null=True, blank=True, verbose_name='Platform')
os = models.CharField(max_length=128, null=True, blank=True, verbose_name=_('OS'))
- os_version = models.FloatField(null=True, blank=True, verbose_name=_('OS Version'))
+ os_version = models.CharField(max_length=16, null=True, blank=True, verbose_name=_('OS Version'))
os_arch = models.CharField(max_length=16, blank=True, null=True, verbose_name=_('OS Arch'))
hostname_raw = models.CharField(max_length=128, blank=True, null=True, verbose_name=_('Hostname raw'))
diff --git a/apps/assets/serializers.py b/apps/assets/serializers.py
index 50e7188f3..615220948 100644
--- a/apps/assets/serializers.py
+++ b/apps/assets/serializers.py
@@ -1,5 +1,6 @@
# -*- coding: utf-8 -*-
from django.utils.translation import ugettext_lazy as _
+from django.core.cache import cache
from rest_framework import viewsets, serializers, generics
from .models import AssetGroup, Asset, IDC, AdminUser, SystemUser
from common.mixins import IDInFilterMixin
@@ -117,6 +118,7 @@ class AssetSerializer(BulkSerializerMixin, serializers.ModelSerializer):
# system_users = SystemUserSerializer(many=True, read_only=True)
# admin_user = AdminUserSerializer(many=False, read_only=True)
hardware = serializers.SerializerMethodField()
+ is_online = serializers.SerializerMethodField()
class Meta(object):
model = Asset
@@ -130,6 +132,16 @@ class AssetSerializer(BulkSerializerMixin, serializers.ModelSerializer):
else:
return ''
+ @staticmethod
+ def get_is_online(obj):
+ hostname = obj.hostname
+ if cache.get(hostname) == '1':
+ return True
+ elif cache.get(hostname) == '0':
+ return False
+ else:
+ return 'Unknown'
+
def get_field_names(self, declared_fields, info):
fields = super(AssetSerializer, self).get_field_names(declared_fields, info)
fields.extend(['get_type_display', 'get_env_display'])
diff --git a/apps/assets/tasks.py b/apps/assets/tasks.py
index 06cc2a9b4..68b0cafca 100644
--- a/apps/assets/tasks.py
+++ b/apps/assets/tasks.py
@@ -2,6 +2,8 @@
from celery import shared_task
import json
+from django.core.cache import cache
+
from ops.tasks import run_AdHoc
from common.utils import get_object_or_none, capacity_convert, sum_capacity
from .models import Asset
@@ -43,7 +45,7 @@ def update_assets_hardware_info(assets):
___platform = info['ansible_system']
___os = info['ansible_distribution']
- ___os_version = float(info['ansible_distribution_version'])
+ ___os_version = info['ansible_distribution_version']
___os_arch = info['ansible_architecture']
___hostname_raw = info['ansible_hostname']
@@ -51,24 +53,28 @@ def update_assets_hardware_info(assets):
if k.startswith('___'):
setattr(asset, k.strip('_'), v)
asset.save()
+ return summary
@shared_task
-def test_admin_user_connective(assets=None):
- if None:
- assets = Asset.objects.filter(type__in=['Server', 'VM'])
- if not assets:
- return 'No asset get'
+def update_assets_hardware_period():
+ assets = Asset.objects.filter(type__in=['Server', 'VM'])
+ update_assets_hardware_info(assets)
+
+
+@shared_task
+def test_admin_user_connective_period():
+ assets = Asset.objects.filter(type__in=['Server', 'VM'])
task_tuple = (
('ping', ''),
)
- summary, result = run_AdHoc(task_tuple, assets, record=False)
- return summary, result
+ summary, _ = run_AdHoc(task_tuple, assets, record=False)
+ for i in summary['success']:
+ cache.set(i, '1', 2*60*60*60)
+
+ for i in summary['failed']:
+ cache.set(i, '0', 60*60*60)
+ return summary
+
-def get_assets_hardware_info(assets):
- task_tuple = (
- ('setup', ''),
- )
- task = run_AdHoc.delay(task_tuple, assets, record=False)
- return task
\ No newline at end of file
diff --git a/apps/assets/templates/assets/asset_detail.html b/apps/assets/templates/assets/asset_detail.html
index c56116d61..18ce868cc 100644
--- a/apps/assets/templates/assets/asset_detail.html
+++ b/apps/assets/templates/assets/asset_detail.html
@@ -188,7 +188,7 @@
{% trans 'Rrefresh hardware' %}: |
-
+
|
@@ -196,19 +196,10 @@
{% trans 'Test admin user' %}: |
-
+
|
-
- {% trans 'Test system pingpong' %}: |
-
-
-
-
- |
-
-
@@ -453,8 +444,17 @@ $(document).ready(function () {
var the_url = '{% url "api-assets:asset-detail" pk=99991937 %}'.replace('99991937', uid);
var redirect_url = "{% url 'assets:asset-list' %}";
objectDelete($this, name, the_url, redirect_url);
-}).on('click', '.btn-refresh-asset', function () {
+}).on('click', '#btn_refresh_asset', function () {
+ alert('请等待几秒, 等待完成');
refreshAssetHardware()
+}).on('click', '#btn_test_admin_user', function () {
+ $.ajax({
+ url: '{% url "api-assets:asset-admin-user-test" pk=asset.id %}'
+ }).done(function (data, textStatue, jqXHR) {
+ toastr.success('Success')
+ }).fail(function (data, textStaue, errorThrown) {
+ toastr.error('Error')
+ })
})
diff --git a/apps/assets/templates/assets/asset_list.html b/apps/assets/templates/assets/asset_list.html
index e47f48428..9bf9f122f 100644
--- a/apps/assets/templates/assets/asset_list.html
+++ b/apps/assets/templates/assets/asset_list.html
@@ -121,7 +121,9 @@ $(document).ready(function(){
}
}},
{targets: 8, createdCell: function (td, cellData) {
- if (!cellData) {
+ if (cellData == 'Unknown'){
+ $(td).html('')
+ } else if (!cellData) {
$(td).html('')
} else {
$(td).html('')
@@ -136,7 +138,7 @@ $(document).ready(function(){
ajax_url: '{% url "api-assets:asset-list" %}',
columns: [{data: "id"}, {data: "hostname" }, {data: "ip" }, {data: "port" },
{data: "get_type_display" }, {data: "get_env_display"}, {data: "hardware"},
- {data: "is_active" }, {data: "is_active"}, {data: "id" }],
+ {data: "is_active" }, {data: "is_online"}, {data: "id" }],
op_html: $('#actions').html()
};
var table = jumpserver.initDataTable(options);
diff --git a/apps/assets/urls/api_urls.py b/apps/assets/urls/api_urls.py
index ec1c8433c..f54b0a0e6 100644
--- a/apps/assets/urls/api_urls.py
+++ b/apps/assets/urls/api_urls.py
@@ -16,7 +16,6 @@ router.register(r'v1/system-user', api.SystemUserViewSet, 'system-user')
urlpatterns = [
url(r'^v1/assets_bulk/$', api.AssetListUpdateApi.as_view(), name='asset-bulk-update'),
- # url(r'^v1/idc/(?P[0-9]+)/assets/$', api.IDCAssetsApi.as_view(), name='api-idc-assets'),
url(r'^v1/system-user/(?P[0-9]+)/auth-info/', api.SystemUserAuthInfoApi.as_view(),
name='system-user-auth-info'),
url(r'^v1/assets/(?P\d+)/groups/$',
@@ -24,6 +23,8 @@ urlpatterns = [
url(r'^v1/assets/(?P\d+)/refresh/$',
api.AssetRefreshHardwareView.as_view(), name='asset-refresh'),
+ url(r'^v1/assets/(?P\d+)/admin-user-test/$',
+ api.AssetAdminUserTestView.as_view(), name='asset-admin-user-test'),
url(r'^v1/assets/(?P\d+)/system-users/$',
api.SystemUserUpdateApi.as_view(), name='asset-update-system-users'),
diff --git a/apps/assets/utils.py b/apps/assets/utils.py
index cd064e942..e67412615 100644
--- a/apps/assets/utils.py
+++ b/apps/assets/utils.py
@@ -1,3 +1,17 @@
# ~*~ coding: utf-8 ~*~
#
+from ops.utils import run_AdHoc
+
+
+def test_admin_user_connective_manual(asset):
+ if not isinstance(asset, list):
+ asset = [asset]
+ task_tuple = (
+ ('ping', ''),
+ )
+ summary, _ = run_AdHoc(task_tuple, asset, record=False)
+ if len(summary['failed']) != 0:
+ return False
+ else:
+ return True
diff --git a/apps/common/celery.py b/apps/common/celery.py
index 51de45349..3094351e5 100644
--- a/apps/common/celery.py
+++ b/apps/common/celery.py
@@ -5,6 +5,7 @@ import os
from datetime import timedelta
from celery import Celery
+from celery.schedules import crontab
# set the default Django settings module for the 'celery' program.
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'jumpserver.settings')
@@ -19,3 +20,17 @@ app.config_from_object('django.conf:settings')
app.autodiscover_tasks(lambda: [app_config.split('.')[0]
for app_config in settings.INSTALLED_APPS])
+app.conf.update(
+ CELERYBEAT_SCHEDULE={
+ 'refresh-asset-hardware-info': {
+ 'task': 'assets.tasks.update_assets_hardware_period',
+ 'schedule': 60*60*60*24,
+ 'args': (),
+ },
+ 'test-admin-user-connective': {
+ 'task': 'assets.tasks.test_admin_user_connective_period',
+ 'schedule': 60*60*60,
+ 'args': (),
+ }
+ }
+)
diff --git a/apps/jumpserver/settings.py b/apps/jumpserver/settings.py
index ed919cb47..7f8a6289b 100644
--- a/apps/jumpserver/settings.py
+++ b/apps/jumpserver/settings.py
@@ -108,6 +108,10 @@ TEMPLATES = [
LOGIN_REDIRECT_URL = reverse_lazy('index')
LOGIN_URL = reverse_lazy('users:login')
+SESSION_COOKIE_DOMAIN = CONFIG.SESSION_COOKIE_DOMAIN or None
+CSRF_COOKIE_DOMAIN = CONFIG.CSRF_COOKIE_DOMAIN or None
+SESSION_COOKIE_AGE = CONFIG.SESSION_COOKIE_AGE or 3600*24
+
# Database
# https://docs.djangoproject.com/en/1.10/ref/settings/#databases
diff --git a/apps/ops/utils.py b/apps/ops/utils.py
index 0c3cbbc99..b27c81671 100644
--- a/apps/ops/utils.py
+++ b/apps/ops/utils.py
@@ -27,7 +27,8 @@ def run_AdHoc(task_tuple, assets,
:param pattern:
:param record:
:param verbose:
- :return:
+ :return: summary: {'success': [], 'failed': [{'192.168.1.1': 'msg'}]}
+ result: {'contacted': {'hostname': [{''}, {''}], 'dark': []}
"""
if not assets:
diff --git a/apps/static/js/jumpserver.js b/apps/static/js/jumpserver.js
index 2ad48ec86..c9b091338 100644
--- a/apps/static/js/jumpserver.js
+++ b/apps/static/js/jumpserver.js
@@ -149,7 +149,7 @@ function getCookie(name) {
// Does this cookie string begin with the name we want?
if (cookie.substring(0, name.length + 1) === (name + '=')) {
cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
- break;
+ // break;
}
}
}
diff --git a/apps/users/views/login.py b/apps/users/views/login.py
index fcbdac30c..115db0f1a 100644
--- a/apps/users/views/login.py
+++ b/apps/users/views/login.py
@@ -69,7 +69,7 @@ class UserLogoutView(TemplateView):
def get(self, request, *args, **kwargs):
auth_logout(request)
- return super(UserLogoutView, self).get(request)
+ return super(UserLogoutView, self).get(request, *args, **kwargs)
def get_context_data(self, **kwargs):
context = {
@@ -201,9 +201,4 @@ class UserFirstLoginView(LoginRequiredMixin, SessionWizardView):
form = super(UserFirstLoginView, self).get_form(step, data, files)
form.instance = self.request.user
- if step is None:
- step = self.steps.current
-
- # if step == '1':
- # form.instance = self.request.user
return form
diff --git a/config_example.py b/config_example.py
index cbe79aa8b..92a2bd43b 100644
--- a/config_example.py
+++ b/config_example.py
@@ -72,6 +72,11 @@ class Config:
# Api token expiration when create
TOKEN_EXPIRATION = 3600
+ # Session and csrf domain settings
+ SESSION_COOKIE_DOMAIN = '.jms.com'
+ CSRF_COOKIE_DOMAIN = '.jms.com'
+ SESSION_COOKIE_AGE = 3600*24
+
# Email SMTP setting, we only support smtp send mail
# EMAIL_HOST = 'smtp.qq.com'
# EMAIL_PORT = 25
diff --git a/requirements/rpm_requirements.txt b/requirements/rpm_requirements.txt
index 3853d8419..03d5e2c92 100644
--- a/requirements/rpm_requirements.txt
+++ b/requirements/rpm_requirements.txt
@@ -1 +1 @@
-libtiff-devel libjpeg-devel libzip-devel freetype-devel lcms2-devel libwebp-devel tcl-devel tk-devel
\ No newline at end of file
+libtiff-devel libjpeg-devel libzip-devel freetype-devel lcms2-devel libwebp-devel tcl-devel tk-devel sshpass
diff --git a/run_server.py b/run_server.py
index 77cda4139..2af0a20ca 100644
--- a/run_server.py
+++ b/run_server.py
@@ -31,7 +31,7 @@ def start_celery():
os.environ.setdefault('C_FORCE_ROOT', '1')
os.environ.setdefault('PYTHONOPTIMIZE', '1')
print('start celery')
- subprocess.call('celery -A common worker -s /tmp/celerybeat-schedule -l debug', shell=True)
+ subprocess.call('celery -A common worker -B -s /tmp/celerybeat-schedule -l debug', shell=True)
def main():