Skip to content
Projects
Groups
Snippets
Help
Loading...
Sign in
Toggle navigation
J
jumpserver
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
ops
jumpserver
Commits
f00da207
Commit
f00da207
authored
Sep 19, 2016
by
xiaoyu
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
user-group delete implement
parent
4e2a41f4
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
126 additions
and
30 deletions
+126
-30
mixins.py
apps/common/mixins.py
+38
-0
api.py
apps/users/api.py
+6
-1
models.py
apps/users/models.py
+24
-22
serializers.py
apps/users/serializers.py
+7
-1
user_group_list.html
apps/users/templates/users/user_group_list.html
+48
-3
urls.py
apps/users/urls.py
+3
-3
No files found.
apps/common/mixins.py
0 → 100644
View file @
f00da207
# coding: utf-8
from
django.db
import
models
from
django.utils.timezone
import
now
from
django.utils.translation
import
ugettext_lazy
as
_
class
NoDeleteQuerySet
(
models
.
query
.
QuerySet
):
def
delete
(
self
):
return
self
.
update
(
is_discard
=
True
,
discard_time
=
now
())
class
NoDeleteManager
(
models
.
Manager
):
def
get_all
(
self
):
return
NoDeleteQuerySet
(
self
.
model
,
using
=
self
.
_db
)
def
get_queryset
(
self
):
return
NoDeleteQuerySet
(
self
.
model
,
using
=
self
.
_db
)
.
filter
(
is_discard
=
False
)
def
get_deleted
(
self
):
return
NoDeleteQuerySet
(
self
.
model
,
using
=
self
.
_db
)
.
filter
(
is_discard
=
True
)
class
NoDeleteModelMixin
(
models
.
Model
):
is_discard
=
models
.
BooleanField
(
verbose_name
=
_
(
"is discard"
),
default
=
False
)
discard_time
=
models
.
DateTimeField
(
verbose_name
=
_
(
"discard time"
),
null
=
True
,
blank
=
True
)
objects
=
NoDeleteManager
()
class
Meta
:
abstract
=
True
def
delete
(
self
):
self
.
is_discard
=
True
self
.
discard_time
=
now
()
return
self
.
save
()
apps/users/api.py
View file @
f00da207
...
...
@@ -6,7 +6,7 @@ import logging
from
rest_framework
import
generics
from
.serializers
import
UserSerializer
,
UserGroupSerializer
,
UserAttributeSerializer
,
UserGroupEditSerializer
,
\
UserPKUpdateSerializer
GroupEditSerializer
,
UserPKUpdateSerializer
from
.models
import
User
,
UserGroup
...
...
@@ -87,3 +87,8 @@ class UserUpdatePKApi(generics.UpdateAPIView):
user
=
self
.
get_object
()
user
.
private_key
=
serializer
.
validated_data
[
'_public_key'
]
user
.
save
()
class
GroupDeleteApi
(
generics
.
DestroyAPIView
):
queryset
=
UserGroup
.
objects
.
all
()
serializer_class
=
GroupEditSerializer
apps/users/models.py
View file @
f00da207
...
...
@@ -4,19 +4,22 @@ from __future__ import unicode_literals
from
django.conf
import
settings
from
django.contrib.auth.hashers
import
make_password
from
django.utils
import
timezone
from
django.db
import
models
from
django.contrib.auth.models
import
AbstractUser
from
django.core
import
signing
from
django.db
import
models
,
IntegrityError
from
django.db.models.signals
import
post_save
from
django.dispatch
import
receiver
from
django.
utils
import
timezone
from
django.
db
import
IntegrityError
from
django.utils.translation
import
ugettext_lazy
as
_
from
django.core
import
signing
from
rest_framework.authtoken.models
import
Token
from
common.utils
import
encrypt
,
decrypt
,
date_expired_default
from
common.mixins
import
NoDeleteModelMixin
class
UserGroup
(
models
.
Model
):
class
UserGroup
(
NoDeleteModelMixin
):
name
=
models
.
CharField
(
max_length
=
100
,
unique
=
True
,
verbose_name
=
_
(
'Name'
))
comment
=
models
.
TextField
(
blank
=
True
,
verbose_name
=
_
(
'Comment'
))
date_created
=
models
.
DateTimeField
(
auto_now_add
=
True
)
...
...
@@ -30,14 +33,20 @@ class UserGroup(models.Model):
return
True
return
False
def
delete
(
self
):
if
self
.
name
!=
'Default'
:
self
.
users
.
clear
()
return
super
(
UserGroup
,
self
)
.
delete
()
return
True
class
Meta
:
db_table
=
'user
_
group'
db_table
=
'user
-
group'
@classmethod
def
initial
(
cls
):
group
_or_create
=
cls
.
objects
.
get_or_create
(
name
=
'Default'
,
comment
=
'Default user group for all user'
,
created_by
=
'System'
)
return
group
_or_create
[
0
]
group
,
created
=
cls
.
objects
.
get_or_create
(
name
=
'Default'
,
comment
=
'Default user group for all user'
,
created_by
=
'System'
)
return
group
@classmethod
def
generate_fake
(
cls
,
count
=
100
):
...
...
@@ -48,8 +57,7 @@ class UserGroup(models.Model):
for
i
in
range
(
count
):
group
=
cls
(
name
=
forgery_py
.
name
.
full_name
(),
comment
=
forgery_py
.
lorem_ipsum
.
sentence
(),
created_by
=
choice
(
User
.
objects
.
all
())
.
username
)
created_by
=
choice
(
User
.
objects
.
all
())
.
username
)
try
:
group
.
save
()
except
IntegrityError
:
...
...
@@ -76,11 +84,10 @@ class User(AbstractUser):
_private_key
=
models
.
CharField
(
max_length
=
5000
,
blank
=
True
,
verbose_name
=
_
(
'ssh private key'
))
_public_key
=
models
.
CharField
(
max_length
=
1000
,
blank
=
True
,
verbose_name
=
_
(
'ssh public key'
))
comment
=
models
.
TextField
(
max_length
=
200
,
blank
=
True
,
verbose_name
=
_
(
'Comment'
))
is_first_login
=
models
.
BooleanField
(
default
=
Tru
e
)
is_first_login
=
models
.
BooleanField
(
default
=
Fals
e
)
date_expired
=
models
.
DateTimeField
(
default
=
date_expired_default
,
blank
=
True
,
null
=
True
,
verbose_name
=
_
(
'Date expired'
))
created_by
=
models
.
CharField
(
max_length
=
30
,
default
=
''
,
verbose_name
=
_
(
'Created by'
))
is_public_key_valid
=
models
.
BooleanField
(
default
=
False
)
@property
def
password_raw
(
self
):
...
...
@@ -144,17 +151,13 @@ class User(AbstractUser):
pass
def
save
(
self
,
*
args
,
**
kwargs
):
# If user not set name, it's default equal username
if
not
self
.
name
:
self
.
name
=
self
.
username
super
(
User
,
self
)
.
save
(
*
args
,
**
kwargs
)
# Set user default group 'All'
# Todo: It's have bug
# Add the current user to the default group.
group
=
UserGroup
.
initial
()
if
group
not
in
self
.
groups
.
all
():
self
.
groups
.
add
(
group
)
# super(User, self).save(*args, **kwargs)
self
.
groups
.
add
(
group
)
@property
def
private_token
(
self
):
...
...
@@ -227,8 +230,7 @@ class User(AbstractUser):
role
=
choice
(
dict
(
User
.
ROLE_CHOICES
)
.
keys
()),
wechat
=
forgery_py
.
internet
.
user_name
(
True
),
comment
=
forgery_py
.
lorem_ipsum
.
sentence
(),
created_by
=
choice
(
cls
.
objects
.
all
())
.
username
,
)
created_by
=
choice
(
cls
.
objects
.
all
())
.
username
)
try
:
user
.
save
()
except
IntegrityError
:
...
...
@@ -240,13 +242,13 @@ class User(AbstractUser):
def
init_all_models
():
for
model
in
(
UserGroup
,
User
):
if
hasattr
(
model
,
b
'initial'
):
if
hasattr
(
model
,
'initial'
):
model
.
initial
()
def
generate_fake
():
for
model
in
(
UserGroup
,
User
):
if
hasattr
(
model
,
b
'generate_fake'
):
if
hasattr
(
model
,
'generate_fake'
):
model
.
generate_fake
()
...
...
apps/users/serializers.py
View file @
f00da207
# -*- coding: utf-8 -*-
#
from
django.utils.translation
import
ugettext_lazy
as
_
from
rest_framework
import
serializers
...
...
@@ -27,6 +26,13 @@ class UserGroupSerializer(serializers.ModelSerializer):
fields
=
'__all__'
class
GroupEditSerializer
(
serializers
.
ModelSerializer
):
class
Meta
:
model
=
UserGroup
fields
=
[
'id'
,
'name'
,
'comment'
,
'date_created'
,
'created_by'
]
class
UserAttributeSerializer
(
serializers
.
ModelSerializer
):
class
Meta
:
...
...
apps/users/templates/users/user_group_list.html
View file @
f00da207
{% extends '_list_base.html' %}
{% load i18n %}
{% load i18n static %}
{% block custom_head_css_js %}
<link
href=
"{% static "
css
/
plugins
/
sweetalert
/
sweetalert
.
css
"
%}"
rel=
"stylesheet"
>
<script
src=
"{% static "
js
/
plugins
/
sweetalert
/
sweetalert
.
min
.
js
"
%}"
></script>
{% endblock %}
{% block content_left_head %}
<a
href=
"{% url 'users:user-group-create' %}"
class=
"btn btn-sm btn-primary "
>
{% trans "Add User Group" %}
</a>
{% endblock %}
...
...
@@ -30,8 +35,9 @@
<td
class=
"text-center"
>
999
</td>
<th
class=
"text-center"
>
{{ user_group.comment|truncatewords:8 }}
</th>
<td
class=
"text-center"
>
<a
href=
"{% url 'users:user-group-update' pk=user_group.id %}"
class=
"btn btn-xs btn-info"
>
编辑
</a>
<a
href=
"{% url 'users:user-group-delete' pk=user_group.id %}"
class=
"btn btn-xs btn-danger del"
>
删除
</a>
<a
href=
"{% url 'users:user-group-update' pk=user_group.id %}"
class=
"btn btn-xs btn-info"
>
{% trans "Edit" %}
</a>
<a
href=
"javascript:void(0)"
data-gid=
"{{ user_group.id }}"
class=
"btn btn-xs btn-danger del {% ifequal user_group.name 'Default' %}disabled{% else %}btn_delete_user_group{% endifequal %}"
>
{% trans "Delete" %}
</a>
</td>
</tr>
{% endfor %}
...
...
@@ -52,3 +58,42 @@
</form>
{% endblock %}
{% block custom_foot_js %}
<script>
$
(
document
).
on
(
'click'
,
'.btn_delete_user_group'
,
function
(){
var
$this
=
$
(
this
);
function
doDelete
()
{
var
group_id
=
$this
.
data
(
'gid'
);
var
the_url
=
"{% url 'users:user-group-delete-api' 99991937 %}"
.
replace
(
'99991937'
,
group_id
);
var
body
=
{};
var
success
=
function
()
{
var
msg
=
"{% trans 'Group Deleted.' %}"
;
swal
(
"{% trans 'Group Delete' %}"
,
msg
,
"success"
);
$this
.
closest
(
'tr.gradeX'
).
remove
();
};
var
fail
=
function
()
{
var
msg
=
"{% trans 'Group Deleting failed.' %}"
;
swal
(
"{% trans 'Group Delete' %}"
,
msg
,
"error"
);
}
APIUpdateAttr
({
url
:
the_url
,
body
:
JSON
.
stringify
(
body
),
method
:
'DELETE'
,
success
:
success
,
error
:
fail
});
}
swal
({
title
:
"{% trans 'Are you sure?' %}"
,
text
:
"{% trans 'This will delete the selected group, but will not remove any user in this group.' %}"
,
type
:
"warning"
,
showCancelButton
:
true
,
confirmButtonColor
:
"#DD6B55"
,
confirmButtonText
:
"{% trans 'Confirm' %}"
,
closeOnConfirm
:
false
},
function
()
{
doDelete
();
});
})
</script>
{% endblock %}
apps/users/urls.py
View file @
f00da207
...
...
@@ -22,8 +22,7 @@ urlpatterns = [
name
=
'user-asset-permission-create'
),
url
(
r'^user/(?P<pk>[0-9]+)/granted-asset'
,
views
.
UserGrantedAssetView
.
as_view
(),
name
=
'user-granted-asset'
),
url
(
r'^user/(?P<pk>[0-9]+)/login-history'
,
views
.
UserDetailView
.
as_view
(),
name
=
'user-login-history'
),
url
(
r'^first-login/$'
,
views
.
UserFirstLoginView
.
as_view
(),
name
=
'user-first-login'
),
url
(
r'^user/(?P<pk>[0-9]+)/assets-perm$'
,
views
.
UserDetailView
.
as_view
(),
name
=
'user-detail'
),
url
(
r'^first-login/$'
,
views
.
UserFirstLoginView
.
as_view
(),
name
=
'user-first-login'
),
url
(
r'^user/(?P<pk>[0-9]+)/assets-perm$'
,
views
.
UserDetailView
.
as_view
(),
name
=
'user-detail'
),
url
(
r'^user/create$'
,
views
.
UserCreateView
.
as_view
(),
name
=
'user-create'
),
url
(
r'^user/(?P<pk>[0-9]+)/update$'
,
views
.
UserUpdateView
.
as_view
(),
name
=
'user-update'
),
url
(
r'^user/(?P<pk>[0-9]+)/delete$'
,
views
.
UserDeleteView
.
as_view
(),
name
=
'user-delete'
),
...
...
@@ -31,7 +30,6 @@ urlpatterns = [
url
(
r'^user-group/(?P<pk>[0-9]+)$'
,
views
.
UserGroupDetailView
.
as_view
(),
name
=
'user-group-detail'
),
url
(
r'^user-group/create$'
,
views
.
UserGroupCreateView
.
as_view
(),
name
=
'user-group-create'
),
url
(
r'^user-group/(?P<pk>[0-9]+)/update$'
,
views
.
UserGroupUpdateView
.
as_view
(),
name
=
'user-group-update'
),
url
(
r'^user-group/(?P<pk>[0-9]+)/delete$'
,
views
.
UserGroupDeleteView
.
as_view
(),
name
=
'user-group-delete'
),
]
...
...
@@ -49,4 +47,6 @@ urlpatterns += [
api
.
UserGroupDetailDeleteUpdateApi
.
as_view
(),
name
=
'user-group-detail-api'
),
url
(
r'^v1/user-groups/(?P<pk>[0-9]+)/edit$'
,
api
.
UserGroupEditApi
.
as_view
(),
name
=
'user-group-edit-api'
),
url
(
r'^v1/user-groups/(?P<pk>[0-9]+)/delete/$'
,
api
.
GroupDeleteApi
.
as_view
(),
name
=
'user-group-delete-api'
),
]
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment