date | author |
---|---|
2024-07-05 |
Matthias C. Hormann (Moonbase59) |
Table of Contents ⇧
- Table of Contents
- How to avoid long station startup time?
- How to assure jingles are not cut off?
- How to ensure pre-recorded shows or podcasts aren’t cut off early?
- How to pre-process more than one file at a time ("mass tagging")?
- What tagging software to use?
- Can I use
cue_file
to replaygain my files? - Can I use
cue_file
to manually add/overwrite tags when pre-processing? - How to make transitions tighter, i.e. overlay earlier?
- How to make transitions longer, i.e. overlay later and keep every bit of a song ending?
- Can I completely disable the "sustained endings" feature?
- Can I completely disable the "longtail" feature?
- How to ensure Autocue doesn’t mess with Ad Insertion files?
- How to ensure Autocue doesn’t try to process video files?
- Why should I use
check_autocue_setup
, and what does it do? - What are good first steps to use Autocue in my own Liquidsoap script?
- What will happen when I switch to the upcoming Liquidsoap 2.3.0?
- What can I do if some files or a remote playlist simply don’t play?
- What exactly is
liq_cue_file
for, and should I use it?
How to avoid long station startup time? ⇧
To ensure continuous playout without interruptions, Liquidsoap tries to prepare at least one track from each playlist to be ready for switching and fallbacks. This can strain your system a bit on startup, especially if you have long files like recordings, prerecorded shows, DJ sets, podcasts and the like. The number of existing playlists also affects startup time.
There are two basic strategies to avoid this, which can also be used in combination:
- Pre-process your files (at least the long ones!) using the commandline tool
cue_file
, using the same settings your station uses. The docs have a reference table for easy lookup. - Disable processing all files at startup.
- In Profile → Edit Profile → AutoDJ → Advanced Configuration, disable the setting Always Write Playlists to Liquidsoap.
- Do not use
enable_autocue_metadata()
, but theautocue:
protocol instead. - This needs to be done for requests, single, and playlists, usually before any annotations. Example:
shows = playlist(prefix='autocue:annotate:liq_blankskip=0.0:', 'show-playlist.m3u')
- Never use both
enable_autocue_metadata
and theautocue:
protocol together! This would lead to unneccessary processing of each file twice!
How to assure jingles are not cut off? ⇧
Set the jingle’s fade-in and fade-out times to a short value, like 0.1
seconds. This will override the default settings and ensure the jingle is not faded out early. It is advisable to also set the blank skipping feature off by using a value of 0.0
seconds.
- Use the Visual Cue Editor or the Advanced tab next to it to set both fade-in and fade-out to
0.1
seconds. - Play jingles from a playlist that has Hide Metadata from Listeners ("Jingle Mode") switched on.
- Use an
annotate:
prefix on a jingles playlist to setliq_fade_in
,liq_fade_out
, andliq_blankskip
:jingles = playlist(prefix='annotate:liq_fade_in=0.1,liq_fade_out=0.1,liq_blankskip=0.0:', 'playlist.m3u')
- Set the appropriate tags:
Tag Value liq_blankskip 0.00 liq_fade_in 0.10 liq_fade_out 0.10
How to ensure pre-recorded shows or podcasts aren’t cut off early? ⇧
Pre-recorded shows and podcasts often have pauses, which could trigger the blankskip
logic and thus end playout at such a pause. If you have global blank skipping on (settings.autocue.cue_file.blankskip
> 0.00
), this could hit you.
- The solution here is to switch off blank skipping for such a track or playlist, usually done in pre-processing.
- Simply do not use the
-b
/--blankskip
parameter withcue_file
. This will setliq_blankskip=0.00
.
- Use an
annotate:
prefix on a show or podcast playlist to setliq_blankskip
to zero (=disabled):shows = playlist(prefix='annotate:liq_blankskip=0.0:', 'show-playlist.m3u')
- Set the appropriate tags:
Tag Value liq_blankskip 0.00
How to pre-process more than one file at a time ("mass tagging")? ⇧
cue_file
is a tool that processes only one track at a time.
- You can write your own "wrapper" around it.
- You can use/modify the shell script @LordHelmchen666 kindly provided. Note this is for running on the station, and handles MP3 and WMA files only. It’s very easy to adapt, though.
- Bear in mind you should have separate sub-folders for tracks that require different pre-processing parameters! Example:
- Songs (normal handling, incl.
blankskip
if you like) - Jingles, Ads (switch blankskip off, set fades)
- Pre-recorded shows, DJ sets (switch blankskip off)
- Podcasts (switch blankskip off)
- Recordings (switch blankskip off)
- Songs (normal handling, incl.
What tagging software to use? ⇧
That very much depends, but most of them have some drawbacks, can’t handle all file types, or simply corrupt files because they do something wrong. Sad experience from 25+ years of tagging music files.
Most of these are available for Linux, MacOS and Windows.
- MusicBrainz Picard — Ideal for initial tagging of files, and you help the community when getting a free MusicBrainz account and help adding new albums. Uses Mutagen.
- Kid3 — Originally part of the KDE desktop, but can be installed on others. Very good for "the quick fix", like changing
liq_blankskip
. - cue_file. For pre-processing and adding Autocue/ReplayGain (track) data. Uses Mutagen.
- mid3v2 — Part of Mutagen, nice to quickly change a tag or two in a shell script. Only for MP3, though.
- MP3 Diags — To repair some hard-to-catch problems with MP3 files. Not for general tagging.
- Honorable mention: foobar2000 — Windows only. Versatile player/tag editor that also does things right.
As always, you should know what you’re doing, and set up these tools appropriately.
- Get rid of ID3v1 tags. They are obsolete nowadays and only good for real vintage MP3 players. Saving both ID3v1 and ID3v2 tags can lead to all kinds of obscure and unwanted problems.
- With MP3 files (and very few others), use ID3v2.4 type tags. They are modern and handle UTF-8 encoding well.
- If you cannot use ID3v2.4 (because you have some old players that can’t handle that tag format), use ID3v2.3.0 and UTF-16 encoding (this tag format doesn’t yet know about UTF-8).
Can I use cue_file
to replaygain my files? ⇧
- Yes, you absolutely can, if you can live without the ReplayGain album data (
cue_file
has no concept of an album).cue_file
basically follows the same logicloudgain
uses, but doesn’t have all its features. - Just add the
-r
/--replaygain
parameter in addition to-w
/--write
when usingcue_file
for pre-processing and it will write these ReplayGain2 tags:Tag Unit replaygain_reference_loudness LUFS replaygain_track_gain dB replaygain_track_peak true peak, linear replaygain_track_range dB
Can I use cue_file
to manually add/overwrite tags when pre-processing? ⇧
- Yes, you can, even after forcing a re-analysis (v4.0.4+).
- Only tags from
cue_file
’s list of known tags (seecue_file --help
) will ever been written bycue_file
. So no overriding artist or title here—that’s what should have been done in an earlier step, using a good tagging software. - Use with care! Some values are dependent on others, you could easily mess up something.
- You must create well-formed JSON and can then use
cue_file
with the-j
/--json
switch to let your tags override or add to what’s already there.
echo '{"liq_fade_in": 0.1, "liq_fade_out": 0.1}' | cue_file -j - -fwr "filename.ext"
-j -
— sets JSON input tostdin
-fwr
— force re-analysis, write tags, write replaygain
{
"liq_fade_in": 0.10,
"liq_fade_out": 0.10
}
cue_file -j fades.json -fwr "filename.ext"
-j fades.json
— read JSON data from filefades.json
-fwr
— force re-analysis, write tags, write replaygain
How to make transitions tighter, i.e. overlay earlier? ⇧
- First, try to decrease
-d
/--drop
/settings.autocue.cue_file.sustained_loudness_drop
gradually. The default is40.0
%, so maybe go down in 10% increments and see how you like it. - Second, if the above isn’t sufficient, try decreasing
-x
/--extra
/settings.autocue.cue_file.overlay_longtail
gradually. The (new) default is-12.0
LU, you could try decreasing in 2 LU increments. Note: This affects both "sustaned endings" and "longtail" handling. - Don’t forget the
-f
/--force
switch incue_file
, so you get real, freshly analyzed results!
I recommend testing this on a few selected test songs, before you modify your station settings or re-tag all your files! A good tool is for instance Audacity, you can switch the selection input to seconds start & end, and just enter the values cue_file got you on the test file.
How to make transitions longer, i.e. overlay later and keep every bit of a song ending? ⇧
- First, try to increase
-d
/--drop
/settings.autocue.cue_file.sustained_loudness_drop
gradually. The default is40.0
%, so maybe go up in 10% increments and see how you like it. A good value is60.0
%. - Second, if the above isn’t sufficient, try increasing
-x
/--extra
/settings.autocue.cue_file.overlay_longtail
gradually. The (new) default is-12.0
LU, you could try increasing in 2 LU increments. A good value is-15.0
LU. Note: This affects both "sustaned endings" and "longtail" handling. - Don’t forget the
-f
/--force
switch incue_file
, so you get real, freshly analyzed results!
I recommend testing this on a few selected test songs, before you modify your station settings or re-tag all your files! A good tool is for instance Audacity, you can switch the selection input to seconds start & end, and just enter the values cue_file got you on the test file.
Can I completely disable the "sustained endings" feature? ⇧
I can’t see a reason for it, but yes, you can.
- Just set
-d
/--drop
/settings.autocue.cue_file.sustained_loudness_drop
to zero (0.0
%), which will disable this feature.
Can I completely disable the "longtail" feature? ⇧
Again, I don’t see a reason for it, but you can.
- Just set
-x
/--extra
/settings.autocue.cue_file.overlay_longtail
to zero (0.0
LU), which will disable this feature. Note: This affects both "sustaned endings" and "longtail" handling.
How to ensure Autocue doesn’t mess with Ad Insertion files? ⇧
Ad insertion files are special files that usually shouldn’t be tampered with. You can set or annotate the special tag liq_cue_file
and set it to false
, which will keep Autocue from doing anything with this track.
Should an ad insertion file need replaygaining, remember to also set liq_amplify
to the same value your replaygain_track_gain
shows.
- Use an
annotate:
prefix on a playlist to setliq_cue_file
tofalse
(=disable Autocue):ad_inserts = playlist(prefix='annotate:liq_cue_file=false:', 'ad-inserts.m3u')
- Set the appropriate tags:
Tag Value liq_cue_file false
How to ensure Autocue doesn’t try to process video files? ⇧
Some stations have video streams. Now cue_file
can process even multi-GB video files, but it’ll use CPU and take long. Resources wasted if you overlay the video’s audio with your radio stream anyway!
You can set or annotate the special tag liq_cue_file
and set it to false
, which will keep Autocue from doing anything with video files.
- Use an
annotate:
prefix on a playlist to setliq_cue_file
tofalse
(=disable Autocue):videos = playlist(prefix='annotate:liq_cue_file=false:', 'videos.m3u')
-
Set the appropriate tags:
Tag Value liq_cue_file false -
This will probably only work for
.mp4
type videos right now. Mutagen doesn’t yet support the Matroska (.mkv
) and WebM (.webm
) EBML data structure.
Why should I use check_autocue_setup
, and what does it do? ⇧
It’s a little check to ensure things for autocue.cue_file
have been set up correctly, and a good diagnostic, since it logs the versions of your autocue.cue_file.liq
and external cue_file
to the log (and console if you set print=true
). It is important that the Liquidsoap script and the external cue_file
are the same version, and autocue.cue_file
integrated properly, otherwise odd things could happen, or Liquidsoap could fall back to its internal autocue, and you wouldn’t get the results you expect.
So always use it, after your settings and before a possible enable_autocue_metadata()
. (AzuraCast does this automatically for you, so nothing to add in any input box.)
check_autocue_setup
will…
- check if your
autocue.cue_file.liq
and externalcue_file
versions match and log the result for easier debugging:2024/06/21 06:46:51 [autocue.cue_file:2] You are using autocue.cue_file version 4.0.3. 2024/06/21 06:46:51 [autocue.cue_file:2] The external "cue_file" is version 4.0.3
- set its metadata priority:
settings.autocue.metadata.priority := 10
- set the preferred autocue implementation:
settings.autocue.preferred := "cue_file"
- set the correct "amplify behaviour":
settings.autocue.amplify_behavior := "keep"
- set the default cross duration to your specified fade-out duration:
settings.autocue.target_cross_duration := settings.autocue.cue_file.fade_out()
. This is done to avoid problems when your default fade-out is different from Liquidsoap’s default cross duration of3.0
seconds. The result is logged:2024/06/21 06:46:51 [autocue.cue_file:2] Setting `settings.autocue.target_cross_duration` to 2.5 s, from `settings.autocue.cue_file.fade_out`.
- If you set
print=true
, the results will also be shown on the console. This is practical when programming, so you don’t have to find the log and look it up. - If you set
shutdown=true
, your Liquidsoap script will shut down if an error occurs. Most of the time, you should set this, because the results are unspecified or you can get a lot of errors if the versions ofautocue.cue_file.liq
andcue_file
don’t match. - The log/console output in case of an error looks like this:
ERROR: autocue.cue_file v4.0.3 doesn’t match external "cue_file" v4.0.2! Autocue NOT ACTIVATED! Shutting down...
check_autocue_setup
can be used in two ways:
- Automatic: Handles everything for you, including Liquidsoap shutdown:
ignore(check_autocue_setup(shutdown=true, print=true))
- Manual: You want to do some special processing, depending on its result:
if check_autocue_setup(shutdown=false, print=false) then # all okay, your code here else # error ocurred, your code here end
What are good first steps to use Autocue in my own Liquidsoap script? ⇧
- Install Liquidsoap and Autocue, obviously.
- Start simple, use the defaults. It should work first, then you can fine-tune it.
- A good example is in minimal_example_autocue.cue_file.liq. It shows the basic structure:
%include "autocue.cue_file.liq"
- Do your settings. You can copy all settings from the README, and only un-comment those you need. The advantage is: You have them all together and don’t have to look them up every time.
ignore(check_autocue_setup(shutdown=true, print=true))
enable_autocue_metadata()
if you want to use it.- Rest of your script.
If you plan to use custom crossfading,
- remember that some functions, like
fade_in
andfade_out
need metadata passed to them. - instead of hard-coding values into the crossfading function, use the
autocue.cue_file
settings. Doing so will later allow easy changing in just one place and avoid obscure side-effects if you forgot to change something.
Plan for diagnostics logging. The Liquidsoap integration layer might change things you can’t see in the autocue.cue_file
log output. It can be useful to write a show_meta
function that gets called on_metadata
.
Good examples for all this are in test_autocue.cue_file.liq
. Study the def live_aware_crossfade(old, new)
and def show_meta(m)
function definitions and their usage.
Have fun!
What will happen when I switch to the upcoming Liquidsoap 2.3.0? ⇧
Nothing is definite yet, Liquidsoap 2.3.0 is still under heavy development.
Most certainly, as of 2024-06-23…
-
you will need a new version of both
autocue.cue_file
andcue_file
, because Liquidsoap will change the tags and API. -
you’ll need to pre-process your files again, if you have used that feature.
-
I will see that
cue_file
will be able to remove obsolete tags. -
if possible, I’ll do some checking so that you don’t run
autocue.cue_file
(and thuscue_file
) under an incompatible Liquidsoap version. Thecheck_autocue_setup()
function will take care of that. -
liq_fade_in
might change toliq_fade_in_duration
. -
liq_fade_out
might change toliq_fade_out_duration
. -
liq_cross_duration
will be split intoliq_cross_start_duration
andliq_cross_end_duration
,
which makes some internal handling much more straightforward.
See also:
What can I do if some files or a remote playlist simply don’t play? ⇧
This most often happens with large files, large remote files, and files that are hard to analyse because they’re already clipping (too loud).
Check your Liquidsoap log for entries like
2024/06/26 10:01:43 [request:2] Time limit exceeded by 16.00 secs!
This can happen if the downloading/preparing is slow, or the files are large (recordings, prerecorded shows, DJ sets, podcasts) or hard to analyse. These factors are out of our control. If a request timeout happens, the file will simply not be played, and the next available used.
Playing from a remote playlist presents another hurdle: Liquidsoap will then download a temporary copy of the file(s) in the playlist, autocue that copy, and when it has played, will delete it again. So next time round, the same file will have to be analyzed again.
In such cases, I suggest to pre-tag files using the cue_file
tool, but this might not always be possible.
In the above case, I’d suggest increasing the Autocue timeout slightly from the default 60.0
seconds to 60
+ timeout shown (16.0
) + a small "safety margin", say another 10
seconds, making for 86
seconds. Let’s round that up to 90
seconds.
In AzuraCast’s Edit Liquidsoap Configuration, in the second input box, add this parameter:
settings.autocue.cue_file.timeout := 90.0
Note: Please do not use arbitrary large values like 480.0
"just to prevent it happening"! Doing so could well have adverse side effects.
Save Changes and Restart Broadcasting.
Keep watching your logs for timeouts, just in case even larger files arrive. You can search for Time limit exceeded
to quickly find such entries in the log.
If the above should not help, you should look for a faster/higher bandwidth connection to the source you download the files from. To be able to work with a file, Liquidsoap has to download a complete copy first, before autocueing and playout can begin.
What exactly is liq_cue_file
for, and should I use it? ⇧
Starting with v4.1.0, we have a new liq_cue_file
handling, which allows to ignore overrides for cue_file
data if true. This is mainly for fast-changing files like news or time, for which LS/AzuraCast might not yet have updated the metadata.
- not set — default behaviour (metadata can override
cue_file
results) false
— don’t autocue (still use metadata if present)true
—cue_file
results override metadata (special use cases)
AzuraCast and other third-party apps can store (cache) cue_file
metadata in order to speed up processing. They can also decide to override certain cue_file
results like cue, fading and ramp points, as is done in AzuraCast’s Visucal Cue Editor (VCE) and Advanced track edit tab.
For normal operation, just make sure the tag liq_cue_file
is not set, and you don’t annotate it. Your radio automation will then be able to use whatever Autocue has calculated, and—if needed—be able to override results, for instance in AzuraCast’s VCE/Advanced tab.
Now if you aggregate syndicated news, spoken time announcements or the like outside the app, and use the same filename, the app might not immediately know about the change and update its stored metadata, resulting in wrong metadata on playout, even when you carefully pre-tagged the file with cue_file
in your external process. For instance, AzuraCast’s media checker runs only about every five minutes or so. If you download a syndicated news file at 9:59 and prepare it at 9:59:45, to be played at 10:00 sharp, chances are good the media checker hasn’t yet hit in and updated the metadata. Result: Problems.
If you now pre-tag such a file in your external process, using the liq_cue_file
tag and set it to true
, the Autocue in Liquidsoap will know you want to use the tagged cue_file
results and ignore the values it might have gotten from elsewhere (stored, annotated, etc.).
A corresponding log entry will be made by Autocue in this case:
[autocue.cue_file:3] cue_file results override existing metadata because liq_cue_file=true tells us to.
Autocue is a CPU-intensive process. So if your station plays large video files, for instance, you will want to exclude these from being autocued. Do this by tagging or annotating the file or playlist using liq_cue_file
and set it to false
. Even if Autocue is enabled by default, it will then know to skip these files and write a log entry to that effect:
[autocue.cue_file:2] Skipping cue_file for "filename" because liq_cue_file=false forbids it.