Thanks for the review. I'll add tests before submitting a new revision. Tom
On Thu, Jan 8, 2026 at 12:30 PM Alexander Kanavin <[email protected]> wrote: > This looks alright, but it really does need tests, in > meta/lib/oeqa/selftest/cases/devtool.py > > Alex > > On Thu, 8 Jan 2026 at 00:12, Tom Geelen <[email protected]> wrote: > > > > Based of a feature of AUH this is a plugin to run a testimage directly > with one packages installed that you are working on via devtool. > > > > Inputs would be a: > > - target image > > - target packages > > > > The tool will take care to make sure it also installs the minimal > necessary dependencies to be able to run ptest on the target image. > > Logs will be captured and stored in the devtool workspace for easy > access. > > > > Minimal example to test: > > - modify a package via devtool > > - call this new method with said package and for instance > core-image-minimal > > > > Signed-off-by: Tom Geelen <[email protected]> > > --- > > scripts/lib/devtool/testimage.py | 122 +++++++++++++++++++++++++++++++ > > 1 file changed, 122 insertions(+) > > create mode 100644 scripts/lib/devtool/testimage.py > > > > diff --git a/scripts/lib/devtool/testimage.py > b/scripts/lib/devtool/testimage.py > > new file mode 100644 > > index 0000000000..809bd4bfb2 > > --- /dev/null > > +++ b/scripts/lib/devtool/testimage.py > > @@ -0,0 +1,122 @@ > > +# Development tool - test-image plugin > > +# > > +# Copyright (C) 2026 Authors > > +# > > +# SPDX-License-Identifier: GPL-2.0-only > > + > > +"""Devtool plugin containing the test-image subcommand. > > + > > +Builds a target image, installs specified package(s) from the workspace > or > > +layer, and runs the image's test suite via the BitBake `testimage` task. > > +""" > > + > > +import os > > +import logging > > + > > +from devtool import setup_tinfoil, parse_recipe, DevtoolError > > +from devtool.build_image import build_image_task > > + > > +logger = logging.getLogger('devtool') > > + > > + > > +def _collect_install_packages(tinfoil, config, package_names): > > + """Return list of packages to install, including -ptest when > available. > > + > > + package_names: list of PN values (typically recipe names). > > + """ > > + install = [] > > + for pn in package_names: > > + rd = parse_recipe(config, tinfoil, pn, True) > > + if not rd: > > + # parse_recipe already logs errors > > + raise DevtoolError(f'Unable to find or parse recipe for > package {pn}') > > + > > + install.append(pn) > > + packages_var = rd.getVar('PACKAGES') or '' > > + packages = packages_var.split() > > + ptest_pkg = f'{pn}-ptest' > > + if ptest_pkg in packages: > > + install.append(ptest_pkg) > > + logger.info('Including ptest package %s', ptest_pkg) > > + else: > > + logger.debug('No ptest package found for %s', pn) > > + return install > > + > > + > > +def test_image(args, config, basepath, workspace): > > + """Entry point for the devtool 'test-image' subcommand.""" > > + > > + if not args.imagename: > > + raise DevtoolError('Image recipe to test must be specified') > > + if not args.package: > > + raise DevtoolError('Package(s) to install must be specified via > -p/--package') > > + > > + package_names = [p.strip() for p in args.package.split(',') if > p.strip()] > > + if not package_names: > > + raise DevtoolError('No valid package name(s) provided') > > + > > + # Prepare a bbappend with IMAGE_INSTALL and testimage variables > > + tinfoil = setup_tinfoil(basepath=basepath) > > + try: > > + install_pkgs = _collect_install_packages(tinfoil, config, > package_names) > > + finally: > > + tinfoil.shutdown() > > + > > + logdir = os.path.join(config.workspace_path, 'testimage-logs') > > + try: > > + os.makedirs(logdir, exist_ok=True) > > + except Exception as exc: > > + raise DevtoolError(f'Failed to create test logs directory > {logdir}: {exc}') > > + > > + pkg_append = ' '.join(sorted(set(install_pkgs))) > > + extra_append = [ > > + f'TEST_LOG_DIR = "{logdir}"', > > + # Ensure changes to these vars retrigger testimage and are > visible > > + 'TESTIMAGE_UPDATE_VARS:append = " TEST_LOG_DIR IMAGE_CLASSES > TEST_SUITES DISTRO_FEATURES"', > > + # Ensure runtime test framework is enabled even if image/distro > omitted it > > + 'IMAGE_CLASSES:append = " testimage"', > > + 'TEST_SUITES = "ping ssh ptest"', > > + 'DISTRO_FEATURES:append = " ptest"', > > + 'TEST_RUNQEMUPARAMS = "slirp"', > > + # Ensure requested packages (and -ptest where available) are > installed > > + f'IMAGE_INSTALL:append = " {pkg_append}"', > > + ] > > + > > + logger.info('Building and testing image %s with packages: %s', > > + args.imagename, ' '.join(install_pkgs)) > > + > > + # Reuse build_image_task to run -c testimage with our bbappend > > + result, _outputdir = build_image_task( > > + config, > > + basepath, > > + workspace, > > + args.imagename, > > + add_packages=install_pkgs, > > + task='testimage', > > + extra_append=extra_append, > > + ) > > + > > + if result == 0: > > + logger.info('Testimage completed. Logs are in %s', logdir) > > + return result > > + > > + > > +def register_commands(subparsers, context): > > + """Register devtool subcommands from the test-image plugin""" > > + parser = subparsers.add_parser( > > + 'test-image', > > + help='Build image, install package(s), and run testimage', > > + description=( > > + 'Builds an image, installs specified package(s), and runs > the\n' > > + 'BitBake testimage task to validate on-target > functionality.' > > + ), > > + group='testbuild', > > + order=-9, > > + ) > > + parser.add_argument('imagename', help='Image recipe to test') > > + parser.add_argument( > > + '-p', '--package', '--packages', > > + help='Package(s) to install into the image (comma-separated)', > > + metavar='PACKAGES', > > + ) > > + parser.set_defaults(func=test_image) > > -- > > 2.43.0 > > >
-=-=-=-=-=-=-=-=-=-=-=- Links: You receive all messages sent to this group. View/Reply Online (#229081): https://lists.openembedded.org/g/openembedded-core/message/229081 Mute This Topic: https://lists.openembedded.org/mt/117144059/21656 Group Owner: [email protected] Unsubscribe: https://lists.openembedded.org/g/openembedded-core/unsub [[email protected]] -=-=-=-=-=-=-=-=-=-=-=-
