How to call "snap" command inside a snap

Hi everyone, I’d like to call the “snap” command (e.g. “snap info <snap_name>” or “snap install <snap_name>”) from within another snap written in golang.

If I call the “snap” command with this:

    cmd := exec.Command("snap", "info", snap_name)
    out, err := cmd.CombinedOutput()
    if err != nil {
    	return string(out), err
    } else {
    	return string(out), nil

it returns “fork/exec /usr/bin/snap: permission denied”.

If I set “confinement:devmode” it perfectly works but if I run it in “confinement:strict” it doesn’t.

Am i missing something?

This is my snapcraft.yaml:

name: test
summary: test.
description: |
  Test.
version: '1.0'
grade: devel
confinement: strict

apps:
  agent:
    command: bin/Agent
    plugs:
      - snapd-control
      - home
      - network
    daemon: simple
    restart-condition: always

parts:
  poc-root:
    plugin: go
    go-packages:
      - test/Agent
    source: .
    source-type: local
    go-importpath: test
    build-packages: [ gcc ]

architectures:
  - build-on: amd64
    run-on: [amd64, arm64]

Thank you

Hi! You have two problems:

  1. You can’t call binaries outside your snap’s confinement in strict mode, so you’d have to ship such binaries within the snap itself. This however leads to the second issue.

  2. Controlling the host’s snapd is not possible in strict mode without the snapd-control interface (https://snapcraft.io/docs/snapd-control-interface). But you won’t get permission to publish a snap with that interface without a brand store.

There’s the alternative of creating a classic snap if you can provide very good reasons to the store maintainers that your specific snap absolutely needs this, and that you’re a reliable publisher. But I don’t think it’s very likely for you to be granted such a privileged (non-)confinement.

1 Like