Skip to content
Snippets Groups Projects
Commit 0b01cdff authored by André Anjos's avatar André Anjos :speech_balloon:
Browse files

[backend] Remove syserr field, use logger instead; Prefer logger.error() as...

[backend] Remove syserr field, use logger instead; Prefer logger.error() as way to contact sysadmins than directly e-mailing
parent 7143c20e
No related branches found
No related tags found
1 merge request!203[backend] Remove syserr field, use logger instead; Prefer logger.error() as way …
Pipeline #
# -*- coding: utf-8 -*-
# Generated by Django 1.9.5 on 2016-06-30 17:35
from __future__ import unicode_literals
from django.db import migrations
class Migration(migrations.Migration):
dependencies = [
('backend', '0002_scheduler_addons'),
]
operations = [
migrations.RemoveField(
model_name='result',
name='syserr',
),
]
......@@ -448,9 +448,8 @@ class Worker(models.Model):
j.job.block.name,
j.job.block.experiment.fullname(),
)
logger.warn(message)
j.end(Result(status=1, usrerr=settings.DEFAULT_USER_ERROR,
syserr=message))
logger.error(message)
j.end(Result(status=1, usrerr=settings.DEFAULT_USER_ERROR))
# cmdline base argument
cmdline = [process]
......@@ -478,9 +477,9 @@ class Worker(models.Model):
"Available environments are `%s'" % \
'|'.join(environments.keys()),
)
logger.warn(message)
logger.error(message)
split.end(Result(status=1,
usrerr=settings.DEFAULT_USER_ERROR, syserr=message))
usrerr=settings.DEFAULT_USER_ERROR))
continue
# if we get to this point, then we launch the user process
......@@ -695,7 +694,6 @@ class Result(models.Model):
stdout = models.TextField(null=True, blank=True)
stderr = models.TextField(null=True, blank=True)
usrerr = models.TextField(null=True, blank=True)
syserr = models.TextField(null=True, blank=True)
_stats = models.TextField(null=True, blank=True)
timed_out = models.BooleanField(default=False)
cancelled = models.BooleanField(default=False)
......@@ -707,7 +705,6 @@ class Result(models.Model):
if self.stdout: retval += ', stdout=' + self.stdout
if self.stderr: retval += ', stderr=' + self.stderr
if self.usrerr: retval += ', usrerr=' + self.usrerr
if self.syserr: retval += ', syserr=' + self.syserr
retval += ')'
return retval
......@@ -879,8 +876,8 @@ class Job(models.Model):
message = "Index splitting for block `%s' of experiment " \
"`%s' could not be completed: not splittable!" % \
(self.block.name, self.block.experiment.fullname())
logger.warn(message)
self._cancel(usrerr=settings.DEFAULT_USER_ERROR, syserr=message)
logger.error(message)
self._cancel(usrerr=settings.DEFAULT_USER_ERROR)
# if you get to this point, the splitting has succeeded,
# create the necessary splits and assign the ranges
......@@ -905,8 +902,8 @@ class Job(models.Model):
"error: %s" % (self.block.name,
self.block.experiment.fullname(),
traceback.format_exc())
logger.warn(message)
self._cancel(usrerr=settings.DEFAULT_USER_ERROR, syserr=message)
logger.error(message)
self._cancel(usrerr=settings.DEFAULT_USER_ERROR)
def _cascade_updates(self):
......@@ -1036,7 +1033,7 @@ class Job(models.Model):
os.remove(f)
def _cancel(self, usrerr=None, syserr=None):
def _cancel(self, usrerr=None):
'''Cancel the execution of this job
As a consequence: delete all associated jobs, mark end_date and set
......@@ -1055,8 +1052,8 @@ class Job(models.Model):
for s in self.splits.all(): s._cancel()
else:
self.status = Job.CANCELLED
if usrerr or syserr:
r = Result(status=1, usrerr=usrerr, syserr=syserr)
if usrerr:
r = Result(status=1, usrerr=usrerr)
r.save()
self.result = r
self.save()
......@@ -1078,7 +1075,6 @@ class Job(models.Model):
stdout = _merge_strings([k.stdout for k in job_results])
stderr = _merge_strings([k.stderr for k in job_results])
usrerr = _merge_strings([k.usrerr for k in job_results])
syserr = _merge_strings([k.syserr for k in job_results])
# merge beat.core statistics
if job_results:
......@@ -1092,7 +1088,7 @@ class Job(models.Model):
timed_out = any([k.timed_out for k in job_results])
r = Result(status=status, stdout=stdout, stderr=stderr, usrerr=usrerr,
syserr=syserr, timed_out=timed_out, cancelled=cancelled)
timed_out=timed_out, cancelled=cancelled)
r.stats = stats
r.save()
self.result = r
......@@ -1428,8 +1424,8 @@ class JobSplit(models.Model):
(self.split_index+1, self.job.block.required_slots,
os.getpid(), self.worker, self.job.block.name,
self.job.block.experiment.fullname())
logger.warn(message)
self.try_end(Result(status=1, syserr=message,
logger.error(message)
self.try_end(Result(status=1,
usrerr=settings.DEFAULT_USER_ERROR))
config['range'] = [self.start_index, self.end_index]
......@@ -1481,7 +1477,6 @@ class JobSplit(models.Model):
stdout=result['stdout'],
stderr=result['stderr'],
usrerr=result['user_error'],
syserr=result['system_error'],
_stats=simplejson.dumps(result['statistics'], indent=2),
))
logger.info("Split `%s' (pid=%d) ended gracefully", self,
......@@ -1495,15 +1490,14 @@ class JobSplit(models.Model):
logger.info("Split `%s' reached the maximum number of IO " \
"errors (%d > %d). Force failing this split." % \
(self, self.cache_errors, settings.MAXIMUM_IO_ERRORS))
logger.error(traceback.format_exc())
self.try_end(Result(status=1,
usrerr=settings.DEFAULT_USER_ERROR,
syserr=traceback.format_exc(),))
usrerr=settings.DEFAULT_USER_ERROR))
else:
logger.info("Split `%s' will be retried (%d/%d)",
self, self.cache_errors, settings.MAXIMUM_IO_ERRORS)
except Exception:
logger.warn("Split `%s' (pid=%d) ended with an error: %s",
logger.error("Split `%s' (pid=%d) ended with an error: %s",
self, os.getpid(), traceback.format_exc())
self.try_end(Result(status=1, usrerr=settings.DEFAULT_USER_ERROR,
syserr=traceback.format_exc(),))
self.try_end(Result(status=1, usrerr=settings.DEFAULT_USER_ERROR))
......@@ -47,7 +47,11 @@ from ..common.api import ListCreateBaseView
from ..common.responses import BadRequestResponse
from ..common.utils import ensure_html
from ..dataformats.serializers import ReferencedDataFormatSerializer
from ..utils.api import report_server_error
import logging
import traceback
logger = logging.getLogger(__name__)
#----------------------------------------------------------
......@@ -222,7 +226,8 @@ class RetrieveDatabaseView(views.APIView):
try:
result['declaration'] = database.declaration_file.read()
except:
return report_server_error()
logger.error(traceback.format_exc())
return HttpResponse(status=500)
# Retrieve the source code
......@@ -230,7 +235,8 @@ class RetrieveDatabaseView(views.APIView):
try:
result['code'] = database.source_code_file.read()
except:
return report_server_error()
logger.error(traceback.format_exc())
return HttpResponse(status=500)
# Retrieve the description in HTML format
......@@ -270,4 +276,5 @@ class RetrieveDatabaseView(views.APIView):
# Return the result
return Response(result)
except:
return report_server_error()
logger.error(traceback.format_exc())
return HttpResponse(status=500)
......@@ -44,7 +44,6 @@ from beat.core.utils import NumpyJSONEncoder
from ..algorithms.models import Algorithm
from ..toolchains.models import Toolchain
from ..utils.api import send_email_to_administrators
from ..common.models import Shareable
from ..common.models import ContributionManager
......@@ -1159,10 +1158,6 @@ class Block(models.Model):
self.outputs.update(**info)
if self.job.result.syserr: #mail admins
send_email_to_administrators('System error captured',
self.job.result.syserr)
if self.job.status == Block.SKIPPED:
self.status = Block.CACHED
else:
......
#!/usr/bin/env python
# vim: set fileencoding=utf-8 :
###############################################################################
# #
# Copyright (c) 2016 Idiap Research Institute, http://www.idiap.ch/ #
# Contact: beat.support@idiap.ch #
# #
# This file is part of the beat.web module of the BEAT platform. #
# #
# Commercial License Usage #
# Licensees holding valid commercial BEAT licenses may use this file in #
# accordance with the terms contained in a written agreement between you #
# and Idiap. For further information contact tto@idiap.ch #
# #
# Alternatively, this file may be used under the terms of the GNU Affero #
# Public License version 3 as published by the Free Software and appearing #
# in the file LICENSE.AGPL included in the packaging of this file. #
# The BEAT platform is distributed in the hope that it will be useful, but #
# WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY #
# or FITNESS FOR A PARTICULAR PURPOSE. #
# #
# You should have received a copy of the GNU Affero Public License along #
# with the BEAT platform. If not, see http://www.gnu.org/licenses/. #
# #
###############################################################################
from django.conf import settings
from django.http import HttpResponse
from django.core.mail import send_mail
import traceback
import logging
logger = logging.getLogger(__name__)
#----------------------------------------------------------
def report_server_error(additional_content=None):
try:
subject = settings.EMAIL_SUBJECT_PREFIX + 'Internal server error'
message = traceback.format_exc()
if additional_content:
message = additional_content + '\n\n' + message
send_mail(subject, message, settings.DEFAULT_FROM_EMAIL,
map(lambda x: x[1], settings.ADMINS))
except Exception:
import traceback
logger.warn("Could not send e-mail to system administrators about " \
"`%s'. Exception caught: %s", subject, traceback.format_exc())
return HttpResponse(status=500)
#----------------------------------------------------------
def send_email_to_administrators(title, content):
try:
subject = settings.EMAIL_SUBJECT_PREFIX + title
send_mail(subject, content, settings.DEFAULT_FROM_EMAIL,
map(lambda x: x[1], settings.ADMINS))
except Exception:
import traceback
logger.warn("Could not send e-mail to system administrators about " \
"`%s'. Exception caught: %s", subject, traceback.format_exc())
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment