mirror of
https://github.com/rwinkhart/flac2pod.git
synced 2026-09-03 23:57:19 -04:00
Initial commit
This commit is contained in:
@@ -1,2 +1,27 @@
|
|||||||
# flac2pod
|
# flac2pod
|
||||||
Seamlessly converts your existing FLAC library to be played on an iPod Classic.
|
Seamlessly converts your existing FLAC library to be played on an iPod Classic.
|
||||||
|
|
||||||
|
This script makes use of ffmpeg to convert your existing FLAC music library to either MP3-320 or ALAC for easy iPod Classic use. It also takes advantage of "rg2sc" (https://github.com/rwinkhart/rg2sc) to convert any existing ReplayGain tags to Apple Sound Check tags that are compatible with Apple products.
|
||||||
|
|
||||||
|
# Usage
|
||||||
|
|
||||||
|
```
|
||||||
|
flac2pod -f --mp3 # will convert library to MP3-320 and forcefully update Sound Check tags (even if they already exist)
|
||||||
|
|
||||||
|
flac2pod --alac # will convert library to ALAC in a .m4a container - only updates missing Sound Check tags
|
||||||
|
|
||||||
|
flac2pod # will convert library to MP3-320 - only updates missing Sound Check tags
|
||||||
|
```
|
||||||
|
|
||||||
|
In order for flac2pod to function, your library must be structured as follows:
|
||||||
|
Library dir -> Artist dir -> Album dir -> FLAC files
|
||||||
|
|
||||||
|
When prompted for the source directory, you want to input your library parent directory.
|
||||||
|
|
||||||
|
# Installation
|
||||||
|
|
||||||
|
flac2pod is available in the AUR as "flac2pod". If installing on a non-Arch-based distribution, follow the manual installation instructions:
|
||||||
|
|
||||||
|
- copy the flac2pod executable from https://github.com/rwinkhart/flac2pod/blob/master/bin/flac2pod to your /usr/bin/
|
||||||
|
- copy the rg2sc executable from https://github.com/rwinkhart/rg2sc/blob/master/bin/rg2sc to your /usr/bin
|
||||||
|
- install python-mutagen, ffmpeg, and lame
|
||||||
|
|||||||
Executable
+84
@@ -0,0 +1,84 @@
|
|||||||
|
#!/bin/python3
|
||||||
|
|
||||||
|
# external modules
|
||||||
|
|
||||||
|
from os import path, system, walk
|
||||||
|
from pathlib import Path
|
||||||
|
from sys import argv
|
||||||
|
|
||||||
|
|
||||||
|
# utility functions
|
||||||
|
|
||||||
|
def scan_source():
|
||||||
|
_artist_dirs, _album_dirs, _full_paths = [], [], []
|
||||||
|
for _root, _directories, _files in walk(path.expanduser(source)):
|
||||||
|
for _dir in sorted(_directories):
|
||||||
|
if not _root.endswith(path.expanduser(source)):
|
||||||
|
_artist_dirs.append(_root)
|
||||||
|
_artist_dirs = list(set(_artist_dirs))
|
||||||
|
for _artist in sorted(_artist_dirs):
|
||||||
|
for _root, _directories, _files in walk(path.expanduser(_artist)):
|
||||||
|
if not _root.endswith(path.expanduser(_artist)):
|
||||||
|
_album_dirs.append(_root)
|
||||||
|
_album_dirs = list(set(_album_dirs))
|
||||||
|
for _album in sorted(_album_dirs):
|
||||||
|
for _root, _directories, _files in walk(path.expanduser(_album)):
|
||||||
|
for _filename in _files:
|
||||||
|
if _filename.endswith('.flac'):
|
||||||
|
_full_paths.append(f"{_album}/{_filename[:-5]}")
|
||||||
|
return _album_dirs, _full_paths
|
||||||
|
|
||||||
|
|
||||||
|
def create_destination():
|
||||||
|
for _dir in source_directories[0]:
|
||||||
|
Path(path.expanduser(_dir.replace(path.expanduser(source), path.expanduser(destination))))\
|
||||||
|
.mkdir(0o700, parents=True, exist_ok=True)
|
||||||
|
|
||||||
|
|
||||||
|
def scan_destination_convert_alac():
|
||||||
|
for _file in source_directories[1]:
|
||||||
|
if not Path(f"{_file.replace(path.expanduser(source), path.expanduser(destination))}.m4a").is_file():
|
||||||
|
system(f"ffmpeg -i '{_file}.flac' -c:v copy -c:a alac -map_metadata 0 -id3v2_version 3 "
|
||||||
|
f"'{_file.replace(path.expanduser(source), path.expanduser(destination))}.m4a'")
|
||||||
|
|
||||||
|
|
||||||
|
def scan_destination_convert_mp3():
|
||||||
|
for _file in source_directories[1]:
|
||||||
|
print(_file)
|
||||||
|
if not Path(f"{_file.replace(path.expanduser(source), path.expanduser(destination))}.mp3").is_file():
|
||||||
|
system(f"ffmpeg -i '{_file}.flac' -c:v copy -ab 320k -map_metadata 0 -id3v2_version 3 "
|
||||||
|
f"'{_file.replace(path.expanduser(source), path.expanduser(destination))}.mp3'")
|
||||||
|
|
||||||
|
|
||||||
|
def rg2sc():
|
||||||
|
if argument.__contains__('-f'):
|
||||||
|
system(f"{rg2sc} -f {destination}")
|
||||||
|
else:
|
||||||
|
system(f"{rg2sc} {destination}")
|
||||||
|
|
||||||
|
|
||||||
|
# program start sequence
|
||||||
|
|
||||||
|
# retrieve typed argument
|
||||||
|
argument_list = argv
|
||||||
|
i, argument = 0, ''
|
||||||
|
for _ in argument_list:
|
||||||
|
while i < len(argument_list) - 1:
|
||||||
|
i += 1
|
||||||
|
argument += argument_list[i] + ' '
|
||||||
|
argument = argument[:-1]
|
||||||
|
|
||||||
|
source = input('Source parent directory: ')
|
||||||
|
if source.endswith('/'):
|
||||||
|
source = source[:-1]
|
||||||
|
destination = input('Destination parent directory: ')
|
||||||
|
if destination.endswith('/'):
|
||||||
|
destination = destination[:-1]
|
||||||
|
|
||||||
|
source_directories = scan_source()
|
||||||
|
create_destination()
|
||||||
|
if argument.__contains__('--alac'):
|
||||||
|
scan_destination_convert_alac()
|
||||||
|
else:
|
||||||
|
scan_destination_convert_mp3()
|
||||||
|
rg2sc()
|
||||||
Executable
+53
@@ -0,0 +1,53 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# This script packages flac2pod (from source) for Arch Linux.
|
||||||
|
|
||||||
|
echo -e '\n\nThe value entered in this field will only affect the version reported to the package manager. The latest source is used regardless.\n'
|
||||||
|
read -r -p "Version number: " version
|
||||||
|
read -r -p "Revision number: " revision
|
||||||
|
|
||||||
|
echo -e '\nOptions (please enter the number only):'
|
||||||
|
echo -e '\n1. GitHub Release Tag\n2. Local\n'
|
||||||
|
read -r -p "Source (for build scripts): " source
|
||||||
|
|
||||||
|
if [ "$source" == "1" ]; then
|
||||||
|
source='https://github.com/rwinkhart/flac2pod/releases/download/v$pkgver/flac2pod-$pkgver.tar.xz'
|
||||||
|
else
|
||||||
|
source=local://flac2pod-"$version".tar.xz
|
||||||
|
fi
|
||||||
|
|
||||||
|
|
||||||
|
# Archive creation
|
||||||
|
echo -e '\nPackaging as generic...\n'
|
||||||
|
mkdir -p packages/archtemp/usr
|
||||||
|
cp -r bin packages/archtemp/usr/
|
||||||
|
cp -r share packages/archtemp/usr/
|
||||||
|
tar -C packages/archtemp -cvf packages/flac2pod-"$version".tar.xz usr/
|
||||||
|
rm -rf packages/archtemp
|
||||||
|
sha512="$(sha512sum packages/flac2pod-"$version".tar.xz | awk '{print $1;}')"
|
||||||
|
echo -e "\nsha512 sum:\n$sha512"
|
||||||
|
echo -e "\nGeneric packaging complete.\n"
|
||||||
|
|
||||||
|
# PKGBUILD creation
|
||||||
|
echo -e '\nGenerating PKGBUILD...'
|
||||||
|
echo "# Maintainer: Randall Winkhart <idgr at tutanota dot com>
|
||||||
|
|
||||||
|
pkgname=flac2pod
|
||||||
|
pkgver="$version"
|
||||||
|
pkgrel="$revision"
|
||||||
|
pkgdesc='Converts your FLAC library to be iPod-ready'
|
||||||
|
url='https://github.com/rwinkhart/flac2pod'
|
||||||
|
arch=('any')
|
||||||
|
license=('GPL2')
|
||||||
|
depends=(python ffmpeg lame rg2sc)
|
||||||
|
|
||||||
|
source=(\""$source"\")
|
||||||
|
sha512sums=('"$sha512"')
|
||||||
|
|
||||||
|
package() {
|
||||||
|
|
||||||
|
tar xf flac2pod-"\"\$pkgver\"".tar.xz -C "\"\${pkgdir}\""
|
||||||
|
|
||||||
|
}
|
||||||
|
" > packages/PKGBUILD
|
||||||
|
echo -e "\nPKGBUILD generated.\n"
|
||||||
Executable
+15
@@ -0,0 +1,15 @@
|
|||||||
|
flac2pod is a FOSS audio transcoding script for preparing music for an Apple iPod.
|
||||||
|
Copyright (C) 2022 Randall Winkhart idgr@tutanota.com
|
||||||
|
|
||||||
|
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
|
||||||
|
the Free Software Foundation; either version 2 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
Reference in New Issue
Block a user