Merge branch 'release_19.05' into dev

This commit is contained in:
John Chilton
2019-06-10 15:01:42 -04:00
9 changed files with 66 additions and 26 deletions
+5
View File
@@ -393,6 +393,11 @@ Enhancements
Fixes
-------------------------------
* Explicitly specify system user under which Kubernetes jobs should run.
`Pull Request 8103`_
* Ensure Kubernetes job querries filter the same namespace as defined in the
job destination.
`Pull Request 8092`_
* Fix client styleguide asset handling.
`Pull Request 7664`_
* Handle subworkflows in view workflow mako
+2
View File
@@ -1,5 +1,7 @@
.. github_links
.. _Pull Request 8103: https://github.com/galaxyproject/galaxy/pull/8103
.. _Pull Request 8092: https://github.com/galaxyproject/galaxy/pull/8092
.. _Pull Request 4659: https://github.com/galaxyproject/galaxy/pull/4659
.. _Pull Request 5495: https://github.com/galaxyproject/galaxy/pull/5495
.. _Pull Request 6321: https://github.com/galaxyproject/galaxy/pull/6321
+40 -12
View File
@@ -54,6 +54,8 @@ class KubernetesJobRunner(AsynchronousJobRunner):
k8s_job_api_version=dict(map=str, default="batch/v1"),
k8s_supplemental_group_id=dict(map=str),
k8s_pull_policy=dict(map=str, default="Default"),
k8s_run_as_user_id=dict(map=str, valid=lambda s: s == "$uid" or s.isdigit()),
k8s_run_as_group_id=dict(map=str, valid=lambda s: s == "$gid" or s.isdigit()),
k8s_fs_group_id=dict(map=int),
k8s_default_requests_cpu=dict(map=str, default=None),
k8s_default_requests_memory=dict(map=str, default=None),
@@ -76,6 +78,8 @@ class KubernetesJobRunner(AsynchronousJobRunner):
self._galaxy_instance_id = self.__get_galaxy_instance_id()
self._run_as_user_id = self.__get_run_as_user_id()
self._run_as_group_id = self.__get_run_as_group_id()
self._supplemental_group = self.__get_supplemental_group()
self._fs_group = self.__get_fs_group()
self._default_pull_policy = self.__get_pull_policy()
@@ -169,6 +173,24 @@ class KubernetesJobRunner(AsynchronousJobRunner):
return self.runner_params['k8s_pull_policy']
return None
def __get_run_as_user_id(self):
if "k8s_run_as_user_id" in self.runner_params:
run_as_user = self.runner_params["k8s_run_as_user_id"]
if run_as_user == "$uid":
return os.getuid()
else:
return int(self.runner_params["k8s_run_as_user_id"])
return None
def __get_run_as_group_id(self):
if "k8s_run_as_group_id" in self.runner_params:
run_as_group = self.runner_params["k8s_run_as_group_id"]
if run_as_group == "$gid":
return self.app.config.gid
else:
return int(self.runner_params["k8s_run_as_group_id"])
return None
def __get_supplemental_group(self):
if "k8s_supplemental_group_id" in self.runner_params:
try:
@@ -238,17 +260,21 @@ class KubernetesJobRunner(AsynchronousJobRunner):
}
# TODO include other relevant elements that people might want to use from
# TODO http://kubernetes.io/docs/api-reference/v1/definitions/#_v1_podspec
if self._supplemental_group and self._supplemental_group > 0:
k8s_spec_template["spec"]["securityContext"] = dict(supplementalGroups=[self._supplemental_group])
if self._fs_group and self._fs_group > 0:
if "securityContext" in k8s_spec_template["spec"]:
k8s_spec_template["spec"]["securityContext"]["fsGroup"] = self._fs_group
else:
k8s_spec_template["spec"]["securityContext"] = dict(fsGroup=self._fs_group)
k8s_spec_template["spec"]["securityContext"] = self.__get_k8s_security_context()
return k8s_spec_template
def __get_k8s_security_context(self):
security_context = {}
if self._run_as_user_id:
security_context["runAsUser"] = self._run_as_user_id
if self._run_as_group_id:
security_context["runAsGroup"] = self._run_as_group_id
if self._supplemental_group and self._supplemental_group > 0:
security_context["supplementalGroups"] = [self._supplemental_group]
if self._fs_group and self._fs_group > 0:
security_context["fsGroup"] = self._fs_group
return security_context
def __get_k8s_restart_policy(self, job_wrapper):
"""The default Kubernetes restart policy for Jobs"""
return "Never"
@@ -475,7 +501,8 @@ class KubernetesJobRunner(AsynchronousJobRunner):
marks the job for resubmission (resubmit logic is part of destinations).
"""
pods = Pod.objects(self._pykube_api).filter(selector="app=%s" % job_state.job_id)
pods = Pod.objects(self._pykube_api).filter(selector="app=%s" % job_state.job_id,
namespace=self.runner_params['k8s_namespace'])
pod = Pod(self._pykube_api, pods.response['items'][0])
if pod.obj['status']['phase'] == "Failed" and \
@@ -488,8 +515,9 @@ class KubernetesJobRunner(AsynchronousJobRunner):
"""Attempts to delete a dispatched job to the k8s cluster"""
job = job_wrapper.get_job()
try:
jobs = Job.objects(self._pykube_api).filter(selector="app=" +
self.__produce_unique_k8s_job_name(job.get_id_tag()))
jobs = Job.objects(self._pykube_api).filter(
selector="app=" + self.__produce_unique_k8s_job_name(job.get_id_tag()),
namespace=self.runner_params['k8s_namespace'])
if len(jobs.response['items']) >= 0:
job_to_delete = Job(self._pykube_api, jobs.response['items'][0])
job_to_delete.scale(replicas=0)
+3 -1
View File
@@ -65,7 +65,9 @@
${ galaxy_client.load( app=self.js_app ) }
${ galaxy_client.config_sentry( app=self.js_app ) }
${ galaxy_client.config_google_analytics( app=self.js_app ) }
%if self.js_app and self.js_app.config and self.js_app.config.ga_code:
${ galaxy_client.config_google_analytics(self.js_app.config.ga_code) }
%endif
%if not form_input_auto_focus is UNDEFINED and form_input_auto_focus:
<script type="text/javascript">
+1 -1
View File
@@ -70,7 +70,7 @@
</script>
%if t.webapp.name == 'galaxy' and app.config.ga_code:
${galaxy_client.config_google_analytics(app)}
${galaxy_client.config_google_analytics(app.config.ga_code)}
%endif
</%def>
+9 -8
View File
@@ -39,8 +39,6 @@ ${ h.dumps( dictionary, indent=( 2 if trans.debug else 0 ) ) }
%if app and app.config:
<script type="text/javascript">
// TODO: make this work the same in all places, maybe
// make a global func in galaxy_client_app?
var sentry = {};
%if app.config.sentry_dsn:
sentry.sentry_dsn_public = "${app.config.sentry_dsn_public}"
@@ -57,17 +55,20 @@ ${ h.dumps( dictionary, indent=( 2 if trans.debug else 0 ) ) }
%endif
</%def>
<%def name="config_google_analytics(app)">
%if app and app.config and app.config.ga_code:
<script>
<%def name="config_google_analytics(ga_code)">
<script>
console.log("config_google_analytics ga_code:", '${ga_code}');
%if ga_code:
(function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
(i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
})(window,document,'script','//www.google-analytics.com/analytics.js','ga');
ga('create', '${app.config.ga_code}', 'auto');
ga('create', '${ga_code}', 'auto');
ga('send', 'pageview');
</script>
%endif
%else:
console.warn("Missing google analytics code");
%endif
</script>
</%def>
+4 -2
View File
@@ -74,8 +74,10 @@
</script>
%endif
## ${ galaxy_client.config_sentry(app)}
## ${ galaxy_client.config_google_analytics(app)}
${ galaxy_client.config_sentry(app) }
%if app.config.ga_code:
${ galaxy_client.config_google_analytics(app.config.ga_code) }
%endif
</%def>
+1 -1
View File
@@ -225,7 +225,7 @@
</script>
${ galaxy_client.load() }
## ${ galaxy_client.config_sentry(app) }
${ galaxy_client.config_sentry(app) }
</%def>
+1 -1
View File
@@ -46,7 +46,7 @@
<%def name="masthead()">
%if app.config.ga_code:
${galaxy_client.config_google_analytics(app)}
${ galaxy_client.config_google_analytics(app.config.ga_code)}
%endif
## start main tag