github.com/AlpineAIO/wails/v2@v2.0.0-beta.32.0.20240505041856-1047a8fa5fef/internal/system/packagemanager/apt.go (about)

     1  //go:build linux
     2  // +build linux
     3  
     4  package packagemanager
     5  
     6  import (
     7  	"bytes"
     8  	"os"
     9  	"os/exec"
    10  	"regexp"
    11  	"strings"
    12  
    13  	"github.com/AlpineAIO/wails/v2/internal/shell"
    14  )
    15  
    16  // Apt represents the Apt manager
    17  type Apt struct {
    18  	name string
    19  	osid string
    20  }
    21  
    22  // NewApt creates a new Apt instance
    23  func NewApt(osid string) *Apt {
    24  	return &Apt{
    25  		name: "apt",
    26  		osid: osid,
    27  	}
    28  }
    29  
    30  // Packages returns the libraries that we need for Wails to compile
    31  // They will potentially differ on different distributions or versions
    32  func (a *Apt) Packages() packagemap {
    33  	return packagemap{
    34  		"libgtk-3": []*Package{
    35  			{Name: "libgtk-3-dev", SystemPackage: true, Library: true},
    36  		},
    37  		"libwebkit": []*Package{
    38  			{Name: "libwebkit2gtk-4.0-dev", SystemPackage: true, Library: true},
    39  		},
    40  		"gcc": []*Package{
    41  			{Name: "build-essential", SystemPackage: true},
    42  		},
    43  		"pkg-config": []*Package{
    44  			{Name: "pkg-config", SystemPackage: true},
    45  		},
    46  		"npm": []*Package{
    47  			{Name: "npm", SystemPackage: true},
    48  		},
    49  		"docker": []*Package{
    50  			{Name: "docker.io", SystemPackage: true, Optional: true},
    51  		},
    52  		"nsis": []*Package{
    53  			{Name: "nsis", SystemPackage: true, Optional: true},
    54  		},
    55  	}
    56  }
    57  
    58  // Name returns the name of the package manager
    59  func (a *Apt) Name() string {
    60  	return a.name
    61  }
    62  
    63  // PackageInstalled tests if the given package name is installed
    64  func (a *Apt) PackageInstalled(pkg *Package) (bool, error) {
    65  	if pkg.SystemPackage == false {
    66  		return false, nil
    67  	}
    68  	cmd := exec.Command("apt", "list", "-qq", pkg.Name)
    69  	var stdo, stde bytes.Buffer
    70  	cmd.Stdout = &stdo
    71  	cmd.Stderr = &stde
    72  	cmd.Env = append(os.Environ(), "LANGUAGE=en")
    73  	err := cmd.Run()
    74  	return strings.Contains(stdo.String(), "[installed]"), err
    75  }
    76  
    77  // PackageAvailable tests if the given package is available for installation
    78  func (a *Apt) PackageAvailable(pkg *Package) (bool, error) {
    79  	if pkg.SystemPackage == false {
    80  		return false, nil
    81  	}
    82  	stdout, _, err := shell.RunCommand(".", "apt", "list", "-qq", pkg.Name)
    83  	// We add a space to ensure we get a full match, not partial match
    84  	output := a.removeEscapeSequences(stdout)
    85  	installed := strings.HasPrefix(output, pkg.Name)
    86  	a.getPackageVersion(pkg, output)
    87  	return installed, err
    88  }
    89  
    90  // InstallCommand returns the package manager specific command to install a package
    91  func (a *Apt) InstallCommand(pkg *Package) string {
    92  	if pkg.SystemPackage == false {
    93  		return pkg.InstallCommand[a.osid]
    94  	}
    95  	return "sudo apt install " + pkg.Name
    96  }
    97  
    98  func (a *Apt) removeEscapeSequences(in string) string {
    99  	escapechars, _ := regexp.Compile(`\x1B(?:[@-Z\\-_]|\[[0-?]*[ -/]*[@-~])`)
   100  	return escapechars.ReplaceAllString(in, "")
   101  }
   102  
   103  func (a *Apt) getPackageVersion(pkg *Package, output string) {
   104  
   105  	splitOutput := strings.Split(output, " ")
   106  	if len(splitOutput) > 1 {
   107  		pkg.Version = splitOutput[1]
   108  	}
   109  }