mirror of
https://codeberg.org/scip/tablizer.git
synced 2025-12-19 05:21:03 +01:00
Compare commits
4 Commits
fix/ci-win
...
feature/mu
| Author | SHA1 | Date | |
|---|---|---|---|
| 479d8c274a | |||
| a49e28518b | |||
| e29e72b7d2 | |||
| f6e3075ea8 |
4
.github/workflows/ci.yaml
vendored
4
.github/workflows/ci.yaml
vendored
@@ -5,7 +5,9 @@ jobs:
|
|||||||
strategy:
|
strategy:
|
||||||
matrix:
|
matrix:
|
||||||
version: ['1.22']
|
version: ['1.22']
|
||||||
os: [ubuntu-latest, macos-latest, windows-latest]
|
# windows-latest removed, see:
|
||||||
|
# https://github.com/rogpeppe/go-internal/issues/284
|
||||||
|
os: [ubuntu-latest, macos-latest]
|
||||||
name: Build
|
name: Build
|
||||||
runs-on: ${{ matrix.os }}
|
runs-on: ${{ matrix.os }}
|
||||||
steps:
|
steps:
|
||||||
|
|||||||
63
.github/workflows/release.yaml
vendored
63
.github/workflows/release.yaml
vendored
@@ -1,8 +1,8 @@
|
|||||||
name: build-release
|
name: build-and-test
|
||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
tags:
|
tags:
|
||||||
- "v*.*.*"
|
- "*"
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
release:
|
release:
|
||||||
@@ -10,10 +10,10 @@ jobs:
|
|||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout code
|
- name: Checkout code
|
||||||
uses: actions/checkout@v4
|
uses: actions/checkout@v2
|
||||||
|
|
||||||
- name: Set up Go
|
- name: Set up Go
|
||||||
uses: actions/setup-go@v5
|
uses: actions/setup-go@v1
|
||||||
with:
|
with:
|
||||||
go-version: 1.22.11
|
go-version: 1.22.11
|
||||||
|
|
||||||
@@ -30,58 +30,3 @@ jobs:
|
|||||||
tag: ${{ github.ref_name }}
|
tag: ${{ github.ref_name }}
|
||||||
file: ./releases/*
|
file: ./releases/*
|
||||||
file_glob: true
|
file_glob: true
|
||||||
|
|
||||||
- name: Build Changelog
|
|
||||||
id: github_release
|
|
||||||
uses: mikepenz/release-changelog-builder-action@v5
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
mode: "PR"
|
|
||||||
configurationJson: |
|
|
||||||
{
|
|
||||||
"template": "#{{CHANGELOG}}\n\n**Full Changelog**: #{{RELEASE_DIFF}}",
|
|
||||||
"pr_template": "- #{{TITLE}} (##{{NUMBER}}) by #{{AUTHOR}}\n#{{BODY}}",
|
|
||||||
"empty_template": "- no changes",
|
|
||||||
"categories": [
|
|
||||||
{
|
|
||||||
"title": "## New Features",
|
|
||||||
"labels": ["add", "feature"]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"title": "## Bug Fixes",
|
|
||||||
"labels": ["fix", "bug", "revert"]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"title": "## Documentation Enhancements",
|
|
||||||
"labels": ["doc"]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"title": "## Refactoring Efforts",
|
|
||||||
"labels": ["refactor"]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"title": "## Miscellaneus Changes",
|
|
||||||
"labels": []
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"ignore_labels": [
|
|
||||||
"duplicate", "good first issue", "help wanted", "invalid", "question", "wontfix"
|
|
||||||
],
|
|
||||||
"label_extractor": [
|
|
||||||
{
|
|
||||||
"pattern": "(.) (.+)",
|
|
||||||
"target": "$1"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"pattern": "(.) (.+)",
|
|
||||||
"target": "$1",
|
|
||||||
"on_property": "title"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
}
|
|
||||||
|
|
||||||
- name: Create Release
|
|
||||||
uses: softprops/action-gh-release@v2
|
|
||||||
with:
|
|
||||||
body: ${{steps.github_release.outputs.changelog}}
|
|
||||||
|
|||||||
2
Makefile
2
Makefile
@@ -64,7 +64,7 @@ install: buildlocal
|
|||||||
clean:
|
clean:
|
||||||
rm -rf $(tool) releases coverage.out
|
rm -rf $(tool) releases coverage.out
|
||||||
|
|
||||||
test: clean
|
test:
|
||||||
go test ./... $(OPTS)
|
go test ./... $(OPTS)
|
||||||
|
|
||||||
singletest:
|
singletest:
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ Operational Flags:
|
|||||||
-s, --separator string Custom field separator
|
-s, --separator string Custom field separator
|
||||||
-k, --sort-by int Sort by column (default: 1)
|
-k, --sort-by int Sort by column (default: 1)
|
||||||
-z, --fuzzy Use fuzzy search [experimental]
|
-z, --fuzzy Use fuzzy search [experimental]
|
||||||
-F, --filter field[!]=reg Filter given field with regex, can be used multiple times
|
-F, --filter field=reg Filter given field with regex, can be used multiple times
|
||||||
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
||||||
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
Copyright © 2022-2025 Thomas von Dein
|
Copyright © 2022-2024 Thomas von Dein
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
This program is free software: you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -28,7 +28,7 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
const DefaultSeparator string = `(\s\s+|\t)`
|
const DefaultSeparator string = `(\s\s+|\t)`
|
||||||
const Version string = "v1.3.2"
|
const Version string = "v1.3.1"
|
||||||
const MAXPARTS = 2
|
const MAXPARTS = 2
|
||||||
|
|
||||||
var DefaultConfigfile = os.Getenv("HOME") + "/.config/tablizer/config"
|
var DefaultConfigfile = os.Getenv("HOME") + "/.config/tablizer/config"
|
||||||
@@ -58,11 +58,6 @@ type Pattern struct {
|
|||||||
Negate bool
|
Negate bool
|
||||||
}
|
}
|
||||||
|
|
||||||
type Filter struct {
|
|
||||||
Regex *regexp.Regexp
|
|
||||||
Negate bool
|
|
||||||
}
|
|
||||||
|
|
||||||
// internal config
|
// internal config
|
||||||
type Config struct {
|
type Config struct {
|
||||||
Debug bool
|
Debug bool
|
||||||
@@ -105,7 +100,7 @@ type Config struct {
|
|||||||
|
|
||||||
// used for field filtering
|
// used for field filtering
|
||||||
Rawfilters []string
|
Rawfilters []string
|
||||||
Filters map[string]Filter //map[string]*regexp.Regexp
|
Filters map[string]*regexp.Regexp
|
||||||
|
|
||||||
// -r <file>
|
// -r <file>
|
||||||
InputFile string
|
InputFile string
|
||||||
@@ -275,20 +270,12 @@ func (conf *Config) PrepareModeFlags(flag Modeflag) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (conf *Config) PrepareFilters() error {
|
func (conf *Config) PrepareFilters() error {
|
||||||
conf.Filters = make(map[string]Filter, len(conf.Rawfilters))
|
conf.Filters = make(map[string]*regexp.Regexp, len(conf.Rawfilters))
|
||||||
|
|
||||||
for _, rawfilter := range conf.Rawfilters {
|
for _, filter := range conf.Rawfilters {
|
||||||
filter := Filter{}
|
parts := strings.Split(filter, "=")
|
||||||
|
|
||||||
parts := strings.Split(rawfilter, "!=")
|
|
||||||
if len(parts) != MAXPARTS {
|
if len(parts) != MAXPARTS {
|
||||||
parts = strings.Split(rawfilter, "=")
|
return errors.New("filter field and value must be separated by =")
|
||||||
|
|
||||||
if len(parts) != MAXPARTS {
|
|
||||||
return errors.New("filter field and value must be separated by '=' or '!='")
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
filter.Negate = true
|
|
||||||
}
|
}
|
||||||
|
|
||||||
reg, err := regexp.Compile(parts[1])
|
reg, err := regexp.Compile(parts[1])
|
||||||
@@ -297,8 +284,7 @@ func (conf *Config) PrepareFilters() error {
|
|||||||
parts[0], err)
|
parts[0], err)
|
||||||
}
|
}
|
||||||
|
|
||||||
filter.Regex = reg
|
conf.Filters[strings.ToLower(strings.ToLower(parts[0]))] = reg
|
||||||
conf.Filters[strings.ToLower(parts[0])] = filter
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
Copyright © 2022-2025 Thomas von Dein
|
Copyright © 2022-2024 Thomas von Dein
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
This program is free software: you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -190,7 +190,7 @@ func Execute() {
|
|||||||
|
|
||||||
// filters
|
// filters
|
||||||
rootCmd.PersistentFlags().StringArrayVarP(&conf.Rawfilters,
|
rootCmd.PersistentFlags().StringArrayVarP(&conf.Rawfilters,
|
||||||
"filter", "F", nil, "Filter by field (field=regexp || field!=regexp)")
|
"filter", "F", nil, "Filter by field (field=regexp)")
|
||||||
rootCmd.PersistentFlags().StringArrayVarP(&conf.Transposers,
|
rootCmd.PersistentFlags().StringArrayVarP(&conf.Transposers,
|
||||||
"regex-transposer", "R", nil, "apply /search/replace/ regexp to fields given in -T")
|
"regex-transposer", "R", nil, "apply /search/replace/ regexp to fields given in -T")
|
||||||
|
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ SYNOPSIS
|
|||||||
-s, --separator string Custom field separator
|
-s, --separator string Custom field separator
|
||||||
-k, --sort-by int|name Sort by column (default: 1)
|
-k, --sort-by int|name Sort by column (default: 1)
|
||||||
-z, --fuzzy Use fuzzy search [experimental]
|
-z, --fuzzy Use fuzzy search [experimental]
|
||||||
-F, --filter field[!]=reg Filter given field with regex, can be used multiple times
|
-F, --filter field=reg Filter given field with regex, can be used multiple times
|
||||||
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
||||||
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
||||||
|
|
||||||
@@ -181,10 +181,6 @@ DESCRIPTION
|
|||||||
If you specify more than one filter, both filters have to match (AND
|
If you specify more than one filter, both filters have to match (AND
|
||||||
operation).
|
operation).
|
||||||
|
|
||||||
These field filters can also be negated:
|
|
||||||
|
|
||||||
fieldname!=regexp
|
|
||||||
|
|
||||||
If the option -v is specified, the filtering is inverted.
|
If the option -v is specified, the filtering is inverted.
|
||||||
|
|
||||||
COLUMNS
|
COLUMNS
|
||||||
@@ -420,7 +416,7 @@ Operational Flags:
|
|||||||
-s, --separator string Custom field separator
|
-s, --separator string Custom field separator
|
||||||
-k, --sort-by int|name Sort by column (default: 1)
|
-k, --sort-by int|name Sort by column (default: 1)
|
||||||
-z, --fuzzy Use fuzzy search [experimental]
|
-z, --fuzzy Use fuzzy search [experimental]
|
||||||
-F, --filter field[!]=reg Filter given field with regex, can be used multiple times
|
-F, --filter field=reg Filter given field with regex, can be used multiple times
|
||||||
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
||||||
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
Copyright © 2022-2025 Thomas von Dein
|
Copyright © 2022-2024 Thomas von Dein
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
This program is free software: you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -86,19 +86,15 @@ func FilterByFields(conf cfg.Config, data *Tabdata) (*Tabdata, bool, error) {
|
|||||||
keep := true
|
keep := true
|
||||||
|
|
||||||
for idx, header := range data.headers {
|
for idx, header := range data.headers {
|
||||||
lcheader := strings.ToLower(header)
|
if !Exists(conf.Filters, strings.ToLower(header)) {
|
||||||
if !Exists(conf.Filters, lcheader) {
|
|
||||||
// do not filter by unspecified field
|
// do not filter by unspecified field
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
match := conf.Filters[lcheader].Regex.MatchString(row[idx])
|
if !conf.Filters[strings.ToLower(header)].MatchString(row[idx]) {
|
||||||
if conf.Filters[lcheader].Negate {
|
// there IS a filter, but it doesn't match
|
||||||
match = !match
|
|
||||||
}
|
|
||||||
|
|
||||||
if !match {
|
|
||||||
keep = false
|
keep = false
|
||||||
|
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
Copyright © 2024-2025 Thomas von Dein
|
Copyright © 2024 Thomas von Dein
|
||||||
|
|
||||||
This program is free software: you can redistribute it and/or modify
|
This program is free software: you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -98,20 +98,6 @@ func TestFilterByFields(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
{
|
|
||||||
name: "one-field-negative",
|
|
||||||
filter: []string{"one!=asd"},
|
|
||||||
expect: Tabdata{
|
|
||||||
headers: []string{
|
|
||||||
"ONE", "TWO", "THREE",
|
|
||||||
},
|
|
||||||
entries: [][]string{
|
|
||||||
{"19191", "EDD 1", "x"},
|
|
||||||
{"8d8", "AN 1", "y"},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
|
|
||||||
{
|
{
|
||||||
name: "one-field-inverted",
|
name: "one-field-inverted",
|
||||||
filter: []string{"one=19"},
|
filter: []string{"one=19"},
|
||||||
|
|||||||
10
tablizer.1
10
tablizer.1
@@ -133,7 +133,7 @@
|
|||||||
.\" ========================================================================
|
.\" ========================================================================
|
||||||
.\"
|
.\"
|
||||||
.IX Title "TABLIZER 1"
|
.IX Title "TABLIZER 1"
|
||||||
.TH TABLIZER 1 "2025-01-30" "1" "User Commands"
|
.TH TABLIZER 1 "2025-01-22" "1" "User Commands"
|
||||||
.\" For nroff, turn off justification. Always turn off hyphenation; it makes
|
.\" For nroff, turn off justification. Always turn off hyphenation; it makes
|
||||||
.\" way too many mistakes in technical documents.
|
.\" way too many mistakes in technical documents.
|
||||||
.if n .ad l
|
.if n .ad l
|
||||||
@@ -155,7 +155,7 @@ tablizer \- Manipulate tabular output of other programs
|
|||||||
\& \-s, \-\-separator string Custom field separator
|
\& \-s, \-\-separator string Custom field separator
|
||||||
\& \-k, \-\-sort\-by int|name Sort by column (default: 1)
|
\& \-k, \-\-sort\-by int|name Sort by column (default: 1)
|
||||||
\& \-z, \-\-fuzzy Use fuzzy search [experimental]
|
\& \-z, \-\-fuzzy Use fuzzy search [experimental]
|
||||||
\& \-F, \-\-filter field[!]=reg Filter given field with regex, can be used multiple times
|
\& \-F, \-\-filter field=reg Filter given field with regex, can be used multiple times
|
||||||
\& \-T, \-\-transpose\-columns string Transpose the speficied columns (separated by ,)
|
\& \-T, \-\-transpose\-columns string Transpose the speficied columns (separated by ,)
|
||||||
\& \-R, \-\-regex\-transposer /from/to/ Apply /search/replace/ regexp to fields given in \-T
|
\& \-R, \-\-regex\-transposer /from/to/ Apply /search/replace/ regexp to fields given in \-T
|
||||||
\&
|
\&
|
||||||
@@ -340,12 +340,6 @@ Fieldnames (== columns headers) are case insensitive.
|
|||||||
If you specify more than one filter, both filters have to match (\s-1AND\s0
|
If you specify more than one filter, both filters have to match (\s-1AND\s0
|
||||||
operation).
|
operation).
|
||||||
.PP
|
.PP
|
||||||
These field filters can also be negated:
|
|
||||||
.PP
|
|
||||||
.Vb 1
|
|
||||||
\& fieldname!=regexp
|
|
||||||
.Ve
|
|
||||||
.PP
|
|
||||||
If the option \fB\-v\fR is specified, the filtering is inverted.
|
If the option \fB\-v\fR is specified, the filtering is inverted.
|
||||||
.SS "\s-1COLUMNS\s0"
|
.SS "\s-1COLUMNS\s0"
|
||||||
.IX Subsection "COLUMNS"
|
.IX Subsection "COLUMNS"
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ tablizer - Manipulate tabular output of other programs
|
|||||||
-s, --separator string Custom field separator
|
-s, --separator string Custom field separator
|
||||||
-k, --sort-by int|name Sort by column (default: 1)
|
-k, --sort-by int|name Sort by column (default: 1)
|
||||||
-z, --fuzzy Use fuzzy search [experimental]
|
-z, --fuzzy Use fuzzy search [experimental]
|
||||||
-F, --filter field[!]=reg Filter given field with regex, can be used multiple times
|
-F, --filter field=reg Filter given field with regex, can be used multiple times
|
||||||
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
-T, --transpose-columns string Transpose the speficied columns (separated by ,)
|
||||||
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
-R, --regex-transposer /from/to/ Apply /search/replace/ regexp to fields given in -T
|
||||||
|
|
||||||
@@ -194,10 +194,6 @@ Fieldnames (== columns headers) are case insensitive.
|
|||||||
If you specify more than one filter, both filters have to match (AND
|
If you specify more than one filter, both filters have to match (AND
|
||||||
operation).
|
operation).
|
||||||
|
|
||||||
These field filters can also be negated:
|
|
||||||
|
|
||||||
fieldname!=regexp
|
|
||||||
|
|
||||||
If the option B<-v> is specified, the filtering is inverted.
|
If the option B<-v> is specified, the filtering is inverted.
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user