Compare commits
7 Commits
Author | SHA1 | Date | |
---|---|---|---|
293c75456e | |||
95934ee91a | |||
2253683cab | |||
22b7120c43 | |||
23e043fee2 | |||
96a20b9278 | |||
1d4ca55f2a |
|
@ -6,7 +6,16 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||||
and this project adheres to
|
and this project adheres to
|
||||||
[Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
[Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||||
|
|
||||||
|
## [1.1.0] - 2024-01-19
|
||||||
|
|
||||||
|
### Added
|
||||||
|
|
||||||
|
- Support for comments (`#`) in parts files.
|
||||||
|
- Explicitly inherit paths from `PATH` environment variable.
|
||||||
|
- Ability to deduplicate output paths.
|
||||||
|
|
||||||
## [1.0.2] - 2023-12-05
|
## [1.0.2] - 2023-12-05
|
||||||
|
|
||||||
### Added
|
### Added
|
||||||
|
|
||||||
- Initial release.
|
- Initial release.
|
||||||
|
|
2
Makefile
2
Makefile
|
@ -1,4 +1,4 @@
|
||||||
VERSION = 1.0.2
|
VERSION = 1.1.0
|
||||||
PREFIX ?= /usr/local
|
PREFIX ?= /usr/local
|
||||||
|
|
||||||
OS != uname -o
|
OS != uname -o
|
||||||
|
|
|
@ -35,7 +35,7 @@ Running the program with such a directory would yield the following result:
|
||||||
|
|
||||||
```
|
```
|
||||||
$ pathsd paths.d/
|
$ pathsd paths.d/
|
||||||
export PATH="/Users/bilbo/opt/bin:/opt/homebrew/bin:/opt/homebrew/sbin":$PATH
|
export PATH="/Users/bilbo/opt/bin:/opt/homebrew/bin:/opt/homebrew/sbin":<paths inherited from $PATH>
|
||||||
```
|
```
|
||||||
|
|
||||||
You can specify multiple directories. They'll be processed one by one in the
|
You can specify multiple directories. They'll be processed one by one in the
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
# Package
|
# Package
|
||||||
|
|
||||||
version = "1.0.2"
|
version = "1.1.0"
|
||||||
author = "Tomek Wójcik <contact@bthlabs.pl>"
|
author = "Tomek Wójcik <contact@bthlabs.pl>"
|
||||||
description = "pathsd by BTHLabs"
|
description = "pathsd by BTHLabs"
|
||||||
license = "MIT"
|
license = "MIT"
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import std/[algorithm, dirs, logging, options, paths, strutils, syncio]
|
import std/[algorithm, dirs, envvars, logging, options, paths, strutils, syncio]
|
||||||
import strformat
|
import strformat
|
||||||
|
|
||||||
import commandant
|
import commandant
|
||||||
|
@ -9,7 +9,7 @@ type
|
||||||
output*: seq[string]
|
output*: seq[string]
|
||||||
errorCode*: ErrorCode
|
errorCode*: ErrorCode
|
||||||
|
|
||||||
const version = "1.0.2"
|
const version = "1.1.0"
|
||||||
const usage_string = """usage: pathsd [--version | --help] [-v | -q] [-s shell] search_path ..."""
|
const usage_string = """usage: pathsd [--version | --help] [-v | -q] [-s shell] search_path ..."""
|
||||||
const version_string = fmt"""pathsd {version}"""
|
const version_string = fmt"""pathsd {version}"""
|
||||||
const help_string = fmt"""pathsd {version} by BTHLabs
|
const help_string = fmt"""pathsd {version} by BTHLabs
|
||||||
|
@ -19,6 +19,7 @@ Usage:
|
||||||
pathsd [options] search_path ...
|
pathsd [options] search_path ...
|
||||||
Options:
|
Options:
|
||||||
-s --shell target shell (defaults to bash)
|
-s --shell target shell (defaults to bash)
|
||||||
|
-d --dedupe deduplicate the final paths
|
||||||
-v --verbose turn debugging messages on
|
-v --verbose turn debugging messages on
|
||||||
-q --quiet supress all logging messages
|
-q --quiet supress all logging messages
|
||||||
--version show the version
|
--version show the version
|
||||||
|
@ -52,7 +53,8 @@ proc readPart(path: Path): seq[string] =
|
||||||
try:
|
try:
|
||||||
var line: string = readLine(pathFile)
|
var line: string = readLine(pathFile)
|
||||||
while line != "":
|
while line != "":
|
||||||
result.add(line)
|
if line.startsWith("#") == false:
|
||||||
|
result.add(line)
|
||||||
line = readLine(pathFile)
|
line = readLine(pathFile)
|
||||||
except EOFError as exception:
|
except EOFError as exception:
|
||||||
discard
|
discard
|
||||||
|
@ -62,7 +64,7 @@ proc readPart(path: Path): seq[string] =
|
||||||
return result
|
return result
|
||||||
|
|
||||||
|
|
||||||
proc main*(searchPaths: seq[string]): MainResult =
|
proc main*(searchPaths: seq[string], envParts: seq[string], dedupe: bool): MainResult =
|
||||||
var parts: seq[string] = @[]
|
var parts: seq[string] = @[]
|
||||||
|
|
||||||
logger.log(lvlDebug, fmt"Processing search paths: {searchPaths}")
|
logger.log(lvlDebug, fmt"Processing search paths: {searchPaths}")
|
||||||
|
@ -83,6 +85,16 @@ proc main*(searchPaths: seq[string]): MainResult =
|
||||||
for partPath in partPaths:
|
for partPath in partPaths:
|
||||||
parts = parts & readPart(partPath)
|
parts = parts & readPart(partPath)
|
||||||
|
|
||||||
|
parts = parts & envParts
|
||||||
|
|
||||||
|
if dedupe == true:
|
||||||
|
var dedupedParts: seq[string] = @[]
|
||||||
|
for part in parts:
|
||||||
|
if dedupedParts.contains(part) == false:
|
||||||
|
dedupedParts.add(part)
|
||||||
|
|
||||||
|
parts = dedupedParts
|
||||||
|
|
||||||
return MainResult(output: parts, errorCode: QuitSuccess)
|
return MainResult(output: parts, errorCode: QuitSuccess)
|
||||||
|
|
||||||
|
|
||||||
|
@ -92,6 +104,7 @@ when isMainModule:
|
||||||
commandant.option(shell, string, "shell", "s", "bash")
|
commandant.option(shell, string, "shell", "s", "bash")
|
||||||
flag(verbose, "verbose", "v")
|
flag(verbose, "verbose", "v")
|
||||||
flag(quiet, "quiet", "q")
|
flag(quiet, "quiet", "q")
|
||||||
|
flag(dedupe, "dedupe", "d")
|
||||||
exitoption("help", "h", help_string, QuitFailure)
|
exitoption("help", "h", help_string, QuitFailure)
|
||||||
exitoption("version", "", version_string, QuitFailure)
|
exitoption("version", "", version_string, QuitFailure)
|
||||||
errorproc(handleCommandantError)
|
errorproc(handleCommandantError)
|
||||||
|
@ -104,7 +117,11 @@ when isMainModule:
|
||||||
|
|
||||||
logger.levelThreshold = loggerLevel
|
logger.levelThreshold = loggerLevel
|
||||||
|
|
||||||
var mainResult = main(searchPaths)
|
var envParts: seq[string] = @[]
|
||||||
|
var envPath = envvars.getEnv("PATH")
|
||||||
|
envParts = envPath.split(":")
|
||||||
|
|
||||||
|
var mainResult = main(searchPaths, envParts, dedupe)
|
||||||
|
|
||||||
if mainResult.output != @[] and mainResult.errorCode == QuitSuccess:
|
if mainResult.output != @[] and mainResult.errorCode == QuitSuccess:
|
||||||
var output: string = ""
|
var output: string = ""
|
||||||
|
@ -112,7 +129,7 @@ when isMainModule:
|
||||||
case shell
|
case shell
|
||||||
of "bash":
|
of "bash":
|
||||||
let pathComponents = join(mainResult.output, ":")
|
let pathComponents = join(mainResult.output, ":")
|
||||||
output = fmt"""export PATH="{pathComponents}":$PATH"""
|
output = fmt"""export PATH="{pathComponents}""""
|
||||||
|
|
||||||
if output != "":
|
if output != "":
|
||||||
echo(output)
|
echo(output)
|
||||||
|
|
1
tests/fixtures/paths.d/01-bilbo
vendored
1
tests/fixtures/paths.d/01-bilbo
vendored
|
@ -1 +1,2 @@
|
||||||
/Users/bilbo/opt/bin
|
/Users/bilbo/opt/bin
|
||||||
|
#/Users/bilbo/.local/bin
|
||||||
|
|
|
@ -7,13 +7,17 @@ suite "Test main() proc":
|
||||||
setup:
|
setup:
|
||||||
const fixturesPath = Path(currentSourcePath) / Path("..") / Path("..") / Path("fixtures")
|
const fixturesPath = Path(currentSourcePath) / Path("..") / Path("..") / Path("fixtures")
|
||||||
const pathsdFixturePath = fixturesPath / Path("paths.d")
|
const pathsdFixturePath = fixturesPath / Path("paths.d")
|
||||||
const expectedOutput = @["/Users/bilbo/opt/bin", "/opt/homebrew/bin", "/opt/homebrew/sbin"]
|
const envParts = @["/usr/local/bin", "/usr/bin"]
|
||||||
|
const expectedOutput = @[
|
||||||
|
"/Users/bilbo/opt/bin", "/opt/homebrew/bin", "/opt/homebrew/sbin",
|
||||||
|
"/usr/local/bin", "/usr/bin",
|
||||||
|
]
|
||||||
|
|
||||||
pathsd.logger.levelThreshold = lvlNone
|
pathsd.logger.levelThreshold = lvlNone
|
||||||
|
|
||||||
test "Test happy path":
|
test "Test happy path":
|
||||||
# When
|
# When
|
||||||
var mainResult = pathsd.main(@[pathsdFixturePath.string])
|
var mainResult = pathsd.main(@[pathsdFixturePath.string], envParts, false)
|
||||||
|
|
||||||
# Then
|
# Then
|
||||||
check mainResult.output == expectedOutput
|
check mainResult.output == expectedOutput
|
||||||
|
@ -21,10 +25,28 @@ suite "Test main() proc":
|
||||||
|
|
||||||
test "Test skipping search paths that don't exist":
|
test "Test skipping search paths that don't exist":
|
||||||
# When
|
# When
|
||||||
var mainResult = pathsd.main(@[
|
var mainResult = pathsd.main(
|
||||||
pathsdFixturePath.string,
|
@[
|
||||||
(fixturesPath / Path("idontexist")).string,
|
pathsdFixturePath.string,
|
||||||
])
|
(fixturesPath / Path("idontexist")).string,
|
||||||
|
],
|
||||||
|
envParts,
|
||||||
|
false,
|
||||||
|
)
|
||||||
|
|
||||||
|
# Then
|
||||||
|
check mainResult.output == expectedOutput
|
||||||
|
|
||||||
|
test "Test dedupe":
|
||||||
|
# Given
|
||||||
|
const localEnvParts = @[
|
||||||
|
"/usr/local/bin", "/usr/bin", "/Users/bilbo/opt/bin",
|
||||||
|
]
|
||||||
|
|
||||||
|
# When
|
||||||
|
var mainResult = pathsd.main(
|
||||||
|
@[pathsdFixturePath.string], localEnvParts, true,
|
||||||
|
)
|
||||||
|
|
||||||
# Then
|
# Then
|
||||||
check mainResult.output == expectedOutput
|
check mainResult.output == expectedOutput
|
||||||
|
|
Loading…
Reference in New Issue
Block a user