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
d247e49b
Commit
d247e49b
authored
Apr 02, 2018
by
ibuler
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
[Update] 修改celery位置
parent
a4c843ff
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
26 changed files
with
116 additions
and
268 deletions
+116
-268
api.py
apps/common/api.py
+2
-31
models.py
apps/common/models.py
+0
-9
api_urls.py
apps/common/urls/api_urls.py
+0
-1
view_urls.py
apps/common/urls/view_urls.py
+0
-2
views.py
apps/common/views.py
+0
-15
django.mo
apps/i18n/zh/LC_MESSAGES/django.mo
+0
-0
django.po
apps/i18n/zh/LC_MESSAGES/django.po
+0
-0
api.py
apps/ops/api.py
+12
-15
apps.py
apps/ops/apps.py
+4
-0
__init__.py
apps/ops/celery/__init__.py
+0
-1
signal_handler.py
apps/ops/celery/signal_handler.py
+34
-30
__init__.py
apps/ops/models/__init__.py
+6
-0
adhoc.py
apps/ops/models/adhoc.py
+5
-6
celery.py
apps/ops/models/celery.py
+36
-0
tasks.py
apps/ops/tasks.py
+0
-1
adhoc_history_detail.html
apps/ops/templates/ops/adhoc_history_detail.html
+1
-1
adhoc_history_output.html
apps/ops/templates/ops/adhoc_history_output.html
+0
-37
celery_task_log.html
apps/ops/templates/ops/celery_task_log.html
+1
-1
celery_task_output.html
apps/ops/templates/ops/celery_task_output.html
+0
-94
task_adhoc.html
apps/ops/templates/ops/task_adhoc.html
+3
-0
task_detail.html
apps/ops/templates/ops/task_detail.html
+1
-1
task_history.html
apps/ops/templates/ops/task_history.html
+3
-0
task_list.html
apps/ops/templates/ops/task_list.html
+2
-2
api_urls.py
apps/ops/urls/api_urls.py
+1
-1
view_urls.py
apps/ops/urls/view_urls.py
+1
-2
views.py
apps/ops/views.py
+4
-18
No files found.
apps/common/api.py
View file @
d247e49b
# -*- coding: utf-8 -*-
# -*- coding: utf-8 -*-
#
#
import
os
import
json
import
json
import
uuid
from
django.core.cache
import
cache
from
rest_framework.generics
import
RetrieveAPIView
from
rest_framework.views
import
Response
,
APIView
from
rest_framework.views
import
Response
,
APIView
from
ldap3
import
Server
,
Connection
from
ldap3
import
Server
,
Connection
from
django.core.mail
import
get_connection
,
send_mail
from
django.core.mail
import
get_connection
,
send_mail
from
django.utils.translation
import
ugettext_lazy
as
_
from
django.utils.translation
import
ugettext_lazy
as
_
from
django.conf
import
settings
from
django.conf
import
settings
from
.permissions
import
IsSuperUser
,
IsAppUser
from
.permissions
import
IsSuperUser
from
.serializers
import
MailTestSerializer
,
LDAPTestSerializer
from
.serializers
import
MailTestSerializer
,
LDAPTestSerializer
from
.celery
import
FINISHED
from
.const
import
FILE_END_GUARD
,
celery_task_pre_key
class
MailTestingAPI
(
APIView
):
class
MailTestingAPI
(
APIView
):
...
@@ -112,27 +106,4 @@ class DjangoSettingsAPI(APIView):
...
@@ -112,27 +106,4 @@ class DjangoSettingsAPI(APIView):
return
Response
(
configs
)
return
Response
(
configs
)
class
CeleryTaskLogApi
(
APIView
):
permission_classes
=
(
IsSuperUser
,)
buff_size
=
1024
*
10
end
=
False
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
task_id
=
kwargs
.
get
(
'pk'
)
info
=
cache
.
get
(
celery_task_pre_key
+
task_id
,
{})
log_path
=
info
.
get
(
"log_path"
)
mark
=
request
.
query_params
.
get
(
"mark"
)
or
str
(
uuid
.
uuid4
())
if
not
log_path
or
not
os
.
path
.
isfile
(
log_path
):
return
Response
({
"data"
:
_
(
"Waiting ..."
)},
status
=
203
)
with
open
(
log_path
,
'r'
)
as
f
:
offset
=
cache
.
get
(
mark
,
0
)
f
.
seek
(
offset
)
data
=
f
.
read
(
self
.
buff_size
)
.
replace
(
'
\n
'
,
'
\r\n
'
)
mark
=
str
(
uuid
.
uuid4
())
cache
.
set
(
mark
,
f
.
tell
(),
5
)
if
data
==
''
and
info
[
"status"
]
==
FINISHED
:
self
.
end
=
True
return
Response
({
"data"
:
data
,
'end'
:
self
.
end
,
'mark'
:
mark
})
apps/common/models.py
View file @
d247e49b
...
@@ -80,11 +80,3 @@ class Setting(models.Model):
...
@@ -80,11 +80,3 @@ class Setting(models.Model):
class
Meta
:
class
Meta
:
db_table
=
"settings"
db_table
=
"settings"
class
CeleryTask
(
models
.
Model
):
id
=
models
.
UUIDField
()
name
=
models
.
CharField
(
max_length
=
1024
)
status
=
models
.
CharField
(
max_length
=
128
)
date_published
=
models
.
DateTimeField
(
auto_now_add
=
True
)
date_start
=
models
.
DateTimeField
(
null
=
True
)
date_finished
=
models
.
DateTimeField
(
null
=
True
)
\ No newline at end of file
apps/common/urls/api_urls.py
View file @
d247e49b
...
@@ -10,5 +10,4 @@ urlpatterns = [
...
@@ -10,5 +10,4 @@ urlpatterns = [
url
(
r'^v1/mail/testing/$'
,
api
.
MailTestingAPI
.
as_view
(),
name
=
'mail-testing'
),
url
(
r'^v1/mail/testing/$'
,
api
.
MailTestingAPI
.
as_view
(),
name
=
'mail-testing'
),
url
(
r'^v1/ldap/testing/$'
,
api
.
LDAPTestingAPI
.
as_view
(),
name
=
'ldap-testing'
),
url
(
r'^v1/ldap/testing/$'
,
api
.
LDAPTestingAPI
.
as_view
(),
name
=
'ldap-testing'
),
url
(
r'^v1/django-settings/$'
,
api
.
DjangoSettingsAPI
.
as_view
(),
name
=
'django-settings'
),
url
(
r'^v1/django-settings/$'
,
api
.
DjangoSettingsAPI
.
as_view
(),
name
=
'django-settings'
),
url
(
r'^v1/celery/task/(?P<pk>[0-9a-zA-Z\-]{36})/log/$'
,
api
.
CeleryTaskLogApi
.
as_view
(),
name
=
'celery-task-log'
),
]
]
apps/common/urls/view_urls.py
View file @
d247e49b
...
@@ -11,6 +11,4 @@ urlpatterns = [
...
@@ -11,6 +11,4 @@ urlpatterns = [
url
(
r'^email/$'
,
views
.
EmailSettingView
.
as_view
(),
name
=
'email-setting'
),
url
(
r'^email/$'
,
views
.
EmailSettingView
.
as_view
(),
name
=
'email-setting'
),
url
(
r'^ldap/$'
,
views
.
LDAPSettingView
.
as_view
(),
name
=
'ldap-setting'
),
url
(
r'^ldap/$'
,
views
.
LDAPSettingView
.
as_view
(),
name
=
'ldap-setting'
),
url
(
r'^terminal/$'
,
views
.
TerminalSettingView
.
as_view
(),
name
=
'terminal-setting'
),
url
(
r'^terminal/$'
,
views
.
TerminalSettingView
.
as_view
(),
name
=
'terminal-setting'
),
url
(
r'^celery/task/(?P<pk>[0-9a-zA-Z\-]{36})/log/$'
,
views
.
CeleryTaskLogView
.
as_view
(),
name
=
'celery-task-log'
),
]
]
apps/common/views.py
View file @
d247e49b
...
@@ -122,18 +122,3 @@ class TerminalSettingView(AdminUserRequiredMixin, TemplateView):
...
@@ -122,18 +122,3 @@ class TerminalSettingView(AdminUserRequiredMixin, TemplateView):
return
render
(
request
,
self
.
template_name
,
context
)
return
render
(
request
,
self
.
template_name
,
context
)
class
CeleryTaskLogView
(
AdminUserRequiredMixin
,
TemplateView
):
template_name
=
'common/celery_task_log.html'
task_log_path
=
None
def
get_context_data
(
self
,
**
kwargs
):
context
=
super
()
.
get_context_data
(
**
kwargs
)
task_id
=
self
.
kwargs
.
get
(
"pk"
)
if
cache
.
get
(
celery_task_pre_key
+
task_id
)
is
None
:
raise
Http404
()
context
.
update
({
"task_id"
:
self
.
kwargs
.
get
(
"pk"
)
})
return
context
apps/i18n/zh/LC_MESSAGES/django.mo
View file @
d247e49b
No preview for this file type
apps/i18n/zh/LC_MESSAGES/django.po
View file @
d247e49b
This diff is collapsed.
Click to expand it.
apps/ops/api.py
View file @
d247e49b
...
@@ -6,18 +6,15 @@ from django.core.cache import cache
...
@@ -6,18 +6,15 @@ from django.core.cache import cache
from
django.shortcuts
import
get_object_or_404
from
django.shortcuts
import
get_object_or_404
from
django.utils.translation
import
ugettext
as
_
from
django.utils.translation
import
ugettext
as
_
from
rest_framework
import
viewsets
,
generics
from
rest_framework
import
viewsets
,
generics
from
rest_framework.views
import
APIView
from
rest_framework.views
import
Response
from
rest_framework.views
import
Response
from
.hands
import
IsSuperUser
from
.hands
import
IsSuperUser
from
common.const
import
FILE_END_GUARD
from
.models
import
Task
,
AdHoc
,
AdHocRunHistory
,
CeleryTask
from
.
models
import
Task
,
AdHoc
,
AdHocRunHistory
from
.
serializers
import
TaskSerializer
,
AdHocSerializer
,
\
from
.serializers
import
TaskSerializer
,
AdHocSerializer
,
AdHocRunHistorySerializer
AdHocRunHistorySerializer
from
.tasks
import
run_ansible_task
from
.tasks
import
run_ansible_task
class
TaskViewSet
(
viewsets
.
ModelViewSet
):
class
TaskViewSet
(
viewsets
.
ModelViewSet
):
queryset
=
Task
.
objects
.
all
()
queryset
=
Task
.
objects
.
all
()
serializer_class
=
TaskSerializer
serializer_class
=
TaskSerializer
...
@@ -67,28 +64,28 @@ class AdHocRunHistorySet(viewsets.ModelViewSet):
...
@@ -67,28 +64,28 @@ class AdHocRunHistorySet(viewsets.ModelViewSet):
return
self
.
queryset
return
self
.
queryset
class
LogFileViewApi
(
APIView
):
class
CeleryTaskLogApi
(
generics
.
Retrieve
APIView
):
permission_classes
=
(
IsSuperUser
,)
permission_classes
=
(
IsSuperUser
,)
buff_size
=
1024
*
10
buff_size
=
1024
*
10
end
=
False
end
=
False
queryset
=
CeleryTask
.
objects
.
all
()
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
def
get
(
self
,
request
,
*
args
,
**
kwargs
):
file_path
=
request
.
query_params
.
get
(
"file"
)
mark
=
request
.
query_params
.
get
(
"mark"
)
or
str
(
uuid
.
uuid4
())
mark
=
request
.
query_params
.
get
(
"mark"
)
or
str
(
uuid
.
uuid4
())
task
=
super
()
.
get_object
()
log_path
=
task
.
full_log_path
if
not
os
.
path
.
isfile
(
file_path
):
if
not
log_path
or
not
os
.
path
.
isfile
(
log_path
):
print
(
file_path
)
return
Response
({
"data"
:
_
(
"Waiting ..."
)},
status
=
203
)
return
Response
({
"error"
:
_
(
"Log file not found"
)},
status
=
204
)
with
open
(
file
_path
,
'r'
)
as
f
:
with
open
(
log
_path
,
'r'
)
as
f
:
offset
=
cache
.
get
(
mark
,
0
)
offset
=
cache
.
get
(
mark
,
0
)
f
.
seek
(
offset
)
f
.
seek
(
offset
)
data
=
f
.
read
(
self
.
buff_size
)
.
replace
(
'
\n
'
,
'
\r\n
'
)
data
=
f
.
read
(
self
.
buff_size
)
.
replace
(
'
\n
'
,
'
\r\n
'
)
mark
=
str
(
uuid
.
uuid4
())
mark
=
str
(
uuid
.
uuid4
())
cache
.
set
(
mark
,
f
.
tell
(),
5
)
cache
.
set
(
mark
,
f
.
tell
(),
5
)
if
FILE_END_GUARD
in
data
:
if
data
==
''
and
task
.
is_finished
():
data
.
replace
(
FILE_END_GUARD
,
''
)
self
.
end
=
True
self
.
end
=
True
return
Response
({
"data"
:
data
,
'end'
:
self
.
end
,
'mark'
:
mark
})
return
Response
({
"data"
:
data
,
'end'
:
self
.
end
,
'mark'
:
mark
})
apps/ops/apps.py
View file @
d247e49b
...
@@ -5,3 +5,7 @@ from django.apps import AppConfig
...
@@ -5,3 +5,7 @@ from django.apps import AppConfig
class
OpsConfig
(
AppConfig
):
class
OpsConfig
(
AppConfig
):
name
=
'ops'
name
=
'ops'
def
ready
(
self
):
super
()
.
ready
()
from
.celery
import
signal_handler
apps/ops/celery/__init__.py
View file @
d247e49b
...
@@ -15,4 +15,3 @@ app = Celery('jumpserver')
...
@@ -15,4 +15,3 @@ app = Celery('jumpserver')
# pickle the object when using Windows.
# pickle the object when using Windows.
app
.
config_from_object
(
'django.conf:settings'
,
namespace
=
'CELERY'
)
app
.
config_from_object
(
'django.conf:settings'
,
namespace
=
'CELERY'
)
app
.
autodiscover_tasks
(
lambda
:
[
app_config
.
split
(
'.'
)[
0
]
for
app_config
in
settings
.
INSTALLED_APPS
])
app
.
autodiscover_tasks
(
lambda
:
[
app_config
.
split
(
'.'
)[
0
]
for
app_config
in
settings
.
INSTALLED_APPS
])
apps/ops/celery/signal_handler.py
View file @
d247e49b
...
@@ -5,27 +5,21 @@ import datetime
...
@@ -5,27 +5,21 @@ import datetime
import
sys
import
sys
from
django.conf
import
settings
from
django.conf
import
settings
from
django.utils
import
timezone
from
django.core.cache
import
cache
from
django.core.cache
import
cache
from
django.db
import
transaction
from
celery
import
subtask
from
celery
import
subtask
from
celery.signals
import
worker_ready
,
worker_shutdown
,
task_prerun
,
\
from
celery.signals
import
worker_ready
,
worker_shutdown
,
task_prerun
,
\
task_postrun
,
after_task_publish
task_postrun
,
after_task_publish
from
django_celery_beat.models
import
PeriodicTask
from
django_celery_beat.models
import
PeriodicTask
from
common.utils
import
get_logger
,
TeeObj
from
common.utils
import
get_logger
,
TeeObj
,
get_object_or_none
from
common.const
import
celery_task_pre_key
from
common.const
import
celery_task_pre_key
from
.utils
import
get_after_app_ready_tasks
,
get_after_app_shutdown_clean_tasks
from
.utils
import
get_after_app_ready_tasks
,
get_after_app_shutdown_clean_tasks
from
..models
import
CeleryTask
logger
=
get_logger
(
__file__
)
logger
=
get_logger
(
__file__
)
WAITING
=
"waiting"
RUNNING
=
"running"
FINISHED
=
"finished"
EXPIRE_TIME
=
3600
@worker_ready.connect
@worker_ready.connect
def
on_app_ready
(
sender
=
None
,
headers
=
None
,
body
=
None
,
**
kwargs
):
def
on_app_ready
(
sender
=
None
,
headers
=
None
,
body
=
None
,
**
kwargs
):
...
@@ -54,18 +48,31 @@ def after_app_shutdown(sender=None, headers=None, body=None, **kwargs):
...
@@ -54,18 +48,31 @@ def after_app_shutdown(sender=None, headers=None, body=None, **kwargs):
PeriodicTask
.
objects
.
filter
(
name__in
=
tasks
)
.
delete
()
PeriodicTask
.
objects
.
filter
(
name__in
=
tasks
)
.
delete
()
@after_task_publish.connect
def
after_task_publish_signal_handler
(
sender
,
headers
=
None
,
**
kwargs
):
CeleryTask
.
objects
.
create
(
id
=
headers
[
"id"
],
status
=
CeleryTask
.
WAITING
,
name
=
headers
[
"task"
]
)
@task_prerun.connect
@task_prerun.connect
def
pre_run_task_signal_handler
(
sender
,
task_id
=
None
,
task
=
None
,
**
kwargs
):
def
pre_run_task_signal_handler
(
sender
,
task_id
=
None
,
task
=
None
,
**
kwargs
):
task_key
=
celery_task_pre_key
+
task_id
t
=
get_object_or_none
(
CeleryTask
,
id
=
task_id
)
info
=
cache
.
get
(
task_key
,
{})
if
t
is
None
:
logger
.
warn
(
"Not get the task: {}"
.
format
(
task_id
))
return
now
=
datetime
.
datetime
.
now
()
.
strftime
(
"
%
Y-
%
m-
%
d"
)
now
=
datetime
.
datetime
.
now
()
.
strftime
(
"
%
Y-
%
m-
%
d"
)
log_dir
=
os
.
path
.
join
(
settings
.
PROJECT_DIR
,
"data"
,
"celery"
,
now
)
log_path
=
os
.
path
.
join
(
now
,
task_id
+
'.log'
)
if
not
os
.
path
.
exists
(
log_dir
):
full_path
=
os
.
path
.
join
(
CeleryTask
.
LOG_DIR
,
log_path
)
os
.
makedirs
(
log_dir
)
log_path
=
os
.
path
.
join
(
log_dir
,
task_id
+
'.log'
)
if
not
os
.
path
.
exists
(
os
.
path
.
dirname
(
full_path
)):
info
.
update
({
"status"
:
RUNNING
,
"log_path"
:
log_path
})
os
.
makedirs
(
os
.
path
.
dirname
(
full_path
))
cache
.
set
(
task_key
,
info
,
EXPIRE_TIME
)
with
transaction
.
atomic
():
f
=
open
(
log_path
,
'w'
)
t
.
date_start
=
timezone
.
now
()
t
.
status
=
CeleryTask
.
RUNNING
t
.
log_path
=
log_path
t
.
save
()
f
=
open
(
full_path
,
'w'
)
tee
=
TeeObj
(
f
)
tee
=
TeeObj
(
f
)
sys
.
stdout
=
tee
sys
.
stdout
=
tee
task
.
log_f
=
tee
task
.
log_f
=
tee
...
@@ -73,17 +80,15 @@ def pre_run_task_signal_handler(sender, task_id=None, task=None, **kwargs):
...
@@ -73,17 +80,15 @@ def pre_run_task_signal_handler(sender, task_id=None, task=None, **kwargs):
@task_postrun.connect
@task_postrun.connect
def
post_run_task_signal_handler
(
sender
,
task_id
=
None
,
task
=
None
,
**
kwargs
):
def
post_run_task_signal_handler
(
sender
,
task_id
=
None
,
task
=
None
,
**
kwargs
):
task_key
=
celery_task_pre_key
+
task_id
t
=
get_object_or_none
(
CeleryTask
,
id
=
task_id
)
info
=
cache
.
get
(
task_key
,
{})
if
t
is
None
:
info
.
update
({
"status"
:
FINISHED
})
logger
.
warn
(
"Not get the task: {}"
.
format
(
task_id
))
cache
.
set
(
task_key
,
info
,
EXPIRE_TIME
)
return
with
transaction
.
atomic
():
t
.
status
=
CeleryTask
.
FINISHED
t
.
date_finished
=
timezone
.
now
()
t
.
save
()
task
.
log_f
.
flush
()
task
.
log_f
.
flush
()
sys
.
stdout
=
task
.
log_f
.
origin_stdout
sys
.
stdout
=
task
.
log_f
.
origin_stdout
task
.
log_f
.
close
()
task
.
log_f
.
close
()
@after_task_publish.connect
def
after_task_publish_signal_handler
(
sender
,
headers
=
None
,
**
kwargs
):
task_id
=
headers
[
"id"
]
key
=
celery_task_pre_key
+
task_id
cache
.
set
(
key
,
{
"status"
:
WAITING
},
EXPIRE_TIME
)
\ No newline at end of file
apps/ops/models/__init__.py
0 → 100644
View file @
d247e49b
# -*- coding: utf-8 -*-
#
from
.adhoc
import
*
from
.celery
import
*
\ No newline at end of file
apps/ops/models.py
→
apps/ops/models
/adhoc
.py
View file @
d247e49b
...
@@ -11,15 +11,14 @@ from django.db import models
...
@@ -11,15 +11,14 @@ from django.db import models
from
django.conf
import
settings
from
django.conf
import
settings
from
django.utils
import
timezone
from
django.utils
import
timezone
from
django.utils.translation
import
ugettext_lazy
as
_
from
django.utils.translation
import
ugettext_lazy
as
_
from
django_celery_beat.models
import
CrontabSchedule
,
IntervalSchedule
,
\
from
django_celery_beat.models
import
PeriodicTask
PeriodicTask
from
common.utils
import
get_signer
,
get_logger
from
common.utils
import
get_signer
,
get_logger
from
.celery.utils
import
delete_celery_periodic_task
,
\
from
.
.
celery.utils
import
delete_celery_periodic_task
,
\
create_or_update_celery_periodic_tasks
,
\
create_or_update_celery_periodic_tasks
,
\
disable_celery_periodic_task
disable_celery_periodic_task
from
.ansible
import
AdHocRunner
,
AnsibleError
from
.
.
ansible
import
AdHocRunner
,
AnsibleError
from
.inventory
import
JMSInventory
from
.
.
inventory
import
JMSInventory
__all__
=
[
"Task"
,
"AdHoc"
,
"AdHocRunHistory"
]
__all__
=
[
"Task"
,
"AdHoc"
,
"AdHocRunHistory"
]
...
@@ -91,7 +90,7 @@ class Task(models.Model):
...
@@ -91,7 +90,7 @@ class Task(models.Model):
def
save
(
self
,
force_insert
=
False
,
force_update
=
False
,
using
=
None
,
def
save
(
self
,
force_insert
=
False
,
force_update
=
False
,
using
=
None
,
update_fields
=
None
):
update_fields
=
None
):
from
.tasks
import
run_ansible_task
from
.
.
tasks
import
run_ansible_task
super
()
.
save
(
super
()
.
save
(
force_insert
=
force_insert
,
force_update
=
force_update
,
force_insert
=
force_insert
,
force_update
=
force_update
,
using
=
using
,
update_fields
=
update_fields
,
using
=
using
,
update_fields
=
update_fields
,
...
...
apps/ops/models/celery.py
0 → 100644
View file @
d247e49b
# -*- coding: utf-8 -*-
#
import
uuid
import
os
from
django.conf
import
settings
from
django.db
import
models
class
CeleryTask
(
models
.
Model
):
WAITING
=
"waiting"
RUNNING
=
"running"
FINISHED
=
"finished"
LOG_DIR
=
os
.
path
.
join
(
settings
.
PROJECT_DIR
,
'data'
,
'celery'
)
STATUS_CHOICES
=
(
(
WAITING
,
WAITING
),
(
RUNNING
,
RUNNING
),
(
FINISHED
,
FINISHED
),
)
id
=
models
.
UUIDField
(
primary_key
=
True
,
default
=
uuid
.
uuid4
)
name
=
models
.
CharField
(
max_length
=
1024
)
status
=
models
.
CharField
(
max_length
=
128
,
choices
=
STATUS_CHOICES
)
log_path
=
models
.
CharField
(
max_length
=
256
,
blank
=
True
,
null
=
True
)
date_published
=
models
.
DateTimeField
(
auto_now_add
=
True
)
date_start
=
models
.
DateTimeField
(
null
=
True
)
date_finished
=
models
.
DateTimeField
(
null
=
True
)
def
__str__
(
self
):
return
"{}: {}"
.
format
(
self
.
name
,
self
.
id
)
def
is_finished
(
self
):
return
self
.
status
==
self
.
FINISHED
@property
def
full_log_path
(
self
):
return
os
.
path
.
join
(
self
.
LOG_DIR
,
self
.
log_path
)
apps/ops/tasks.py
View file @
d247e49b
# coding: utf-8
# coding: utf-8
from
celery
import
shared_task
,
subtask
from
celery
import
shared_task
,
subtask
from
common.utils
import
get_logger
,
get_object_or_none
from
common.utils
import
get_logger
,
get_object_or_none
from
.models
import
Task
from
.models
import
Task
...
...
apps/ops/templates/ops/adhoc_history_detail.html
View file @
d247e49b
...
@@ -19,7 +19,7 @@
...
@@ -19,7 +19,7 @@
<a
href=
"{% url 'ops:adhoc-history-detail' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history detail' %}
</a>
<a
href=
"{% url 'ops:adhoc-history-detail' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history detail' %}
</a>
</li>
</li>
<li>
<li>
<a
href=
"{% url 'ops:adhoc-history-output' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'History o
utput' %}
</a>
<a
class=
"text-center celery-task-log"
onclick=
"window.open('{% url 'ops:celery-task-log' pk=object.pk %}','', 'width=800,height=600')"
><i
class=
"fa fa-laptop"
></i>
{% trans 'O
utput' %}
</a>
</li>
</li>
</ul>
</ul>
</div>
</div>
...
...
apps/ops/templates/ops/adhoc_history_output.html
deleted
100644 → 0
View file @
a4c843ff
{% extends 'base.html' %}
{% load static %}
{% load i18n %}
{% block custom_head_css_js %}
<link
href=
"{% static 'css/plugins/select2/select2.min.css' %}"
rel=
"stylesheet"
>
<link
href=
"{% static "
css
/
plugins
/
sweetalert
/
sweetalert
.
css
"
%}"
rel=
"stylesheet"
>
<script
src=
"{% static 'js/plugins/select2/select2.full.min.js' %}"
></script>
<script
src=
"{% static "
js
/
plugins
/
sweetalert
/
sweetalert
.
min
.
js
"
%}"
></script>
</head>
{% endblock %}
{% block content %}
<div
class=
"wrapper wrapper-content animated fadeInRight"
>
<div
class=
"row"
>
<div
class=
"col-sm-12"
>
<div
class=
"ibox float-e-margins"
>
<div
class=
"panel-options"
>
<ul
class=
"nav nav-tabs"
>
<li>
<a
href=
"{% url 'ops:adhoc-history-detail' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history detail' %}
</a>
</li>
<li
class=
"active"
>
<a
href=
"{% url 'ops:adhoc-history-output' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'History output' %}
</a>
</li>
</ul>
</div>
<div
class=
"tab-content"
style=
"height: 800px"
>
<iframe
src=
"{% url 'ops:adhoc-history-output-alone' pk=object.pk %}"
width=
"100%"
height=
"100%"
>
</iframe>
</div>
</div>
</div>
</div>
</div>
{% endblock %}
apps/
common/templates/common
/celery_task_log.html
→
apps/
ops/templates/ops
/celery_task_log.html
View file @
d247e49b
...
@@ -35,7 +35,7 @@
...
@@ -35,7 +35,7 @@
var
rowHeight
=
1
;
var
rowHeight
=
1
;
var
colWidth
=
1
;
var
colWidth
=
1
;
var
mark
=
''
;
var
mark
=
''
;
var
url
=
"{% url 'api-
common:celery-task-log' pk=task_
id %}"
;
var
url
=
"{% url 'api-
ops:celery-task-log' pk=object.
id %}"
;
var
term
;
var
term
;
var
end
=
false
;
var
end
=
false
;
var
error
=
false
;
var
error
=
false
;
...
...
apps/ops/templates/ops/celery_task_output.html
deleted
100644 → 0
View file @
a4c843ff
{% load static %}
<head>
<title>
term.js
</title>
<script
src=
"{% static 'js/jquery-2.1.1.js' %}"
></script>
<style>
html
{
background
:
#000
;
}
h1
{
margin-bottom
:
20px
;
font
:
20px
/
1.5
sans-serif
;
}
.terminal
{
float
:
left
;
font-family
:
'Monaco'
,
'Consolas'
,
"DejaVu Sans Mono"
,
"Liberation Mono"
,
monospace
;
font-size
:
12px
;
color
:
#f0f0f0
;
background-color
:
#555
;
padding
:
20px
20px
20px
;
}
.terminal-cursor
{
color
:
#000
;
background
:
#f0f0f0
;
}
</style>
</head>
<div
class=
"container"
>
<div
id=
"term"
>
</div>
</div>
<script
src=
"{% static 'js/term.js' %}"
></script>
<script>
var
rowHeight
=
1
;
var
colWidth
=
1
;
var
mark
=
''
;
var
url
=
"{% url 'api-ops:history-output' pk=object.id %}"
;
var
term
;
var
end
=
false
;
var
has_error
=
false
;
function
calWinSize
()
{
var
t
=
$
(
'.terminal'
);
rowHeight
=
1.00
*
t
.
height
()
/
24
;
colWidth
=
1.00
*
t
.
width
()
/
80
;
}
function
resize
()
{
var
rows
=
Math
.
floor
(
window
.
innerHeight
/
rowHeight
)
-
2
;
var
cols
=
Math
.
floor
(
window
.
innerWidth
/
colWidth
)
-
5
;
term
.
resize
(
cols
,
rows
);
}
function
requestAndWrite
()
{
if
(
!
end
)
{
$
.
ajax
({
url
:
url
+
'?mark='
+
mark
,
method
:
"GET"
,
contentType
:
"application/json; charset=utf-8"
}).
done
(
function
(
data
,
textStatue
,
jqXHR
)
{
term
.
write
(
data
.
data
);
mark
=
data
.
mark
;
if
(
data
.
end
){
end
=
true
}
}).
fail
(
function
(
jqXHR
,
textStatus
,
errorThrown
)
{
if
(
!
has_error
)
{
var
error
=
jqXHR
.
responseJSON
.
error
;
term
.
write
(
'
\
x1b[31m'
+
error
+
'
\
x1b[m
\
r
\
n'
);
has_error
=
true
}
});
}
}
$
(
document
).
ready
(
function
()
{
term
=
new
Terminal
({
cols
:
80
,
rows
:
24
,
useStyle
:
true
,
screenKeys
:
false
,
convertEol
:
false
,
cursorBlink
:
false
});
term
.
open
();
term
.
on
(
'data'
,
function
(
data
)
{
term
.
write
(
data
.
replace
(
'
\
r'
,
'
\
r
\
n'
))
});
calWinSize
();
resize
();
$
(
'.terminal'
).
detach
().
appendTo
(
'#term'
);
setInterval
(
function
()
{
requestAndWrite
()
},
200
)
});
</script>
apps/ops/templates/ops/task_adhoc.html
View file @
d247e49b
...
@@ -24,6 +24,9 @@
...
@@ -24,6 +24,9 @@
<li>
<li>
<a
href=
"{% url 'ops:task-history' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history' %}
</a>
<a
href=
"{% url 'ops:task-history' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history' %}
</a>
</li>
</li>
<li>
<a
class=
"text-center celery-task-log"
onclick=
"window.open('{% url 'ops:celery-task-log' pk=object.latest_history.pk %}','', 'width=800,height=600')"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Last run output' %}
</a>
</li>
</ul>
</ul>
</div>
</div>
<div
class=
"tab-content"
>
<div
class=
"tab-content"
>
...
...
apps/ops/templates/ops/task_detail.html
View file @
d247e49b
...
@@ -25,7 +25,7 @@
...
@@ -25,7 +25,7 @@
<a
href=
"{% url 'ops:task-history' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history' %}
</a>
<a
href=
"{% url 'ops:task-history' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history' %}
</a>
</li>
</li>
<li>
<li>
<a
href=
"{% url 'ops:adhoc-history-output' pk=object.latest_history.pk %}"
class=
"text-center
"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Last run output' %}
</a>
<a
class=
"text-center celery-task-log"
onclick=
"window.open('{% url 'ops:celery-task-log' pk=object.latest_history.pk %}','', 'width=800,height=600')
"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Last run output' %}
</a>
</li>
</li>
</ul>
</ul>
</div>
</div>
...
...
apps/ops/templates/ops/task_history.html
View file @
d247e49b
...
@@ -24,6 +24,9 @@
...
@@ -24,6 +24,9 @@
<li
class=
"active"
>
<li
class=
"active"
>
<a
href=
"{% url 'ops:task-history' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history' %}
</a>
<a
href=
"{% url 'ops:task-history' pk=object.pk %}"
class=
"text-center"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Run history' %}
</a>
</li>
</li>
<li>
<a
class=
"text-center celery-task-log"
onclick=
"window.open('{% url 'ops:celery-task-log' pk=object.latest_history.pk %}','', 'width=800,height=600')"
><i
class=
"fa fa-laptop"
></i>
{% trans 'Last run output' %}
</a>
</li>
</ul>
</ul>
</div>
</div>
<div
class=
"tab-content"
>
<div
class=
"tab-content"
>
...
...
apps/ops/templates/ops/task_list.html
View file @
d247e49b
...
@@ -113,8 +113,8 @@ $(document).ready(function() {
...
@@ -113,8 +113,8 @@ $(document).ready(function() {
};
};
var
success
=
function
(
data
)
{
var
success
=
function
(
data
)
{
var
task_id
=
data
.
task
;
var
task_id
=
data
.
task
;
var
url
=
'{% url "
common
:celery-task-log" pk=DEFAULT_PK %}'
.
replace
(
"{{ DEFAULT_PK }}"
,
task_id
);
var
url
=
'{% url "
ops
:celery-task-log" pk=DEFAULT_PK %}'
.
replace
(
"{{ DEFAULT_PK }}"
,
task_id
);
window
.
open
(
url
,
''
,
'width=800,height=
8
00'
)
window
.
open
(
url
,
''
,
'width=800,height=
6
00'
)
};
};
APIUpdateAttr
({
APIUpdateAttr
({
url
:
the_url
,
url
:
the_url
,
...
...
apps/ops/urls/api_urls.py
View file @
d247e49b
...
@@ -15,7 +15,7 @@ router.register(r'v1/history', api.AdHocRunHistorySet, 'history')
...
@@ -15,7 +15,7 @@ router.register(r'v1/history', api.AdHocRunHistorySet, 'history')
urlpatterns
=
[
urlpatterns
=
[
url
(
r'^v1/tasks/(?P<pk>[0-9a-zA-Z\-]{36})/run/$'
,
api
.
TaskRun
.
as_view
(),
name
=
'task-run'
),
url
(
r'^v1/tasks/(?P<pk>[0-9a-zA-Z\-]{36})/run/$'
,
api
.
TaskRun
.
as_view
(),
name
=
'task-run'
),
# url(r'^v1/history/(?P<pk>[0-9a-zA-Z\-]{36})/output/$', api.CeleryTaskOutputApi.as_view(), name='history-output
'),
url
(
r'^v1/celery/task/(?P<pk>[0-9a-zA-Z\-]{36})/log/$'
,
api
.
CeleryTaskLogApi
.
as_view
(),
name
=
'celery-task-log
'
),
]
]
urlpatterns
+=
router
.
urls
urlpatterns
+=
router
.
urls
apps/ops/urls/view_urls.py
View file @
d247e49b
...
@@ -18,6 +18,5 @@ urlpatterns = [
...
@@ -18,6 +18,5 @@ urlpatterns = [
url
(
r'^adhoc/(?P<pk>[0-9a-zA-Z\-]{36})/$'
,
views
.
AdHocDetailView
.
as_view
(),
name
=
'adhoc-detail'
),
url
(
r'^adhoc/(?P<pk>[0-9a-zA-Z\-]{36})/$'
,
views
.
AdHocDetailView
.
as_view
(),
name
=
'adhoc-detail'
),
url
(
r'^adhoc/(?P<pk>[0-9a-zA-Z\-]{36})/history/$'
,
views
.
AdHocHistoryView
.
as_view
(),
name
=
'adhoc-history'
),
url
(
r'^adhoc/(?P<pk>[0-9a-zA-Z\-]{36})/history/$'
,
views
.
AdHocHistoryView
.
as_view
(),
name
=
'adhoc-history'
),
url
(
r'^adhoc/history/(?P<pk>[0-9a-zA-Z\-]{36})/$'
,
views
.
AdHocHistoryDetailView
.
as_view
(),
name
=
'adhoc-history-detail'
),
url
(
r'^adhoc/history/(?P<pk>[0-9a-zA-Z\-]{36})/$'
,
views
.
AdHocHistoryDetailView
.
as_view
(),
name
=
'adhoc-history-detail'
),
url
(
r'^adhoc/history/(?P<pk>[0-9a-zA-Z\-]{36})/_output/$'
,
views
.
CeleryTaskOutputView
.
as_view
(),
name
=
'adhoc-history-output-alone'
),
url
(
r'^celery/task/(?P<pk>[0-9a-zA-Z\-]{36})/log/$'
,
views
.
CeleryTaskLogView
.
as_view
(),
name
=
'celery-task-log'
),
url
(
r'^adhoc/history/(?P<pk>[0-9a-zA-Z\-]{36})/output/$'
,
views
.
AdHocHistoryOutputView
.
as_view
(),
name
=
'adhoc-history-output'
),
]
]
apps/ops/views.py
View file @
d247e49b
...
@@ -5,7 +5,7 @@ from django.conf import settings
...
@@ -5,7 +5,7 @@ from django.conf import settings
from
django.views.generic
import
ListView
,
DetailView
,
TemplateView
from
django.views.generic
import
ListView
,
DetailView
,
TemplateView
from
common.mixins
import
DatetimeSearchMixin
from
common.mixins
import
DatetimeSearchMixin
from
.models
import
Task
,
AdHoc
,
AdHocRunHistory
from
.models
import
Task
,
AdHoc
,
AdHocRunHistory
,
CeleryTask
from
.hands
import
AdminUserRequiredMixin
from
.hands
import
AdminUserRequiredMixin
...
@@ -121,19 +121,6 @@ class AdHocHistoryDetailView(AdminUserRequiredMixin, DetailView):
...
@@ -121,19 +121,6 @@ class AdHocHistoryDetailView(AdminUserRequiredMixin, DetailView):
return
super
()
.
get_context_data
(
**
kwargs
)
return
super
()
.
get_context_data
(
**
kwargs
)
class
CeleryTaskOutputView
(
AdminUserRequiredMixin
,
TemplateView
):
class
CeleryTaskLogView
(
AdminUserRequiredMixin
,
DetailView
):
model
=
AdHocRunHistory
template_name
=
'ops/celery_task_log.html'
template_name
=
'ops/celery_task_output.html'
model
=
CeleryTask
class
AdHocHistoryOutputView
(
AdminUserRequiredMixin
,
DetailView
):
model
=
AdHocRunHistory
template_name
=
'ops/adhoc_history_output.html'
def
get_context_data
(
self
,
**
kwargs
):
context
=
{
'app'
:
_
(
'Ops'
),
'action'
:
_
(
'Run history detail'
),
}
kwargs
.
update
(
context
)
return
super
()
.
get_context_data
(
**
kwargs
)
\ No newline at end of file
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