mdk plugin download repository_evernote
+precheck
+--------
+
+Pre-checks a patch on the CI server.
+
+**Example**
+
+::
+
+ mdk precheck
+
+
purge
-----
if [[ "${COMP_CWORD}" == 1 ]]; then
# List the commands and aliases.
# Ignoring these commands on purpose: init
- OPTS="alias backport backup behat config create css doctor fix info install js phpunit plugin purge pull push rebase remove run tracker uninstall update upgrade"
+ OPTS="alias backport backup behat config create css doctor fix info install js phpunit plugin precheck purge pull push rebase remove run tracker uninstall update upgrade"
OPTS="$OPTS $($BIN alias list 2> /dev/null | cut -d ':' -f 1)"
else
# List of options according to the command.
OPTS="$OPTS $(_list_instances)"
fi
;;
+ precheck)
+ OPTS="--branch --push"
+ ;;
purge)
OPTS="--all --integration --stable --manual"
if [[ "$CUR" != -* ]]; then
--- /dev/null
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+
+"""
+Moodle Development Kit
+
+Copyright (c) 2014 Frédéric Massart - FMCorz.net
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program 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. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+http://github.com/FMCorz/mdk
+"""
+
+import logging
+from jenkinsapi import jenkins
+from jenkinsapi.custom_exceptions import JenkinsAPIException, TimeOut
+from .config import Conf
+
+C = Conf()
+
+
+class CI(object):
+ """Wrapper for Jenkins"""
+
+ _jenkins = None
+ url = None
+ token = None
+
+ def __init__(self, url=None, token=None, load=True):
+ self.url = url or C.get('ci.url')
+ self.token = token or C.get('ci.token')
+ if load:
+ self.load()
+
+ @property
+ def jenkins(self):
+ """The Jenkins object"""
+ return self._jenkins
+
+ def load(self):
+ """Loads the Jenkins object"""
+
+ # Resets the logging level.
+ logger = logging.getLogger('jenkinsapi.job')
+ logger.setLevel(logging.WARNING)
+ logger = logging.getLogger('jenkinsapi.build')
+ logger.setLevel(logging.WARNING)
+
+ # Loads the jenkins object.
+ self._jenkins = jenkins.Jenkins(self.url)
+
+ def precheckRemoteBranch(self, remote, branch, integrateto, issue=None):
+ """Runs the precheck job and returns the build object"""
+ params = {
+ 'remote': remote,
+ 'branch': branch,
+ 'integrateto': integrateto
+ }
+ if issue:
+ params['issue'] = issue
+
+ job = self.jenkins.get_job('Precheck remote branch')
+
+ try:
+ invoke = job.invoke(build_params=params, securitytoken=self.token, invoke_pre_check_delay=0)
+ invoke.block_until_not_queued(60, 2)
+ except JenkinsAPIException:
+ raise CIException('Failed to invoke the build, check your permissions.')
+ except TimeOut:
+ raise CIException('The build has been in queue for more than 60s. Aborting, please refer to: %s' % job.baseurl)
+
+ build = invoke.get_build()
+ return build
+
+
+class CIException(Exception):
+ pass
'js',
'phpunit',
'plugin',
+ 'precheck',
'pull',
'purge',
'push',
--- /dev/null
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+
+"""
+Moodle Development Kit
+
+Copyright (c) 2014 Frédéric Massart - FMCorz.net
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program 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. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+http://github.com/FMCorz/mdk
+"""
+
+import sys
+import logging
+from .. import tools, jira
+from ..ci import CI, CIException
+from ..command import Command
+
+
+class PrecheckCommand(Command):
+
+ _arguments = [
+ (
+ ['-b', '--branch'],
+ {
+ 'metavar': 'branch',
+ 'help': 'the branch to pre-check. Defaults to the current branch.'
+ }
+ ),
+ (
+ ['-p', '--push'],
+ {
+ 'action': 'store_true',
+ 'help': 'if set, the branch will be pushed to your default remote.'
+ }
+ ),
+ (
+ ['name'],
+ {
+ 'default': None,
+ 'help': 'name of the instance',
+ 'metavar': 'name',
+ 'nargs': '?'
+ }
+ )
+ ]
+ _description = 'Pre-checks a branch on the CI server'
+
+ FAILED = -1
+
+ def run(self, args):
+ M = self.Wp.resolve(args.name)
+ if not M:
+ raise Exception('This is not a Moodle instance')
+
+ against = M.get('stablebranch')
+ branch = args.branch or M.currentBranch()
+ if branch == 'HEAD':
+ raise Exception('Cannot pre-check the HEAD branch')
+ elif branch == against:
+ raise Exception('Cannot pre-check the stable branch')
+
+ parsedbranch = tools.parseBranch(branch)
+ if not parsedbranch:
+ raise Exception('Could not parse the branch')
+
+ issue = parsedbranch['issue']
+
+ if args.push:
+ J = jira.Jira()
+ if J.isSecurityIssue('MDL-%s' % (issue)):
+ raise Exception('Security issues cannot be pre-checked')
+
+ remote = self.C.get('myRemote')
+ logging.info('Pushing branch \'%s\' to remote \'%s\'', branch, remote)
+ result = M.git().push(remote, branch)
+ if result[0] != 0:
+ raise Exception('Could not push the branch:\n %s' % result[2])
+
+ ci = CI()
+ try:
+ # TODO Remove that ugly hack to get the read-only remote.
+ logging.info('Invoking the build on the CI server...')
+ build = ci.precheckRemoteBranch(self.C.get('repositoryUrl'), branch, against, 'MDL-%s' % issue)
+ except CIException as e:
+ raise e
+
+ logging.info('Waiting for the build to complete, please wait...')
+ build.block_until_complete(3)
+
+ if build.is_good():
+ logging.info('Precheck passed, good work!')
+ sys.exit(0)
+ else:
+ logging.warning('Precheck failed, refer to:\n %s', build.baseurl)
+ sys.exit(self.FAILED)
"pgsql": "PostgreSQL"
},
+ // CI Server related settings
+ "ci": {
+ "url": "http://integration.moodle.org",
+ "token": null
+ },
+
// The information for integrating MDK with Jira
"tracker": {
"url": "https://tracker.moodle.org/",
// This is used to populate the fields on the tracker issue.
"diffUrlTemplate": "https://github.com/YourGitHub/moodle/compare/%headcommit%...%branch%",
- // The public acccess URL of your repository. It is used to populate the fields on the tracker issue.
+ // The public acccess URL of your repository. It is used to populate the fields on the tracker issue,
+ // and as the common read-only URL of the remote 'myRemote'.
"repositoryUrl": "git://github.com/YourGitHub/moodle.git",
// Plugins related settings.
keyring>=3.5
+jenkinsapi>=0.2.25
MySQL-python>=1.2.3
psycopg2>=2.4.5
requests>=2.2.1