Subject: Re: Ripping and Storing CDs
To: Curt Sampson <cjs@cynic.net>
From: Luke Mewburn <lukem@netbsd.org>
List: netbsd-users
Date: 05/20/2003 22:45:40
--2JFBq9zoW8cOFH7v
Content-Type: text/plain; charset=us-ascii
Content-Disposition: inline

On Tue, May 20, 2003 at 09:15:50PM +0900, Curt Sampson wrote:
  | 
  | So I'm thinking I'd like to back up my CD collection. (My main worry is
  | about surviving having it stolen, but of course being able to play it
  | anywhere is also something that would be nice to have.) Because I want
  | to be able to burn new copies of audio CDs if I have to, I need to be
  | able to reconstruct the original audio data, so storing them only in MP3
  | or any other lossy CODEC's format is not an option.
  | 
  | So what do people recommend for ripping and storing this stuff? Ideally
  | there'd be some sort of fairly automatic process that could fetch title
  | information as well, but it has to deal easily with a number of CDs
  | where the title information is unlikely to be available on CDDB or
  | similar. (I have a fair number of rare CDs, and some that aren't even
  | commerical releases.) I've got close to a thousand CDs to rip, so it
  | can't take up too much operator time.

I use abcde (in pkgsrc), ripping to flac (in pkgsrc) which is a lossless
encoding mechanism.  I then use a simple script to convert the flacs
to the "lowest quality" ogg vorbis files for playback over low bandwidth
networks and/or storage on my laptop when "on the road".

abcde isn't the best script, and it has its "niggles" at times, but it
does the job.  I always hand-edit the data that I get back from cddb
because there's a bunch of idiots out there who can't even take the
effort to be consistent on the one album, let alone on releases with
multiple discs...

I've attached my ~/abcde.conf and script to convert from flac to ogg
vorbis, which I use like this:
	find . -name \*.flac | xargs flactoogg

I've also attached a script I use to tweak various vorbis comments
in flacs and oggs.

Hope that helps,
Luke.

--2JFBq9zoW8cOFH7v
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename=".abcde.conf"

#	$Id$

CDROM=/dev/rcd0d

ENCNICE=4
READNICE=2
OGGENCOPTS="-q 5"
CDPARANOIAOPTS=-X
NOSUBMIT=y
OUTPUTTYPE=ogg
OUTPUTFORMAT='${ARTISTFILE}/${ALBUMFILE}/${TRACKNUM}-${TRACKFILE}.${OUTPUTTYPE}'
VAOUTPUTFORMAT='various/${ALBUMFILE}/${TRACKNUM}-${TRACKFILE}.${OUTPUTTYPE}'
CDDBURL="http://us.freedb.org/~cddb/cddb.cgi"

mungefilename ()
{
	echo "$@" | tr -d "[:cntrl:]'?" | tr A-Z a-z | tr -cs -- "-.A-Za-z0-9" _
}

# new stuff: Mon Dec 16 04:27:50 UTC 2002
OUTPUTTYPE=flac
FLACOPTS="-V -8"

--2JFBq9zoW8cOFH7v
Content-Type: text/plain; charset=us-ascii
Content-Description: flactoogg
Content-Disposition: attachment; filename=flactoogg

#!/bin/sh

OGGQUALITY=1

flactoogg()
{
	file=$1
	filebn="${file%.flac}"
	fileogg="${filebn}.ogg"
	if [ "${filebn}" = "${file}" ]; then
#X		echo "Skipping ${file}"
		return
	fi
	if [ "${fileogg}" -nt "${file}" ]; then
#X		echo "Skipping ${file}"
		return
	fi

	echo "Converting ${file}"

	tmptag=${filebn}.tmp.tag
	tmpogg=${filebn}.tmp.ogg
	trap "/bin/rm -f $tmptag $tmpogg; exit 0"  0 2 3 13

#	metaflac --list --block-type=VORBIS_COMMENT "${file}" | \
#	    sed -ne 's/^ *comment\[[0-9]*\]: //p' > ${tmptag}
	metaflac --export-vc-to=${tmptag} "${file}"


	flac -sdc "${file}" | oggenc -Q -q ${OGGQUALITY} -o "${tmpogg}" -

	if [ -s "${tmptag}" ]; then
		vorbiscomment -w -c "${tmptag}" "${tmpogg}" "${fileogg}"
	else
		mv "${tmpogg}" "${fileogg}"
	fi

	rm -f ${tmpogg} ${tmptag}
	trap "-"  0 2 3 13
}


for f in $@; do
	flactoogg ${f}
done

--2JFBq9zoW8cOFH7v
Content-Type: text/plain; charset=us-ascii
Content-Description: tweakvorbis
Content-Disposition: attachment; filename=_fixvarious

#!/bin/sh

trap "rm -f tmp.tag tmp.newtag tmp.ogg; exit 0"  0 2 3 13


fixcomment()
{
	awk '
	/=/ {
		var=substr($0,0,index($0, "=")-1)
		val=substr($0,index($0, "=")+1)
		if (var == "ALBUM")
			gsub("^'"${ARTIST}"' - ", "", val)
		res[var] = val
	}
	END {
		artist="'"${ARTIST2TITLE}"'"
		if (artist != "" && artist != res["ARTIST"]) {
			res["TITLE"] = res["ARTIST"] " - " res["TITLE"]
			res["ARTIST"] = artist
		}
		artist="'"${ARTIST}"'"
		if (artist != "" && artist != res["ARTIST"]) {
			res["ARTIST"] = artist
		}
		album="'"${ALBUM}"'"
		if (album != "" && album != res["ALBUM"]) {
			res["ALBUM"] = album
		}
		for (f in res)
			printf "%s=%s\n", f, res[f]
	}
	'
}

fixogg()
{
	vorbiscomment -l "$1" | sort > tmp.tag
	fixcomment < tmp.tag | sort > tmp.newtag
	if cmp -s tmp.tag tmp.newtag; then
		echo "	no change required"
	else
		diff tmp.tag tmp.newtag
		vorbiscomment -w -c tmp.newtag "$1" tmp.ogg && mv tmp.ogg "$1"
		echo "	fixed"
	fi
}

fixflac()
{
	metaflac --export-vc-to=- "$1" \
		| sort > tmp.tag
	fixcomment < tmp.tag | sort > tmp.newtag
	if cmp -s tmp.tag tmp.newtag; then
		echo "	no change required"
	else
		diff tmp.tag tmp.newtag
		metaflac --preserve-modtime --remove-vc-all --import-vc-from=tmp.newtag "$1"
		echo "	fixed"
	fi
}


for f in $@; do
	case "$f" in
	*.ogg)
		echo "ogg:  $f"
		fixogg $f
		;;
	*.flac)
		echo "flac: $f"
		fixflac $f
		;;
	*)
	esac
done

--2JFBq9zoW8cOFH7v--