Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions app/Main.hs
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,9 @@ main = do
Conduit.mapM_C $ \file -> liftIO $ do
track <- AudioTrack.getTags file
fixFilePath fixFilePathOptions track
Options.NumberTracks Options.NumberTracksOptions {..} files -> do
allFiles <- ConduitUtils.runConduitWithProgress files Conduit.sinkList
Commands.numberTracks nuReverse allFiles
Options.Search options -> do
case options of
Options.SeSearchMany (Options.SearchMany {..}) ->
Expand Down
21 changes: 21 additions & 0 deletions app/Options.hs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ module Options
Command (..),
Files (..),
FixFilePathsOptions (..),
NumberTracksOptions (..),
SearchMany (..),
SearchManySource (..),
SearchOne (..),
Expand Down Expand Up @@ -75,10 +76,16 @@ data SetTagsOptions
| SetTagsFromId UUID.UUID
deriving (Show)

newtype NumberTracksOptions = NumberTracksOptions
{ nuReverse :: Bool
}
deriving (Show)

data Command
= CreateConfig
| GetTags Files
| SetTags SetTagsOptions Files
| NumberTracks NumberTracksOptions Files
| Edit Files
| Check CheckOptions Files
| FixFilePaths FixFilePathsOptions Files
Expand Down Expand Up @@ -122,6 +129,14 @@ checksP =
<*> optional albumSameTagsP
<*> artistSameGenreP

numberTracksOptionsP :: Options.Parser NumberTracksOptions
numberTracksOptionsP =
NumberTracksOptions
<$> Options.switch
( Options.long "reverse"
<> Options.help "Sort in reverse alphabetical order"
)

fixFilePathsOptionsP :: Options.Parser FixFilePathsOptions
fixFilePathsOptionsP =
FixFilePathsOptions
Expand Down Expand Up @@ -470,6 +485,12 @@ optionsP =
(SetTags <$> setTagsOptionsP <*> filesP)
(Options.progDesc "Set tags")
)
<> Options.command
"number-tracks"
( Options.info
(NumberTracks <$> numberTracksOptionsP <*> filesP)
(Options.progDesc "Set track numbers based on filename sort order")
)
<> Options.command
"edit"
( Options.info
Expand Down
15 changes: 15 additions & 0 deletions lib/Commands.hs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
module Commands
( getTags,
setTags,
numberTracks,
checkTrack,
checkDisc,
checkAlbum,
Expand All @@ -21,6 +22,7 @@ import Check.Artist qualified as Artist
import Check.Disc qualified as Disc
import Check.Track qualified as Track
import Commands.FileSystem qualified as FileSystem
import Data.List qualified as List
import Model.Album qualified as Album
import Model.Artist qualified as Artist
import Model.AudioTrack qualified as AudioTrack
Expand Down Expand Up @@ -58,6 +60,19 @@ setTags options filename =
Nothing
(SetTags.setter options)

numberTracks :: (MonadIO m) => Bool -> [Path.Path Path.Abs Path.File] -> m ()
numberTracks isReverse files =
traverse_ (uncurry setTrackNumber) $ zip [1 ..] ordered
where
sorted = List.sort files
ordered = if isReverse then reverse sorted else sorted
setTrackNumber n filename =
HTagLib.setTags
(Path.toFilePath filename)
Nothing
$ HTagLib.trackNumberSetter
$ HTagLib.mkTrackNumber n

countTrues :: [Bool] -> Int
countTrues = length . filter id

Expand Down
45 changes: 44 additions & 1 deletion tests/Tests/Commands.hs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import Path (reldir, relfile, (</>))
import Path qualified
import Path.IO qualified as Path
import Relude.Unsafe qualified as Unsafe
import Sound.HTagLib qualified as HTagLib
import System.IO qualified as System
import Test.Hspec.Expectations (shouldBe)
import Test.Tasty qualified as Tasty
Expand All @@ -19,7 +20,7 @@ import Tests.Common qualified as Common
import UnliftIO.Exception qualified as Exception

test :: Tasty.TestTree
test = Tasty.testGroup "Commands" [testFixFilePaths]
test = Tasty.testGroup "Commands" [testFixFilePaths, testNumberTracks]

testFixFilePaths :: Tasty.TestTree
testFixFilePaths =
Expand Down Expand Up @@ -118,6 +119,48 @@ testFixFilePaths =
null coverFiles `shouldBe` False
]

testNumberTracks :: Tasty.TestTree
testNumberTracks =
Tasty.testGroup
"numberTracks"
[ Tasty.testCase "ascending order" $
withThreeFiles $ \(a, b, c) -> do
Commands.numberTracks False [c, a, b]
getTrack a >>= (`shouldBe` HTagLib.mkTrackNumber 1)
getTrack b >>= (`shouldBe` HTagLib.mkTrackNumber 2)
getTrack c >>= (`shouldBe` HTagLib.mkTrackNumber 3),
Tasty.testCase "descending order" $
withThreeFiles $ \(a, b, c) -> do
Commands.numberTracks True [c, a, b]
getTrack a >>= (`shouldBe` HTagLib.mkTrackNumber 3)
getTrack b >>= (`shouldBe` HTagLib.mkTrackNumber 2)
getTrack c >>= (`shouldBe` HTagLib.mkTrackNumber 1)
]

withThreeFiles ::
( ( Path.Path Path.Abs Path.File,
Path.Path Path.Abs Path.File,
Path.Path Path.Abs Path.File
) ->
IO ()
) ->
Tasty.Assertion
withThreeFiles action =
Path.withSystemTempDir "htagcli" $ \dir -> do
let mkFile name = do
file <- Path.parseRelFile name
let absFile = dir </> file
Path.copyFile [relfile|./data/sample.mp3|] absFile
pure absFile
a <- mkFile "a.mp3"
b <- mkFile "b.mp3"
c <- mkFile "c.mp3"
action (a, b, c)

getTrack ::
(MonadIO m) => Path.Path Path.Abs Path.File -> m (Maybe HTagLib.TrackNumber)
getTrack file = AudioTrack.atTrack <$> AudioTrack.getTags file

testTargetAlreadyExists :: Bool -> Tasty.Assertion
testTargetAlreadyExists dryRun =
Common.withOneTrackFile $ \dir file -> do
Expand Down