Difference between revisions of "Convert FLAC to MP3"

From ArchWiki
Jump to: navigation, search
(how to convert FLAC to MP3 via commandline)
Line 1: Line 1:
[[Category:Development (English)]]
+
[[Category:Audio/Video (English)]]
[[Category: HOWTOs (English)]]
+
[[Category:Scripts (English)]]
[[Category:Package management (English)]]
+
[[Category:HOWTOs (English)]]
{{i18n_links_start}}
+
{{i18n_entry|English|The_Arch_package_making_HOW-TO_-_with_guidelines}}
+
{{i18n_entry|Русский|The_Arch_package_making_HOW-TO_-_with_guidelines(russian)}}
+
{{i18n_entry|简体中文|The_Arch_package_making_HOW-TO_-_with_guidelines(Chinese)}}
+
{{i18n_links_end}}
+
  
这个文档 [[ABS_-_The_Arch_Build_System | ABS - The Arch Build System]] 提供了一份良好的用于制作和修改 Arch Linux 软件包所需工具和文件的总览。如果你只想要定制或重新编译一个已经存在的软件包,这里应该已经提供了足够的信息。但是,如果你想要制作一个新的软件包,你还需要一些额外的指南。这个文档假定你已经事先阅读并掌握了 ABS 的描述。
+
Here is a script that will convert FLAC to MP3 via the commandline.
  
==准备文件==
+
Essentially, the .flac files within a directory will be decompressed to .wav and then the resulting .wav files will be encoded to .mp3 using the latest LAME switches for encodings (''-V 0 --vbr-new''). The ID3 tags of the original .flac files will be passed to the resulting .mp3 files.
所有用于制作一个软件包所需的信息放在 <code>PKGBUILD</code>  文件中。当你运行 <code>makepkg</code> 命令,它将在当前工作目录中寻找 <code>PKGBUILD</code> 文件,然后根据 <code>PKGBUILD</code> 文件中的指令编译软件的源代码。当编译成功后,得到的二进制代码,包括诸如包版本和依赖等meta-信息将封装在名叫 <code>name.pkg.tar.gz</code> 的软件包中,你可以使用 <code>pacman -Up <package file></code> 命令将其安装。
+
  
<code>PKGBUILD</code> 文件包含 '''所有''' 用于制作一个软件包所需的指令,这些指令以能够被 bash 识别的的格式存在(don't worry if that little tidbit of clue doesn't help you)。[[ABS_-_The_Arch_Build_System | ABS]] 条目中描述了这里使用的变量,但是最重要的也是最让人迷惑的变量在这里recapped。为了开始制作一个新的包,你应该首先创建一个空的目录,最好取名为 <code>/var/abs/local/<PKGNAME></code>。这样的话,它可以很好的统一到统一的 ABS 树,但如果你没有同步该树的话,cvsup 不会接触(touch)它。进入你新建的目录,创建 <code>PKGBUILD</code> 文件,你可以直接从 <code>/var/abs/PKGBUILD.proto</code> 复制虚构的原型,也可以复制其他软件包的 <code>PKGBUILD</code> 。如果你不需创建一个全新的文件,而只需修改其中的编译选项的话,后者是非常合适的选择。
+
The original .flac files will not be harmed and the resulting .mp3s will be in the same directory.
  
无论你用那种方式,总之你需要一个 <code>PKGBUILD</code> 文件。
+
For more information on LAME switches/settings such as V0, visit [http://wiki.hydrogenaudio.org/index.php?title=LAME Hydrogenaudio LAME Wiki]. V0 is roughly equivalent to --preset extreme which results in a variable bitrate usually between 220-260. The audio of a V0 is transparent, meaning one cannot tell the difference between the lossy file and the original source (compact disc/lossless), but yet the file size is a quite reasonable.
  
==编辑变量==
+
First you need to install the following packages: flac, lame, and id3
  
现在打开它,根据你构建的包的情况设置各个变量的值:
+
<pre>
<br /><br />
+
pacman -S flac lame id3
*'''pkgname:''' 将这个变量设置为你的包的名字。按照惯例,你应该使用小写字母。最好包的名字与你所在的工作目录的名字相同,当然也与你将要下载的包含源程序的 tar.gz 文件名相同,但这并不是必须的。
+
</pre>
  
*'''pkgver:''' 设置包的版本。它可以包含字母、数字和点,但不能有连字符。它由你打包的程序使用的版本系统决定(主版本.次版本.漏洞修复版本、major.日期等)。另外,在大多数情况下,你可以遵循源代码包的文件名的一部分的版本,以便后续步骤变得更为简单和灵活。还要注意:如果包的作者在其版本编号方案中使用了短横,请用下划线替代它。('0.99-10'  =>  '0.99_10')
+
Once those are installed, copy the following script and make it executable:
  
*'''pkgrel:''' 这个变量从 1 开始,你每重新发布一次,其值将增加 1 ,它的目的是区分一个包的同一版本的连续构建。有时候第一次发布的包有问题或错误。当你第二次发布这个包时,你将 <code>pkgrel</code> 变量加 1 ,这样 pacman 知道它需要重新安装。当这个包又发布了一个新的 '''版本''' 时,你将 <code>pkgrel</code> 变量重设为 1
+
<pre>
 +
for a in *.flac
  
*'''pkgdesc:''' 该变量为该包的简短的描述,通常应该少于 76 个字符。通常并需要重复程序的名字。<code>OpenGL accelerated X server</code> 优于 <code>xgl is a OpenGL...</code> 。
+
do
 +
OUTF=`echo "$a" | sed s/\.flac/.mp3/g`
  
*'''arch:''' 该变量应该为架构的名称,通常为 'i686' ,它描述的是该 PKGBUILD 文件能够使用的架构。你可以在构建过程中使用 <code>$arch</code> 来获取这个变量。
+
ARTIST=`metaflac "$a" --show-tag=ARTIST | sed s/.*=//g`
 +
TITLE=`metaflac "$a" --show-tag=TITLE | sed s/.*=//g`
 +
ALBUM=`metaflac "$a" --show-tag=ALBUM | sed s/.*=//g`
 +
GENRE=`metaflac "$a" --show-tag=GENRE | sed s/.*=//g`
 +
TRACKNUMBER=`metaflac "$a" --show-tag=TRACKNUMBER | sed s/.*=//g`
 +
DATE=`metaflac "$a" --show-tag=DATE | sed s/.*=//g`
  
*'''url:''' 该变量为程序的官方站点的地址,这样有兴趣的人可以由此获得更多的信息。
+
flac -c -d "$a" | lame -m j -q 0 --vbr-new -V 0 -s 44.1 - "$OUTF"
 +
id3 -t "$TITLE" -T "${TRACKNUMBER:-0}" -a "$ARTIST" -A "$ALBUM" -y "$DATE" -g "${GENRE:-12}" "$OUTF"
  
*'''license:''' 许可的类型,如果你不知道,请将其写成 'unknow' 。
+
done
 +
</pre>
  
*'''depends:''' 该变量为在该程序能够运行前所必须安装的一系列包的名字的序列,用空格分开每个包名。这些包名可以用单引号引起来,以避免可能的 shell quoting 的问题,并且该序列必须用圆括号括起来。有时,一个程序需要一个最低版本的依赖;在这种情况下,请将数学上的 "大于 或 等于" 运算符,并将这些运算符也放在引号里。这里是一个添加 glibc 包的依赖的实例,slang 库的版本至少应为 1.8.0 :'''<code>depends('glibc' 'slang>=1.8.0')</code>'''
+
Save the script as flac2mp3 in your home directory. As root copy the script to /usr/local/bin
  
*'''makedepends:''' 该变量为只是在打包过程中需要而在安装后的*使用*过程中并不需要的包的名字的序列。举例:<code>unarj</code> 用于在打包过程中解压某些补丁。
+
<pre>
 +
cp flac2mp3.sh /usr/local/bin
 +
</pre>
  
*'''provides:''' 该变量为因为即将构建的包提供了相同的作用而变得不再需要的包的名字的序列。
+
Once that is done, you are ready to use the script. Open up a terminal and cd to the directory of .flac files that you wish to convert and run ''flac2mp3''
  
*'''conflicts:''' 该变量为安装该包后会产生问题的包的名字的序列。
+
Done. The newly-encoded .mp3s will be V0.
 
+
*'''replaces:''' 该变量为即将构建的包可以替代的陈旧的包的名字的序列。
+
 
+
*'''source:''' 该变量为构建该包所需文件的序列,至少应包含程序源的地址,在大多数情况下是一个完整的用双引号引起来的 http 或 ftp 地址。 这里的 <code>PKGBUILD</code> 的样本向你很好的展示了如何使用以前设置的包名和包版本的变量。如果你发现你需要补充一些不能通过下载得到的文件如自制的补丁时,你只需要要将这些文件与 <code>PKGBUILD</code> 放在同一目录即可,然后将补丁的文件名添加在 source 的序列中。任何你在此添加的路径为相对于 <code>PKGBUILD</code> 所在目录的相对路径。在实际的构建过程开始前,所有此处涉及的文件将被下载或检查是否存在,如果存在任何文件遗失, <code>makepkg</code> 将不能进行。
+
 
+
*'''md5sums:''' 源文件的 md5 检查值,用空格分开,并用引号引起来。当 source 序列中的所有文件都存在时,每个文件的 md5 计算值将自动产生并于这里提供的值对照,'''这些值的顺序应与 source 序列中的顺序相同。''' 同时,源文件本身的顺序并不重要,重要的是与 md5sums 的顺序一致,因为 <code>makepkg</code> 不会猜测 md5sums 属于哪个源文件,所以如果他们不能匹配,则会开始报错,这样可以防止下载错误或程序被篡改。你可以在包含 <code>PKGBUILD</code> 文件的目录下使用 <code>makepkg -g</code> 命令简单的得到 md5sums (在你将源序列正确的设置后) 。<code>makepkg -g >>PKGBUILD</code> 将生成这些 sums 并将其附在 <code>PKGBUILD</code> 的后面,你可以将其挪到合适的位置上。
+
 
+
到目前为止,你只是把与包有关的 meta-信息 设置好了;到哪去下载源代码,包的名字是什么等。下一步是补充如何实际 ''编译和安装'' 你将打包的程序的指令。
+
 
+
==使用源代码==
+
现在你需要下载源代码包,将其解压,记录所有需要的用于编译和安装它的命令。<code>PKGBUILD</code> 内的 <code>build()</code> 函数的作用就是将这些步骤重复一遍,并在这些过程完成以后将所有的东西封装起来。
+
 
+
现在你需要编辑在 <code>PKGBUILD</code> 内的 build() 函数的内容。这个函数使用普通的 bash 语法的  shell 命令。该函数的基本作用就是自动的编译程序并且创建一个用于安装程序的 <code>pkg</code> 目录,然后让 <code>makepkg</code> 将所有的文件封装起来,而不用从你实际的文件系统中将相关文件提取出来。
+
 
+
===build() 函数===
+
通常 build 函数的第一步是进入因解压源代码包生成的目录中。你可以使用 <code>$startdir</code> 变量(它指的是包含<code>PKGBUILD</code>的目录)。你也可以使用你先前设置的 $pkgname 和 $pkgver 变量。举个例子,取决于由 makepkg 解压产生的目录的名字,你的 build 函数的第一个命令可能是 <code>cd $startdir/src/$pkgname-$pkgver</code> ,这通常是一种非常可能的情况,除非该程序的作者是一个十足的麻烦制造者。
+
 
+
编译程序是一个较难的部分。我这里假定你可以成功的手动编译该程序,因为所有可能的步骤将不可避免。这也是程序的作者应该写 README 和 INSTALL 文件的原因。
+
 
+
现在你在那个目录中,你需要将所有用来编译这些文件的命令列出来。在一些简单的情况下,你只需使用现行的 <code>gcc</code> 命令来编译这些包。
+
 
+
好的事情是,如果你可以手动编译该包,你基本上只需将你使用的命令列在这里,一切将会很好的进行下去。因为很多包喜欢将其文件安装在相对的 <code>/usr/local</code>  目录中,为了使命令注意到这一点,你可能需要补充一个参数到配置脚本中。<code>PKGBUILD</code> 的样本可以作为一个例子。当然你的情况也有可能与样本不同。再说一次,你的情况有可能不同。
+
 
+
<code>build()</code> 函数的下一步是将已经编译好的文件放在一个 <code>makepkg</code> 可以将其打包的目录。这个目录就是 <code>pkg</code> 目录。该目录是仿照程序安装步骤中你文件系统的根目录。任何在实际安装过程进入你文件系统的的文件将按照相同的目录结构进入 <code>pkg</code> 目录。(打个比方。加入你想要将 <code>myprog</code> 文件安装在 <code>/usr/bin</code> 中,这里你应该将其放在 <code>$startdir/pkg/usr/bin</code> 中)。幸运的是只有少数程序需要用户手动复制很多文件,但他们需要补充某些安装步骤来替代本来应该自动进行的步骤,通常通过运行 "make install" 来调用。它是 '''critical''' ,但是,that you find out how to tell this installation procedure that it's supposed to stuff all it's nifty files '''not''' into your /, but into <code>$startdir/pkg/</code> instead! Otherwise you'll end up with an empty package file, and the binaries of the program you installed "correctly" added to your system already. Most of the time you'll have to supply the prefix parameter to the "make install" call as shown in the prototype, but it's very well possible that the program you're packaging expects an altogether different approach, but here are some hints:
+
 
+
* 有时 <code>configure</code> 脚本可以使用一个的 prefix 属性来标明安装位置。例如你可以在这些配置中使用 <code>./configure --prefix=$startdir/pkg/usr</code> 代码。
+
 
+
* 有时在 <code>make install</code> 命令后面会附加一个 <code>PREFIX</code> 选项。有时你可以设置为一个变量,而有时你需要设置命令。情况糟糕时,你不得不使用 sed 编辑 Makefile(s)()或给它打上你自己制作的补丁。
+
 
+
* 还有可能需要其他一些类型的安装脚本来制定程序的安装位置。
+
 
+
* 某些情况下,程序需要在一个单独的文件夹内运行,这时你最好将他们复制到 <code>$startdir/pkg/opt</code> 。
+
 
+
可能你已经知道了,这是一个需要一些知识和经验的的部分。你可以通过浏览 ABS 树中的 <code>PKGBUILD</code> 文件获得帮助,那些 PKGBUILD 文件已经经过测试并包含一些已经被证明有用的小技巧。
+
 
+
多数情况下, 程序的安装程序需要在 <code>pkg/</code> 下面建立子目录。 the installation routine of the program will take care to create any subdirectories below the <code>pkg/</code> directory. If it does not, however, you'll get a lot of errors during the install stage as files are copied to nonexistent subdirectories. In that case you'll have to create the needed subdirectories by adding the appropriate <code>mkdir</code> commands in the <code>build()</code> function before running the installation procedure. The actual directory structure is package dependent, of course; some programs need to place files in <code>/etc</code> or <code>/usr</code> while others might need to use <code>/bin</code> or <code>/opt</code>.  Most will need to create several directories.  You can do all of this with the <code>mkdir -p $startdir/pkg/OTHER/DIRS/AS/NEEDED</code> command, where OTHER/DIRS/AS/NEEDED represent directories at the root of the filesystem.
+
 
+
==测试 PKGBUILD==
+
 
+
As you are writing the <code>PKGBUILD</code>'s <code>build()</code> function, you will want to test your changes frequently to ensure there are no bugs. You can do this using the <code>makepkg</code> command in the directory containing the <code>PKGBUILD</code>. With a properly formatted <code>PKGBUILD</code>, this will create a package, but with a broken or unfinished one it will throw an error. Hopefully it will be a descriptive error!
+
 
+
If running <code>makepkg</code> finished successfully, it will place a shiny new file called $pkgname-$pkgver.pkg.tar.gz in your working directory. This is a pacman package and can be installed with the <code>pacman -U</code> and <code>pacman -A</code> options, or added to a local or web based repository.  Note that just because a package file was built it doesn't mean it works!  It might conceivably contain only the directory structure and no files whatsoever if, for example, you specified a prefix improperly. You can use pacman's query functions to display a list of files contained in the package and the dependencies it requires, and compare those with what you consider as correct. "pacman -Qlp <package file>" and "pacman -Qip <package file>" do the trick.
+
 
+
If the package looks sane, that's all you need to do. However, if you plan on releasing the package or PKGBUILD, it is imperative that you check and double check and re-double-check the contents of the depends array. This should contain a list of all packages that need to be installed in order for your package to work. You only need to list first level depends in the depends array. That is, you do not need to list packages that your program depends on if other packages that your program depends on are already listed.
+
 
+
For example, <code>gtk2</code> depends on <code>glib2</code>. Like most open source C programs, it also requires <code>glibc</code> to be installed. However, <code>glibc</code> does not need to be listed as a dependency for <code>gtk2</code> because it is a dependency for <code>glib2</code>, and <code>glib2</code> is already listed in <code>gtk2</code>.
+
 
+
There are some tools you can use to check dependencies, including Jason Chu's famous <code>namcap</code> program (<code>pacman -Sy namcap</code>), and the more arcane <code>ldd</code> program.  Check the man pages for these programs and the links at the end of this document for more information.  You should also scour the program's documentation and website (some nice developers have a page called "dependencies" that helps a lot).
+
 
+
==测试包==
+
同样请确保二进制包''运行''无误!发布一个包含所有需要的文件,但却因为一些不能与其他部分很好的合作的模糊的设置选项而导致出错也是很恼人的。如果你只是想要编译用于你自己的系统的软件包,当然,你不需要对这个质量保证步骤太过费心,毕竟你是唯一受这些错误困扰的人。
+
 
+
==总结==
+
* 下载你想要打包的源代码包
+
* 尝试编译该包并将其安装在假定的目录中
+
* 复制 <code>/var/abs/PKGBUILD.proto</code> 样本,在一个临时工作目中将其改名为 <code>PKGBUILD</code>
+
* 根据你打的包的需要修改 PKGBUILD
+
* 运行 <code>makepkg</code> 命令检查得到的包是否构建无误
+
* 如果有问题,重复最后两个步骤
+
 
+
==有用的链接==
+
* [[ABS_-_The_Arch_Build_System | ABS - The Arch Build System]]
+
* [http://www.archlinux.org/pacman/makepkg.8.html makepkg man page]
+
* [http://bbs.archlinux.org/viewtopic.php?t=4 about dependencies]
+
* [http://bbs.archlinux.org/viewtopic.php?t=1590 makepkg tutorial]
+
* [[PKGBUILD help|PKGBUILD Help]]
+
* [[Arch CVS & SVN PKGBUILD guidelines]]
+
 
+
==警告==
+
* Before you can automate the package building process, you should have done it manually at least once unless you know ''exactly'' what you're doing ''in advance'', in which case you would not be reading this in the first place. Unfortunately, although a good bunch of program authors stick to the 3-step build cycle of "./configure; make; make install", this is not always the case, and things can get real ugly if you have to apply patches to make everything work at all. Rule of thumb: If you can't get the program to compile from the source tarball, and make it install itself to a defined, temporary subdirectory, you don't even need to try packaging it. There isn't any magic pixie dust in <code>makepkg</code> that makes source problems go away.
+
* In a few cases, the packages are not even available as source and you have to use something like <code>sh installer.run</code> to get it to work. You will have to do quite a bit of research (read READMEs, INSTALL instructions, man pages, perhaps ebuilds from gentoo or other package installers, possibly even the MAKEFILEs or source code) to get it working. In some really bad cases, you have to edit the source files to get it to work at all. However, <code>makepkg</code> needs to be completely autonomous, with no user input. Therefore if you need to edit the Makefiles, you may have to bundle a custom patch with the <code>PKGBUILD</code> and install it from inside the <code>build()</code> function, or you might have to issue some <code>sed</code> commands from inside the <code>build()</code> function.
+
* Note that just because a package file was built it doesn't mean it works!  It might conceivably contain only the directory structure and no files whatsoever if, for example, you specified a prefix improperly. You can use pacman's query functions to display a list of files contained in the package and the dependencies it requires, and compare those with what you consider as correct. "pacman -Qlp <package file>" and "pacman -Qip <package file>" do the trick.
+

Revision as of 05:43, 11 January 2008


Here is a script that will convert FLAC to MP3 via the commandline.

Essentially, the .flac files within a directory will be decompressed to .wav and then the resulting .wav files will be encoded to .mp3 using the latest LAME switches for encodings (-V 0 --vbr-new). The ID3 tags of the original .flac files will be passed to the resulting .mp3 files.

The original .flac files will not be harmed and the resulting .mp3s will be in the same directory.

For more information on LAME switches/settings such as V0, visit Hydrogenaudio LAME Wiki. V0 is roughly equivalent to --preset extreme which results in a variable bitrate usually between 220-260. The audio of a V0 is transparent, meaning one cannot tell the difference between the lossy file and the original source (compact disc/lossless), but yet the file size is a quite reasonable.

First you need to install the following packages: flac, lame, and id3

pacman -S flac lame id3

Once those are installed, copy the following script and make it executable:

for a in *.flac

do
OUTF=`echo "$a" | sed s/\.flac/.mp3/g`

ARTIST=`metaflac "$a" --show-tag=ARTIST | sed s/.*=//g`
TITLE=`metaflac "$a" --show-tag=TITLE | sed s/.*=//g`
ALBUM=`metaflac "$a" --show-tag=ALBUM | sed s/.*=//g`
GENRE=`metaflac "$a" --show-tag=GENRE | sed s/.*=//g`
TRACKNUMBER=`metaflac "$a" --show-tag=TRACKNUMBER | sed s/.*=//g`
DATE=`metaflac "$a" --show-tag=DATE | sed s/.*=//g`

flac -c -d "$a" | lame -m j -q 0 --vbr-new -V 0 -s 44.1 - "$OUTF"
id3 -t "$TITLE" -T "${TRACKNUMBER:-0}" -a "$ARTIST" -A "$ALBUM" -y "$DATE" -g "${GENRE:-12}" "$OUTF"

done

Save the script as flac2mp3 in your home directory. As root copy the script to /usr/local/bin

cp flac2mp3.sh /usr/local/bin

Once that is done, you are ready to use the script. Open up a terminal and cd to the directory of .flac files that you wish to convert and run flac2mp3

Done. The newly-encoded .mp3s will be V0.