All of lore.kernel.org
 help / color / mirror / Atom feed
* [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build
@ 2017-02-01 20:12 Aníbal Limón
  2017-02-01 20:14 ` Aníbal Limón
  0 siblings, 1 reply; 5+ messages in thread
From: Aníbal Limón @ 2017-02-01 20:12 UTC (permalink / raw)
  To: yocto; +Cc: joshua.g.lock

The script supports to list avaialable builders and his options,
also can force a build if the builder is IDLE or not.

Also supports specify options via cmdline using python dictionaries
as string.

Signed-off-by: Aníbal Limón <anibal.limon@linux.intel.com>
---
 bin/forcebuild.py | 183 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 183 insertions(+)
 create mode 100755 bin/forcebuild.py

diff --git a/bin/forcebuild.py b/bin/forcebuild.py
new file mode 100755
index 0000000..5fe61a0
--- /dev/null
+++ b/bin/forcebuild.py
@@ -0,0 +1,183 @@
+#!/usr/bin/env python
+
+# YoctoAutobuilder force build script
+#
+# Copyright (C) 2017 Intel Corporation
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2 as
+# published by the Free Software Foundation.
+#
+# 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, write to the Free Software Foundation, Inc.,
+# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+
+import urllib2
+import urllib
+import cookielib
+import uuid
+import sys
+import argparse
+import json
+from bs4 import BeautifulSoup
+
+class YoctoAutobuilderAPI(object):
+    def __init__(self, server):
+        self.server = server
+        self.opener = urllib2.build_opener(
+                urllib2.HTTPCookieProcessor(cookielib.CookieJar()))
+
+    def login(self, user, passwd):
+        data = urllib.urlencode(dict(username=user,
+                                     passwd=passwd))
+        url = self.server + "/login"
+        request = urllib2.Request(url, data)
+        result = self.opener.open(request).read()
+        if result.find("The username or password you entered were not correct") > 0:
+            print("Invalid username or password")
+            return 1
+        return 0
+
+    def _get_builders(self):
+        url = "%s/json/builders/?as_text=1" % (self.server)
+        request = urllib2.Request(url)
+        json_raw_data = self.opener.open(request)
+
+        return json.load(json_raw_data)
+
+    def list_builders(self):
+        builders = self._get_builders()
+
+        if builders:
+            print('Available builders:\n')
+            for builder in builders:
+                print(builder)
+            return 0
+        else:
+            print('No available builders in this server.')
+            return 1
+
+    def _get_options_by_builder(self, builder):
+        options = {}
+
+        url = "%s/builders/%s" % (self.server, builder)
+        request = urllib2.Request(url)
+        html = self.opener.open(request).read()
+
+        inputs = BeautifulSoup(html, 'lxml').find_all('input')
+        for input in inputs:
+            type = input.attrs['type']
+            if  type == 'submit':
+                continue
+
+            options[input.attrs['name']] = input.attrs['value']
+
+        selects = BeautifulSoup(html, 'lxml').find_all('select')
+        for select in selects:
+            value = select.find_all('option', selected=True)[0].getText()
+            options[select.attrs['name']] = value
+
+        return options
+
+    def list_options(self, builder):
+        builders = self._get_builders()
+        if not builder in builders:
+            print('Builder %s specified isn\'t available' % builder)
+            return 1
+
+        opts = self._get_options_by_builder(builder)
+        print('Available options in builder %s:\n' % (builder))
+        for name in opts:
+            value = opts[name]
+            print('Name: %s, Default value: %s' % (name, value))
+
+    def force_build(self, builder, opts, idle_check=False):
+        builders = self._get_builders()
+        if not builder in builders:
+            print('Builder specified isn\'t available')
+            return 1
+
+        state = builders[builder]['state']
+        if idle_check and not state == 'idle':
+            print('Builder %s specified isn\'t IDLE, current state %s' \
+                    % (builder, state))
+            return 1
+
+        opts = eval(opts) # FIXME: transform string argument into dictionary, security?
+        current_opts = self._get_options_by_builder(builder)
+        for opt in opts:
+            if not opt in current_opts:
+                print('Option %s isn\'t supported by builder %s' % \
+                        (opt, builder))
+                return 1
+            else:
+                current_opts[opt] = opts[opt]
+
+        url_params = urllib.urlencode(current_opts)
+        url = "%s/builders/%s/force" % (self.server, builder)
+        request = urllib2.Request(url, url_params)
+        result = self.opener.open(request)
+        if 'Forced build' in result.read():
+            return 0
+        else:
+            print("Failed to force build")
+            return 1
+
+def main():
+    parser = argparse.ArgumentParser(description="Yocto Autobuilder force build script",
+            add_help=False)
+    parser.add_argument('-s', '--server', help='Server URL',
+            action='store', required=True)
+
+    parser.add_argument('-u', '--username', action='store', required=True)
+    parser.add_argument('-p', '--password', action='store', required=True)
+
+    group = parser.add_mutually_exclusive_group()
+    group.add_argument('--list-builders', help='List available builders',
+            action='store_true')
+    group.add_argument('--list-options', help='List options by builder',
+            action='store', metavar='BUILDER')
+    group.add_argument('--force-build', help='Force build by builder',
+            action='store', metavar='BUILDER')
+    group.add_argument('--force-build-idle', help='Force build by builder if is idle',
+            action='store', metavar='BUILDER')
+
+    parser.add_argument('-o', '--options', help='Custom options by operation',
+            action='store')
+
+    parser.add_argument('-d', '--debug', help='Enable debug output',
+            action='store_true')
+    parser.add_argument('-q', '--quiet', help='Print only errors',
+            action='store_true')
+
+    parser.add_argument('-h', '--help', action='help', default=argparse.SUPPRESS,
+                        help='show this help message and exit')
+
+    args = parser.parse_args()
+
+    api = YoctoAutobuilderAPI(args.server)
+    if api.login(args.username, args.password):
+        return 1
+
+    if args.list_builders:
+        return api.list_builders()
+    elif args.list_options:
+        return api.list_options(args.list_options)
+    elif args.force_build:
+        return api.force_build(args.force_build, args.options)
+    elif args.force_build_idle:
+        return api.force_build(args.force_build_idle, args.options, idle_check=True)
+
+if __name__ == '__main__':
+    try:
+        ret = main()
+    except Exception:
+        ret = 1
+        import traceback
+        traceback.print_exc()
+    sys.exit(ret)
-- 
2.1.4



^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build
  2017-02-01 20:12 [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build Aníbal Limón
@ 2017-02-01 20:14 ` Aníbal Limón
  2017-02-08 14:12   ` Lock, Joshua G
  0 siblings, 1 reply; 5+ messages in thread
From: Aníbal Limón @ 2017-02-01 20:14 UTC (permalink / raw)
  To: yocto; +Cc: joshua.g.lock

[-- Attachment #1: Type: text/plain, Size: 8166 bytes --]

I know we have the remote_kick.py [1] script but i don't know if is
currently on use also this new script support list the options in
builders and specify custom ones via cmdline.

Cheers,
	alimon

[1]
http://git.yoctoproject.org/cgit/cgit.cgi/yocto-autobuilder/tree/bin/remote_kick.py

On 02/01/2017 02:12 PM, Aníbal Limón wrote:
> The script supports to list avaialable builders and his options,
> also can force a build if the builder is IDLE or not.
> 
> Also supports specify options via cmdline using python dictionaries
> as string.
> 
> Signed-off-by: Aníbal Limón <anibal.limon@linux.intel.com>
> ---
>  bin/forcebuild.py | 183 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
>  1 file changed, 183 insertions(+)
>  create mode 100755 bin/forcebuild.py
> 
> diff --git a/bin/forcebuild.py b/bin/forcebuild.py
> new file mode 100755
> index 0000000..5fe61a0
> --- /dev/null
> +++ b/bin/forcebuild.py
> @@ -0,0 +1,183 @@
> +#!/usr/bin/env python
> +
> +# YoctoAutobuilder force build script
> +#
> +# Copyright (C) 2017 Intel Corporation
> +#
> +# This program is free software; you can redistribute it and/or modify
> +# it under the terms of the GNU General Public License version 2 as
> +# published by the Free Software Foundation.
> +#
> +# 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, write to the Free Software Foundation, Inc.,
> +# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
> +
> +import urllib2
> +import urllib
> +import cookielib
> +import uuid
> +import sys
> +import argparse
> +import json
> +from bs4 import BeautifulSoup
> +
> +class YoctoAutobuilderAPI(object):
> +    def __init__(self, server):
> +        self.server = server
> +        self.opener = urllib2.build_opener(
> +                urllib2.HTTPCookieProcessor(cookielib.CookieJar()))
> +
> +    def login(self, user, passwd):
> +        data = urllib.urlencode(dict(username=user,
> +                                     passwd=passwd))
> +        url = self.server + "/login"
> +        request = urllib2.Request(url, data)
> +        result = self.opener.open(request).read()
> +        if result.find("The username or password you entered were not correct") > 0:
> +            print("Invalid username or password")
> +            return 1
> +        return 0
> +
> +    def _get_builders(self):
> +        url = "%s/json/builders/?as_text=1" % (self.server)
> +        request = urllib2.Request(url)
> +        json_raw_data = self.opener.open(request)
> +
> +        return json.load(json_raw_data)
> +
> +    def list_builders(self):
> +        builders = self._get_builders()
> +
> +        if builders:
> +            print('Available builders:\n')
> +            for builder in builders:
> +                print(builder)
> +            return 0
> +        else:
> +            print('No available builders in this server.')
> +            return 1
> +
> +    def _get_options_by_builder(self, builder):
> +        options = {}
> +
> +        url = "%s/builders/%s" % (self.server, builder)
> +        request = urllib2.Request(url)
> +        html = self.opener.open(request).read()
> +
> +        inputs = BeautifulSoup(html, 'lxml').find_all('input')
> +        for input in inputs:
> +            type = input.attrs['type']
> +            if  type == 'submit':
> +                continue
> +
> +            options[input.attrs['name']] = input.attrs['value']
> +
> +        selects = BeautifulSoup(html, 'lxml').find_all('select')
> +        for select in selects:
> +            value = select.find_all('option', selected=True)[0].getText()
> +            options[select.attrs['name']] = value
> +
> +        return options
> +
> +    def list_options(self, builder):
> +        builders = self._get_builders()
> +        if not builder in builders:
> +            print('Builder %s specified isn\'t available' % builder)
> +            return 1
> +
> +        opts = self._get_options_by_builder(builder)
> +        print('Available options in builder %s:\n' % (builder))
> +        for name in opts:
> +            value = opts[name]
> +            print('Name: %s, Default value: %s' % (name, value))
> +
> +    def force_build(self, builder, opts, idle_check=False):
> +        builders = self._get_builders()
> +        if not builder in builders:
> +            print('Builder specified isn\'t available')
> +            return 1
> +
> +        state = builders[builder]['state']
> +        if idle_check and not state == 'idle':
> +            print('Builder %s specified isn\'t IDLE, current state %s' \
> +                    % (builder, state))
> +            return 1
> +
> +        opts = eval(opts) # FIXME: transform string argument into dictionary, security?
> +        current_opts = self._get_options_by_builder(builder)
> +        for opt in opts:
> +            if not opt in current_opts:
> +                print('Option %s isn\'t supported by builder %s' % \
> +                        (opt, builder))
> +                return 1
> +            else:
> +                current_opts[opt] = opts[opt]
> +
> +        url_params = urllib.urlencode(current_opts)
> +        url = "%s/builders/%s/force" % (self.server, builder)
> +        request = urllib2.Request(url, url_params)
> +        result = self.opener.open(request)
> +        if 'Forced build' in result.read():
> +            return 0
> +        else:
> +            print("Failed to force build")
> +            return 1
> +
> +def main():
> +    parser = argparse.ArgumentParser(description="Yocto Autobuilder force build script",
> +            add_help=False)
> +    parser.add_argument('-s', '--server', help='Server URL',
> +            action='store', required=True)
> +
> +    parser.add_argument('-u', '--username', action='store', required=True)
> +    parser.add_argument('-p', '--password', action='store', required=True)
> +
> +    group = parser.add_mutually_exclusive_group()
> +    group.add_argument('--list-builders', help='List available builders',
> +            action='store_true')
> +    group.add_argument('--list-options', help='List options by builder',
> +            action='store', metavar='BUILDER')
> +    group.add_argument('--force-build', help='Force build by builder',
> +            action='store', metavar='BUILDER')
> +    group.add_argument('--force-build-idle', help='Force build by builder if is idle',
> +            action='store', metavar='BUILDER')
> +
> +    parser.add_argument('-o', '--options', help='Custom options by operation',
> +            action='store')
> +
> +    parser.add_argument('-d', '--debug', help='Enable debug output',
> +            action='store_true')
> +    parser.add_argument('-q', '--quiet', help='Print only errors',
> +            action='store_true')
> +
> +    parser.add_argument('-h', '--help', action='help', default=argparse.SUPPRESS,
> +                        help='show this help message and exit')
> +
> +    args = parser.parse_args()
> +
> +    api = YoctoAutobuilderAPI(args.server)
> +    if api.login(args.username, args.password):
> +        return 1
> +
> +    if args.list_builders:
> +        return api.list_builders()
> +    elif args.list_options:
> +        return api.list_options(args.list_options)
> +    elif args.force_build:
> +        return api.force_build(args.force_build, args.options)
> +    elif args.force_build_idle:
> +        return api.force_build(args.force_build_idle, args.options, idle_check=True)
> +
> +if __name__ == '__main__':
> +    try:
> +        ret = main()
> +    except Exception:
> +        ret = 1
> +        import traceback
> +        traceback.print_exc()
> +    sys.exit(ret)
> 


[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 836 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build
  2017-02-01 20:14 ` Aníbal Limón
@ 2017-02-08 14:12   ` Lock, Joshua G
  2017-02-08 15:10     ` Aníbal Limón
  0 siblings, 1 reply; 5+ messages in thread
From: Lock, Joshua G @ 2017-02-08 14:12 UTC (permalink / raw)
  To: anibal.limon, yocto

On Wed, 2017-02-01 at 14:14 -0600, Aníbal Limón wrote:
> I know we have the remote_kick.py [1] script but i don't know if is
> currently on use also this new script support list the options in
> builders and specify custom ones via cmdline.

I don't use remote_kick.py, I'm loathe to carry two scripts with a
similar purpose. Any idea how they differ?

Thanks,

Joshua

> Cheers,
> 	alimon
> 
> [1]
> http://git.yoctoproject.org/cgit/cgit.cgi/yocto-autobuilder/tree/bin/
> remote_kick.py
> 
> On 02/01/2017 02:12 PM, Aníbal Limón wrote:
> > The script supports to list avaialable builders and his options,
> > also can force a build if the builder is IDLE or not.
> > 
> > Also supports specify options via cmdline using python dictionaries
> > as string.
> > 
> > Signed-off-by: Aníbal Limón <anibal.limon@linux.intel.com>
> > ---
> >  bin/forcebuild.py | 183
> > ++++++++++++++++++++++++++++++++++++++++++++++++++++++
> >  1 file changed, 183 insertions(+)
> >  create mode 100755 bin/forcebuild.py
> > 
> > diff --git a/bin/forcebuild.py b/bin/forcebuild.py
> > new file mode 100755
> > index 0000000..5fe61a0
> > --- /dev/null
> > +++ b/bin/forcebuild.py
> > @@ -0,0 +1,183 @@
> > +#!/usr/bin/env python
> > +
> > +# YoctoAutobuilder force build script
> > +#
> > +# Copyright (C) 2017 Intel Corporation
> > +#
> > +# This program is free software; you can redistribute it and/or
> > modify
> > +# it under the terms of the GNU General Public License version 2
> > as
> > +# published by the Free Software Foundation.
> > +#
> > +# 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, write to the Free Software
> > Foundation, Inc.,
> > +# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
> > +
> > +import urllib2
> > +import urllib
> > +import cookielib
> > +import uuid
> > +import sys
> > +import argparse
> > +import json
> > +from bs4 import BeautifulSoup
> > +
> > +class YoctoAutobuilderAPI(object):
> > +    def __init__(self, server):
> > +        self.server = server
> > +        self.opener = urllib2.build_opener(
> > +                urllib2.HTTPCookieProcessor(cookielib.CookieJar())
> > )
> > +
> > +    def login(self, user, passwd):
> > +        data = urllib.urlencode(dict(username=user,
> > +                                     passwd=passwd))
> > +        url = self.server + "/login"
> > +        request = urllib2.Request(url, data)
> > +        result = self.opener.open(request).read()
> > +        if result.find("The username or password you entered were
> > not correct") > 0:
> > +            print("Invalid username or password")
> > +            return 1
> > +        return 0
> > +
> > +    def _get_builders(self):
> > +        url = "%s/json/builders/?as_text=1" % (self.server)
> > +        request = urllib2.Request(url)
> > +        json_raw_data = self.opener.open(request)
> > +
> > +        return json.load(json_raw_data)
> > +
> > +    def list_builders(self):
> > +        builders = self._get_builders()
> > +
> > +        if builders:
> > +            print('Available builders:\n')
> > +            for builder in builders:
> > +                print(builder)
> > +            return 0
> > +        else:
> > +            print('No available builders in this server.')
> > +            return 1
> > +
> > +    def _get_options_by_builder(self, builder):
> > +        options = {}
> > +
> > +        url = "%s/builders/%s" % (self.server, builder)
> > +        request = urllib2.Request(url)
> > +        html = self.opener.open(request).read()
> > +
> > +        inputs = BeautifulSoup(html, 'lxml').find_all('input')
> > +        for input in inputs:
> > +            type = input.attrs['type']
> > +            if  type == 'submit':
> > +                continue
> > +
> > +            options[input.attrs['name']] = input.attrs['value']
> > +
> > +        selects = BeautifulSoup(html, 'lxml').find_all('select')
> > +        for select in selects:
> > +            value = select.find_all('option',
> > selected=True)[0].getText()
> > +            options[select.attrs['name']] = value
> > +
> > +        return options
> > +
> > +    def list_options(self, builder):
> > +        builders = self._get_builders()
> > +        if not builder in builders:
> > +            print('Builder %s specified isn\'t available' %
> > builder)
> > +            return 1
> > +
> > +        opts = self._get_options_by_builder(builder)
> > +        print('Available options in builder %s:\n' % (builder))
> > +        for name in opts:
> > +            value = opts[name]
> > +            print('Name: %s, Default value: %s' % (name, value))
> > +
> > +    def force_build(self, builder, opts, idle_check=False):
> > +        builders = self._get_builders()
> > +        if not builder in builders:
> > +            print('Builder specified isn\'t available')
> > +            return 1
> > +
> > +        state = builders[builder]['state']
> > +        if idle_check and not state == 'idle':
> > +            print('Builder %s specified isn\'t IDLE, current state
> > %s' \
> > +                    % (builder, state))
> > +            return 1
> > +
> > +        opts = eval(opts) # FIXME: transform string argument into
> > dictionary, security?
> > +        current_opts = self._get_options_by_builder(builder)
> > +        for opt in opts:
> > +            if not opt in current_opts:
> > +                print('Option %s isn\'t supported by builder %s' %
> > \
> > +                        (opt, builder))
> > +                return 1
> > +            else:
> > +                current_opts[opt] = opts[opt]
> > +
> > +        url_params = urllib.urlencode(current_opts)
> > +        url = "%s/builders/%s/force" % (self.server, builder)
> > +        request = urllib2.Request(url, url_params)
> > +        result = self.opener.open(request)
> > +        if 'Forced build' in result.read():
> > +            return 0
> > +        else:
> > +            print("Failed to force build")
> > +            return 1
> > +
> > +def main():
> > +    parser = argparse.ArgumentParser(description="Yocto
> > Autobuilder force build script",
> > +            add_help=False)
> > +    parser.add_argument('-s', '--server', help='Server URL',
> > +            action='store', required=True)
> > +
> > +    parser.add_argument('-u', '--username', action='store',
> > required=True)
> > +    parser.add_argument('-p', '--password', action='store',
> > required=True)
> > +
> > +    group = parser.add_mutually_exclusive_group()
> > +    group.add_argument('--list-builders', help='List available
> > builders',
> > +            action='store_true')
> > +    group.add_argument('--list-options', help='List options by
> > builder',
> > +            action='store', metavar='BUILDER')
> > +    group.add_argument('--force-build', help='Force build by
> > builder',
> > +            action='store', metavar='BUILDER')
> > +    group.add_argument('--force-build-idle', help='Force build by
> > builder if is idle',
> > +            action='store', metavar='BUILDER')
> > +
> > +    parser.add_argument('-o', '--options', help='Custom options by
> > operation',
> > +            action='store')
> > +
> > +    parser.add_argument('-d', '--debug', help='Enable debug
> > output',
> > +            action='store_true')
> > +    parser.add_argument('-q', '--quiet', help='Print only errors',
> > +            action='store_true')
> > +
> > +    parser.add_argument('-h', '--help', action='help',
> > default=argparse.SUPPRESS,
> > +                        help='show this help message and exit')
> > +
> > +    args = parser.parse_args()
> > +
> > +    api = YoctoAutobuilderAPI(args.server)
> > +    if api.login(args.username, args.password):
> > +        return 1
> > +
> > +    if args.list_builders:
> > +        return api.list_builders()
> > +    elif args.list_options:
> > +        return api.list_options(args.list_options)
> > +    elif args.force_build:
> > +        return api.force_build(args.force_build, args.options)
> > +    elif args.force_build_idle:
> > +        return api.force_build(args.force_build_idle,
> > args.options, idle_check=True)
> > +
> > +if __name__ == '__main__':
> > +    try:
> > +        ret = main()
> > +    except Exception:
> > +        ret = 1
> > +        import traceback
> > +        traceback.print_exc()
> > +    sys.exit(ret)
> > 
> 
> 
---------------------------------------------------------------------
Intel Corporation (UK) Limited
Registered No. 1134945 (England)
Registered Office: Pipers Way, Swindon SN3 1RJ
VAT No: 860 2173 47

This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build
  2017-02-08 14:12   ` Lock, Joshua G
@ 2017-02-08 15:10     ` Aníbal Limón
  2017-02-15 13:57       ` Lock, Joshua G
  0 siblings, 1 reply; 5+ messages in thread
From: Aníbal Limón @ 2017-02-08 15:10 UTC (permalink / raw)
  To: Lock, Joshua G, yocto

[-- Attachment #1: Type: text/plain, Size: 9258 bytes --]



On 02/08/2017 08:12 AM, Lock, Joshua G wrote:
> On Wed, 2017-02-01 at 14:14 -0600, Aníbal Limón wrote:
>> I know we have the remote_kick.py [1] script but i don't know if is
>> currently on use also this new script support list the options in
>> builders and specify custom ones via cmdline.
> 
> I don't use remote_kick.py, I'm loathe to carry two scripts with a
> similar purpose. Any idea how they differ?

The remote_kick script has a fixed set of parameters like builder
(nigthly), buildbot url (localhost:8010) and forces the same build.

The new forcebuild script you can specify buildbot server url, user,
password, builder and options (WEB inputs).

Cheers,
	alimon

> 
> Thanks,
> 
> Joshua
> 
>> Cheers,
>> 	alimon
>>
>> [1]
>> http://git.yoctoproject.org/cgit/cgit.cgi/yocto-autobuilder/tree/bin/
>> remote_kick.py
>>
>> On 02/01/2017 02:12 PM, Aníbal Limón wrote:
>>> The script supports to list avaialable builders and his options,
>>> also can force a build if the builder is IDLE or not.
>>>
>>> Also supports specify options via cmdline using python dictionaries
>>> as string.
>>>
>>> Signed-off-by: Aníbal Limón <anibal.limon@linux.intel.com>
>>> ---
>>>  bin/forcebuild.py | 183
>>> ++++++++++++++++++++++++++++++++++++++++++++++++++++++
>>>  1 file changed, 183 insertions(+)
>>>  create mode 100755 bin/forcebuild.py
>>>
>>> diff --git a/bin/forcebuild.py b/bin/forcebuild.py
>>> new file mode 100755
>>> index 0000000..5fe61a0
>>> --- /dev/null
>>> +++ b/bin/forcebuild.py
>>> @@ -0,0 +1,183 @@
>>> +#!/usr/bin/env python
>>> +
>>> +# YoctoAutobuilder force build script
>>> +#
>>> +# Copyright (C) 2017 Intel Corporation
>>> +#
>>> +# This program is free software; you can redistribute it and/or
>>> modify
>>> +# it under the terms of the GNU General Public License version 2
>>> as
>>> +# published by the Free Software Foundation.
>>> +#
>>> +# 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, write to the Free Software
>>> Foundation, Inc.,
>>> +# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
>>> +
>>> +import urllib2
>>> +import urllib
>>> +import cookielib
>>> +import uuid
>>> +import sys
>>> +import argparse
>>> +import json
>>> +from bs4 import BeautifulSoup
>>> +
>>> +class YoctoAutobuilderAPI(object):
>>> +    def __init__(self, server):
>>> +        self.server = server
>>> +        self.opener = urllib2.build_opener(
>>> +                urllib2.HTTPCookieProcessor(cookielib.CookieJar())
>>> )
>>> +
>>> +    def login(self, user, passwd):
>>> +        data = urllib.urlencode(dict(username=user,
>>> +                                     passwd=passwd))
>>> +        url = self.server + "/login"
>>> +        request = urllib2.Request(url, data)
>>> +        result = self.opener.open(request).read()
>>> +        if result.find("The username or password you entered were
>>> not correct") > 0:
>>> +            print("Invalid username or password")
>>> +            return 1
>>> +        return 0
>>> +
>>> +    def _get_builders(self):
>>> +        url = "%s/json/builders/?as_text=1" % (self.server)
>>> +        request = urllib2.Request(url)
>>> +        json_raw_data = self.opener.open(request)
>>> +
>>> +        return json.load(json_raw_data)
>>> +
>>> +    def list_builders(self):
>>> +        builders = self._get_builders()
>>> +
>>> +        if builders:
>>> +            print('Available builders:\n')
>>> +            for builder in builders:
>>> +                print(builder)
>>> +            return 0
>>> +        else:
>>> +            print('No available builders in this server.')
>>> +            return 1
>>> +
>>> +    def _get_options_by_builder(self, builder):
>>> +        options = {}
>>> +
>>> +        url = "%s/builders/%s" % (self.server, builder)
>>> +        request = urllib2.Request(url)
>>> +        html = self.opener.open(request).read()
>>> +
>>> +        inputs = BeautifulSoup(html, 'lxml').find_all('input')
>>> +        for input in inputs:
>>> +            type = input.attrs['type']
>>> +            if  type == 'submit':
>>> +                continue
>>> +
>>> +            options[input.attrs['name']] = input.attrs['value']
>>> +
>>> +        selects = BeautifulSoup(html, 'lxml').find_all('select')
>>> +        for select in selects:
>>> +            value = select.find_all('option',
>>> selected=True)[0].getText()
>>> +            options[select.attrs['name']] = value
>>> +
>>> +        return options
>>> +
>>> +    def list_options(self, builder):
>>> +        builders = self._get_builders()
>>> +        if not builder in builders:
>>> +            print('Builder %s specified isn\'t available' %
>>> builder)
>>> +            return 1
>>> +
>>> +        opts = self._get_options_by_builder(builder)
>>> +        print('Available options in builder %s:\n' % (builder))
>>> +        for name in opts:
>>> +            value = opts[name]
>>> +            print('Name: %s, Default value: %s' % (name, value))
>>> +
>>> +    def force_build(self, builder, opts, idle_check=False):
>>> +        builders = self._get_builders()
>>> +        if not builder in builders:
>>> +            print('Builder specified isn\'t available')
>>> +            return 1
>>> +
>>> +        state = builders[builder]['state']
>>> +        if idle_check and not state == 'idle':
>>> +            print('Builder %s specified isn\'t IDLE, current state
>>> %s' \
>>> +                    % (builder, state))
>>> +            return 1
>>> +
>>> +        opts = eval(opts) # FIXME: transform string argument into
>>> dictionary, security?
>>> +        current_opts = self._get_options_by_builder(builder)
>>> +        for opt in opts:
>>> +            if not opt in current_opts:
>>> +                print('Option %s isn\'t supported by builder %s' %
>>> \
>>> +                        (opt, builder))
>>> +                return 1
>>> +            else:
>>> +                current_opts[opt] = opts[opt]
>>> +
>>> +        url_params = urllib.urlencode(current_opts)
>>> +        url = "%s/builders/%s/force" % (self.server, builder)
>>> +        request = urllib2.Request(url, url_params)
>>> +        result = self.opener.open(request)
>>> +        if 'Forced build' in result.read():
>>> +            return 0
>>> +        else:
>>> +            print("Failed to force build")
>>> +            return 1
>>> +
>>> +def main():
>>> +    parser = argparse.ArgumentParser(description="Yocto
>>> Autobuilder force build script",
>>> +            add_help=False)
>>> +    parser.add_argument('-s', '--server', help='Server URL',
>>> +            action='store', required=True)
>>> +
>>> +    parser.add_argument('-u', '--username', action='store',
>>> required=True)
>>> +    parser.add_argument('-p', '--password', action='store',
>>> required=True)
>>> +
>>> +    group = parser.add_mutually_exclusive_group()
>>> +    group.add_argument('--list-builders', help='List available
>>> builders',
>>> +            action='store_true')
>>> +    group.add_argument('--list-options', help='List options by
>>> builder',
>>> +            action='store', metavar='BUILDER')
>>> +    group.add_argument('--force-build', help='Force build by
>>> builder',
>>> +            action='store', metavar='BUILDER')
>>> +    group.add_argument('--force-build-idle', help='Force build by
>>> builder if is idle',
>>> +            action='store', metavar='BUILDER')
>>> +
>>> +    parser.add_argument('-o', '--options', help='Custom options by
>>> operation',
>>> +            action='store')
>>> +
>>> +    parser.add_argument('-d', '--debug', help='Enable debug
>>> output',
>>> +            action='store_true')
>>> +    parser.add_argument('-q', '--quiet', help='Print only errors',
>>> +            action='store_true')
>>> +
>>> +    parser.add_argument('-h', '--help', action='help',
>>> default=argparse.SUPPRESS,
>>> +                        help='show this help message and exit')
>>> +
>>> +    args = parser.parse_args()
>>> +
>>> +    api = YoctoAutobuilderAPI(args.server)
>>> +    if api.login(args.username, args.password):
>>> +        return 1
>>> +
>>> +    if args.list_builders:
>>> +        return api.list_builders()
>>> +    elif args.list_options:
>>> +        return api.list_options(args.list_options)
>>> +    elif args.force_build:
>>> +        return api.force_build(args.force_build, args.options)
>>> +    elif args.force_build_idle:
>>> +        return api.force_build(args.force_build_idle,
>>> args.options, idle_check=True)
>>> +
>>> +if __name__ == '__main__':
>>> +    try:
>>> +        ret = main()
>>> +    except Exception:
>>> +        ret = 1
>>> +        import traceback
>>> +        traceback.print_exc()
>>> +    sys.exit(ret)
>>>
>>


[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 836 bytes --]

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build
  2017-02-08 15:10     ` Aníbal Limón
@ 2017-02-15 13:57       ` Lock, Joshua G
  0 siblings, 0 replies; 5+ messages in thread
From: Lock, Joshua G @ 2017-02-15 13:57 UTC (permalink / raw)
  To: anibal.limon, yocto

On Wed, 2017-02-08 at 09:10 -0600, Aníbal Limón wrote:
> 
> On 02/08/2017 08:12 AM, Lock, Joshua G wrote:
> > On Wed, 2017-02-01 at 14:14 -0600, Aníbal Limón wrote:
> > > I know we have the remote_kick.py [1] script but i don't know if
> > > is
> > > currently on use also this new script support list the options in
> > > builders and specify custom ones via cmdline.
> > 
> > I don't use remote_kick.py, I'm loathe to carry two scripts with a
> > similar purpose. Any idea how they differ?
> 
> The remote_kick script has a fixed set of parameters like builder
> (nigthly), buildbot url (localhost:8010) and forces the same build.
> 
> The new forcebuild script you can specify buildbot server url, user,
> password, builder and options (WEB inputs).

Thank you. I've queued up this patch for inclusion with a follow-on
patch that removes remote_kick with the above as reasoning.

Joshua
---------------------------------------------------------------------
Intel Corporation (UK) Limited
Registered No. 1134945 (England)
Registered Office: Pipers Way, Swindon SN3 1RJ
VAT No: 860 2173 47

This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2017-02-15 13:57 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-02-01 20:12 [[PATCH][yocto-autobuilder]] bin/forcebuild.py: Add a script to support force a build Aníbal Limón
2017-02-01 20:14 ` Aníbal Limón
2017-02-08 14:12   ` Lock, Joshua G
2017-02-08 15:10     ` Aníbal Limón
2017-02-15 13:57       ` Lock, Joshua G

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.