xref: /OK3568_Linux_fs/yocto/poky/bitbake/lib/toaster/bldcontrol/bbcontroller.py (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun#
2*4882a593Smuzhiyun# BitBake Toaster Implementation
3*4882a593Smuzhiyun#
4*4882a593Smuzhiyun# Copyright (C) 2014        Intel Corporation
5*4882a593Smuzhiyun#
6*4882a593Smuzhiyun# SPDX-License-Identifier: GPL-2.0-only
7*4882a593Smuzhiyun#
8*4882a593Smuzhiyun
9*4882a593Smuzhiyunimport os
10*4882a593Smuzhiyunimport sys
11*4882a593Smuzhiyunfrom django.db.models import Q
12*4882a593Smuzhiyunfrom bldcontrol.models import BuildEnvironment, BRLayer, BRBitbake
13*4882a593Smuzhiyun
14*4882a593Smuzhiyun# load Bitbake components
15*4882a593Smuzhiyunpath = os.path.join(os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))))
16*4882a593Smuzhiyunsys.path.insert(0, path)
17*4882a593Smuzhiyun
18*4882a593Smuzhiyunclass BitbakeController(object):
19*4882a593Smuzhiyun    """ This is the basic class that controlls a bitbake server.
20*4882a593Smuzhiyun        It is outside the scope of this class on how the server is started and aquired
21*4882a593Smuzhiyun    """
22*4882a593Smuzhiyun
23*4882a593Smuzhiyun    def __init__(self, be):
24*4882a593Smuzhiyun        import bb.server.xmlrpcclient
25*4882a593Smuzhiyun        self.connection = bb.server.xmlrpcclient._create_server(be.bbaddress,
26*4882a593Smuzhiyun                                                          int(be.bbport))[0]
27*4882a593Smuzhiyun
28*4882a593Smuzhiyun    def _runCommand(self, command):
29*4882a593Smuzhiyun        result, error = self.connection.runCommand(command)
30*4882a593Smuzhiyun        if error:
31*4882a593Smuzhiyun            raise Exception(error)
32*4882a593Smuzhiyun        return result
33*4882a593Smuzhiyun
34*4882a593Smuzhiyun    def disconnect(self):
35*4882a593Smuzhiyun        return self.connection.removeClient()
36*4882a593Smuzhiyun
37*4882a593Smuzhiyun    def setVariable(self, name, value):
38*4882a593Smuzhiyun        return self._runCommand(["setVariable", name, value])
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun    def getVariable(self, name):
41*4882a593Smuzhiyun        return self._runCommand(["getVariable", name])
42*4882a593Smuzhiyun
43*4882a593Smuzhiyun    def triggerEvent(self, event):
44*4882a593Smuzhiyun        return self._runCommand(["triggerEvent", event])
45*4882a593Smuzhiyun
46*4882a593Smuzhiyun    def build(self, targets, task = None):
47*4882a593Smuzhiyun        if task is None:
48*4882a593Smuzhiyun            task = "build"
49*4882a593Smuzhiyun        return self._runCommand(["buildTargets", targets, task])
50*4882a593Smuzhiyun
51*4882a593Smuzhiyun    def forceShutDown(self):
52*4882a593Smuzhiyun        return self._runCommand(["stateForceShutdown"])
53*4882a593Smuzhiyun
54*4882a593Smuzhiyun
55*4882a593Smuzhiyun
56*4882a593Smuzhiyundef getBuildEnvironmentController(**kwargs):
57*4882a593Smuzhiyun    """ Gets you a BuildEnvironmentController that encapsulates a build environment,
58*4882a593Smuzhiyun        based on the query dictionary sent in.
59*4882a593Smuzhiyun
60*4882a593Smuzhiyun        This is used to retrieve, for example, the currently running BE from inside
61*4882a593Smuzhiyun        the toaster UI, or find a new BE to start a new build in it.
62*4882a593Smuzhiyun
63*4882a593Smuzhiyun        The return object MUST always be a BuildEnvironmentController.
64*4882a593Smuzhiyun    """
65*4882a593Smuzhiyun
66*4882a593Smuzhiyun    from bldcontrol.localhostbecontroller import LocalhostBEController
67*4882a593Smuzhiyun
68*4882a593Smuzhiyun    be = BuildEnvironment.objects.filter(Q(**kwargs))[0]
69*4882a593Smuzhiyun    if be.betype == BuildEnvironment.TYPE_LOCAL:
70*4882a593Smuzhiyun        return LocalhostBEController(be)
71*4882a593Smuzhiyun    else:
72*4882a593Smuzhiyun        raise Exception("FIXME: Implement BEC for type %s" % str(be.betype))
73*4882a593Smuzhiyun
74*4882a593Smuzhiyun
75*4882a593Smuzhiyunclass BuildEnvironmentController(object):
76*4882a593Smuzhiyun    """ BuildEnvironmentController (BEC) is the abstract class that defines the operations that MUST
77*4882a593Smuzhiyun        or SHOULD be supported by a Build Environment. It is used to establish the framework, and must
78*4882a593Smuzhiyun        not be instantiated directly by the user.
79*4882a593Smuzhiyun
80*4882a593Smuzhiyun        Use the "getBuildEnvironmentController()" function to get a working BEC for your remote.
81*4882a593Smuzhiyun
82*4882a593Smuzhiyun        How the BuildEnvironments are discovered is outside the scope of this class.
83*4882a593Smuzhiyun
84*4882a593Smuzhiyun        You must derive this class to teach Toaster how to operate in your own infrastructure.
85*4882a593Smuzhiyun        We provide some specific BuildEnvironmentController classes that can be used either to
86*4882a593Smuzhiyun        directly set-up Toaster infrastructure, or as a model for your own infrastructure set:
87*4882a593Smuzhiyun
88*4882a593Smuzhiyun            * Localhost controller will run the Toaster BE on the same account as the web server
89*4882a593Smuzhiyun        (current user if you are using the the Django development web server)
90*4882a593Smuzhiyun        on the local machine, with the "build/" directory under the "poky/" source checkout directory.
91*4882a593Smuzhiyun        Bash is expected to be available.
92*4882a593Smuzhiyun
93*4882a593Smuzhiyun    """
94*4882a593Smuzhiyun    def __init__(self, be):
95*4882a593Smuzhiyun        """ Takes a BuildEnvironment object as parameter that points to the settings of the BE.
96*4882a593Smuzhiyun        """
97*4882a593Smuzhiyun        self.be = be
98*4882a593Smuzhiyun        self.connection = None
99*4882a593Smuzhiyun
100*4882a593Smuzhiyun    def setLayers(self, bitbake, ls):
101*4882a593Smuzhiyun        """ Checks-out bitbake executor and layers from git repositories.
102*4882a593Smuzhiyun            Sets the layer variables in the config file, after validating local layer paths.
103*4882a593Smuzhiyun            bitbake must be a single BRBitbake instance
104*4882a593Smuzhiyun            The layer paths must be in a list of BRLayer object
105*4882a593Smuzhiyun
106*4882a593Smuzhiyun            a word of attention: by convention, the first layer for any build will be poky!
107*4882a593Smuzhiyun        """
108*4882a593Smuzhiyun        raise NotImplementedError("FIXME: Must override setLayers")
109*4882a593Smuzhiyun
110*4882a593Smuzhiyun    def getArtifact(self, path):
111*4882a593Smuzhiyun        """ This call returns an artifact identified by the 'path'. How 'path' is interpreted as
112*4882a593Smuzhiyun            up to the implementing BEC. The return MUST be a REST URL where a GET will actually return
113*4882a593Smuzhiyun            the content of the artifact, e.g. for use as a "download link" in a web UI.
114*4882a593Smuzhiyun        """
115*4882a593Smuzhiyun        raise NotImplementedError("Must return the REST URL of the artifact")
116*4882a593Smuzhiyun
117*4882a593Smuzhiyun    def triggerBuild(self, bitbake, layers, variables, targets):
118*4882a593Smuzhiyun        raise NotImplementedError("Must override BE release")
119*4882a593Smuzhiyun
120*4882a593Smuzhiyunclass ShellCmdException(Exception):
121*4882a593Smuzhiyun    pass
122*4882a593Smuzhiyun
123*4882a593Smuzhiyun
124*4882a593Smuzhiyunclass BuildSetupException(Exception):
125*4882a593Smuzhiyun    pass
126*4882a593Smuzhiyun
127