xbps-{install,remove}: implemented column/wide output mode.

See https://github.com/voidlinux/xbps/issues/63 for info.

Close #63
This commit is contained in:
Juan RP 2014-10-30 11:23:10 +01:00
parent 3f7cd86d9d
commit b179c16fc0
4 changed files with 170 additions and 55 deletions

5
NEWS
View File

@ -1,5 +1,10 @@
xbps-0.42 (???):
* xbps-{install,remove}: implemented a column/wide output mode
as requested in #63 (https://github.com/voidlinux/xbps/issues/63).
If the terminal has enough columns it will use this and falling back
to the previous mode otherwise.
* libxbps: replaces the internal redundant dependency sorting step
that was made in xbps_transaction_prepare() with a simple implementation
that fixes 2 bugs and makes xbps 2x faster to resolve dependencies.

View File

@ -34,6 +34,17 @@ struct xferstat {
struct timeval last;
};
struct transaction {
struct xbps_handle *xhp;
xbps_dictionary_t d;
xbps_object_iterator_t iter;
uint32_t inst_pkgcnt;
uint32_t up_pkgcnt;
uint32_t cf_pkgcnt;
uint32_t rm_pkgcnt;
uint32_t dl_pkgcnt;
};
/* from transaction.c */
int install_new_pkg(struct xbps_handle *, const char *, bool);
int update_pkg(struct xbps_handle *, const char *);
@ -52,6 +63,7 @@ int state_cb(const struct xbps_state_cb_data *, void *);
/* From util.c */
void print_package_line(const char *, int, bool);
bool print_trans_colmode(struct transaction *, int);
int get_maxcols(void);
#endif /* !_XBPS_INSTALL_DEFS_H_ */

View File

@ -36,17 +36,6 @@
#include <xbps.h>
#include "defs.h"
struct transaction {
struct xbps_handle *xhp;
xbps_dictionary_t d;
xbps_object_iterator_t iter;
uint32_t inst_pkgcnt;
uint32_t up_pkgcnt;
uint32_t cf_pkgcnt;
uint32_t rm_pkgcnt;
uint32_t dl_pkgcnt;
};
static void
print_array(xbps_array_t a)
{
@ -128,49 +117,51 @@ show_transaction_sizes(struct transaction *trans, int cols)
uint64_t dlsize = 0, instsize = 0, rmsize = 0, disk_free_size = 0;
char size[8];
/*
* Show the list of packages that will be downloaded, installed, updated,
* removed or configured.
*/
xbps_dictionary_get_uint32(trans->d, "total-download-pkgs",
&trans->dl_pkgcnt);
if (trans->dl_pkgcnt) {
printf("%u package%s will be downloaded:\n",
trans->dl_pkgcnt, trans->dl_pkgcnt == 1 ? "" : "s");
show_package_list(trans, NULL, cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-install-pkgs",
&trans->inst_pkgcnt);
if (trans->inst_pkgcnt) {
printf("%u package%s will be installed:\n",
trans->inst_pkgcnt, trans->inst_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "install", cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-update-pkgs",
&trans->up_pkgcnt);
if (trans->up_pkgcnt) {
printf("%u package%s will be updated:\n",
trans->up_pkgcnt, trans->up_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "update", cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-configure-pkgs",
&trans->cf_pkgcnt);
if (trans->cf_pkgcnt) {
printf("%u package%s will be configured:\n",
trans->cf_pkgcnt, trans->cf_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "configure", cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-remove-pkgs",
&trans->rm_pkgcnt);
if (trans->rm_pkgcnt) {
printf("%u package%s will be removed:\n",
trans->rm_pkgcnt, trans->rm_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "remove", cols);
printf("\n");
if (!print_trans_colmode(trans, cols)) {
/*
* Show the list of packages that will be downloaded, installed, updated,
* removed or configured.
*/
xbps_dictionary_get_uint32(trans->d, "total-download-pkgs",
&trans->dl_pkgcnt);
if (trans->dl_pkgcnt) {
printf("%u package%s will be downloaded:\n",
trans->dl_pkgcnt, trans->dl_pkgcnt == 1 ? "" : "s");
show_package_list(trans, NULL, cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-install-pkgs",
&trans->inst_pkgcnt);
if (trans->inst_pkgcnt) {
printf("%u package%s will be installed:\n",
trans->inst_pkgcnt, trans->inst_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "install", cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-update-pkgs",
&trans->up_pkgcnt);
if (trans->up_pkgcnt) {
printf("%u package%s will be updated:\n",
trans->up_pkgcnt, trans->up_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "update", cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-configure-pkgs",
&trans->cf_pkgcnt);
if (trans->cf_pkgcnt) {
printf("%u package%s will be configured:\n",
trans->cf_pkgcnt, trans->cf_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "configure", cols);
printf("\n");
}
xbps_dictionary_get_uint32(trans->d, "total-remove-pkgs",
&trans->rm_pkgcnt);
if (trans->rm_pkgcnt) {
printf("%u package%s will be removed:\n",
trans->rm_pkgcnt, trans->rm_pkgcnt == 1 ? "" : "s");
show_package_list(trans, "remove", cols);
printf("\n");
}
}
/*
* Show total download/installed/removed size for all required packages.

View File

@ -1,5 +1,5 @@
/*-
* Copyright (c) 2008-2013 Juan Romero Pardines.
* Copyright (c) 2008-2014 Juan Romero Pardines.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@ -31,6 +31,7 @@
#include <string.h>
#include <strings.h>
#include <sys/ioctl.h>
#include <assert.h>
#include <xbps.h>
#include "defs.h"
@ -69,3 +70,109 @@ print_package_line(const char *str, int maxcols, bool reset)
}
printf("%s ", str);
}
static unsigned int
find_longest_pkgname(struct transaction *trans)
{
xbps_object_t obj;
const char *pkgver;
char *pkgname;
unsigned int len = 0, max = 0;
while ((obj = xbps_object_iterator_next(trans->iter)) != NULL) {
xbps_dictionary_get_cstring_nocopy(obj, "pkgver", &pkgver);
pkgname = xbps_pkg_name(pkgver);
assert(pkgname);
len = strlen(pkgname);
free(pkgname);
if (max == 0 || len > max)
max = len;
}
xbps_object_iterator_reset(trans->iter);
return max+1;
}
bool
print_trans_colmode(struct transaction *trans, int cols)
{
xbps_object_t obj;
uint64_t dlsize = 0;
char size[8];
unsigned int x, blen, pnamelen;
int hdrlen;
pnamelen = find_longest_pkgname(trans);
/* header length */
hdrlen = 4 + pnamelen + 48;
if (cols <= hdrlen)
return false;
printf("Name");
for (x = 4; x < pnamelen; x++)
printf(" ");
printf("Action Version New version Download size\n");
while ((obj = xbps_object_iterator_next(trans->iter)) != NULL) {
xbps_dictionary_t ipkgd;
const char *pkgver, *ipkgver, *ver, *iver, *tract;
char *pkgname;
bool dload = false;
ver = iver = NULL;
xbps_dictionary_get_cstring_nocopy(obj, "pkgver", &pkgver);
xbps_dictionary_get_cstring_nocopy(obj, "transaction", &tract);
xbps_dictionary_get_uint64(obj, "filename-size", &dlsize);
xbps_dictionary_get_bool(obj, "download", &dload);
pkgname = xbps_pkg_name(pkgver);
assert(pkgname);
if ((strcmp(tract, "update") == 0) || strcmp(tract, "remove") == 0) {
ipkgd = xbps_pkgdb_get_pkg(trans->xhp, pkgname);
assert(ipkgd);
xbps_dictionary_get_cstring_nocopy(ipkgd, "pkgver", &ipkgver);
iver = xbps_pkg_version(ipkgver);
}
ver = xbps_pkg_version(pkgver);
/* print pkgname and some blanks */
blen = pnamelen - strlen(pkgname);
printf("%s", pkgname);
for (x = 0; x < blen; x++)
printf(" ");
/* print action */
printf("%s ", tract);
for (x = strlen(tract); x < 7; x++)
printf(" ");
/* print installed version */
if (iver == NULL)
iver = "-";
/* print new version */
printf("%s ", iver);
for (x = strlen(iver); x < 14; x++)
printf(" ");
if (strcmp(tract, "remove") == 0) {
ver = "-";
}
if (dload)
(void)xbps_humanize_number(size, (int64_t)dlsize);
else {
size[0] = '-';
size[1] = '\0';
}
printf("%s ", ver);
for (x = strlen(ver); x < 18; x++)
printf(" ");
/* print download size */
printf("%s ", size);
printf("\n");
free(pkgname);
}
xbps_object_iterator_reset(trans->iter);
return true;
}