]> git.ipfire.org Git - pakfire.git/blob - src/cli/lib/install.c
cli: install: Migrate the command to the new system
[pakfire.git] / src / cli / lib / install.c
1 /*#############################################################################
2 # #
3 # Pakfire - The IPFire package management system #
4 # Copyright (C) 2023 Pakfire development team #
5 # #
6 # This program is free software: you can redistribute it and/or modify #
7 # it under the terms of the GNU General Public License as published by #
8 # the Free Software Foundation, either version 3 of the License, or #
9 # (at your option) any later version. #
10 # #
11 # This program is distributed in the hope that it will be useful, #
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of #
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the #
14 # GNU General Public License for more details. #
15 # #
16 # You should have received a copy of the GNU General Public License #
17 # along with this program. If not, see <http://www.gnu.org/licenses/>. #
18 # #
19 #############################################################################*/
20
21 #include <argp.h>
22 #include <errno.h>
23 #include <stdlib.h>
24
25 #include <pakfire/pakfire.h>
26 #include <pakfire/transaction.h>
27
28 #include "command.h"
29 #include "install.h"
30 #include "pakfire.h"
31 #include "transaction.h"
32
33 static const char* args_doc = "install [OPTIONS...] PACKAGES...";
34
35 static const char* doc = "Install packages";
36
37 #define MAX_PACKAGES 128
38
39 struct config {
40 int transaction_flags;
41 int job_flags;
42
43 // Packages
44 char* packages[MAX_PACKAGES];
45 unsigned int num_packages;
46 };
47
48 enum {
49 OPT_BEST = 1,
50 OPT_ALLOW_DOWNGRADE = 2,
51 OPT_ALLOW_UNINSTALL = 3,
52 OPT_WITHOUT_RECOMMENDED = 4,
53 };
54
55 static struct argp_option options[] = {
56 { "allow-downgrade", OPT_ALLOW_DOWNGRADE, NULL, 0, "Allow downgrading packages", 0 },
57 { "allow-uninstall", OPT_ALLOW_UNINSTALL, NULL, 0, "Allow uninstalling packages", 0 },
58 { "best", OPT_BEST, NULL, 0, "Only install the best package(s)", 0 },
59 { "without-recommended", OPT_ALLOW_DOWNGRADE, NULL, 0, "Do not install recommended packages", 0 },
60 { NULL },
61 };
62
63 static error_t parse(int key, char* arg, struct argp_state* state, void* data) {
64 struct config* config = data;
65
66 switch (key) {
67 case OPT_BEST:
68 config->job_flags |= PAKFIRE_JOB_BEST;
69 break;
70
71 case OPT_ALLOW_DOWNGRADE:
72 config->transaction_flags |= PAKFIRE_TRANSACTION_ALLOW_DOWNGRADE;
73 break;
74
75 case OPT_ALLOW_UNINSTALL:
76 config->transaction_flags |= PAKFIRE_TRANSACTION_ALLOW_UNINSTALL;
77 break;
78
79 case OPT_WITHOUT_RECOMMENDED:
80 config->transaction_flags |= PAKFIRE_TRANSACTION_WITHOUT_RECOMMENDED;
81 break;
82
83 case ARGP_KEY_ARG:
84 if (config->num_packages >= MAX_PACKAGES)
85 return -ENOBUFS;
86
87 config->packages[config->num_packages++] = arg;
88 break;
89
90 default:
91 return ARGP_ERR_UNKNOWN;
92 }
93
94 return 0;
95 }
96
97 static int __cli_install(struct pakfire_transaction* transaction, int argc, char* argv[], void* data) {
98 struct config* config = (struct config*)data;
99 int r;
100
101 // Add the remaining command line options as packages
102 for (unsigned int i = 0; i < config->num_packages; i++) {
103 r = pakfire_transaction_request(transaction,
104 PAKFIRE_JOB_INSTALL, config->packages[i], config->job_flags);
105 if (r) {
106 fprintf(stderr, "Could not find '%s': %m\n", argv[i]);
107 return r;
108 }
109 }
110
111 return 0;
112 }
113
114 int cli_install(void* data, int argc, char* argv[]) {
115 struct pakfire* pakfire = NULL;
116 struct config config = {};
117 int r;
118
119 struct cli_config* cli_config = data;
120
121 // Parse the command line
122 r = cli_parse(options, NULL, args_doc, doc, parse, argc, argv, &config);
123 if (r)
124 goto ERROR;
125
126 // Setup Pakfire
127 r = cli_setup_pakfire(&pakfire, cli_config);
128 if (r)
129 goto ERROR;
130
131 r = cli_transaction(pakfire, argc, argv, config.transaction_flags, __cli_install, &config);
132
133 ERROR:
134 if (pakfire)
135 pakfire_unref(pakfire);
136
137 return r;
138 }