How to create enhanced audio podcast episodes featuring images and chapters (How the itunes:image tag really works)

Since I released the latest version of Podcast Generator (which includes the support for embedded images for individual¬†podcast episodes), ¬†one of the most recurring questions has been why iTunes and the iOS Podcast app don’t show the artwork associated to single audio episodes yet keep displaying the main podcast artwork/cover art.

Apple’s technical specifications for podcasts¬†state that the¬†iTunes-specific tag¬†<itunes:image> allows to associate a cover art to the podcast feed but also¬†at the episode¬†level.¬†However, this information is currently not fully implemented by Apple since¬†it works only for the general podcast cover art, but not for single episodes, i.e. if an image is specified using the tag¬†<itunes:image> for a single episode (<item>), this is simply ignored by iTunes and the iOS podcast app, which keep displaying the general cover art.

To the best of my knowledge, the only way to show artwork (one or more images) associated to a single podcast episode is to use¬†GarageBand¬†for Mac¬†and create an “enhanced podcast”.

To do so, simply import your audio files using GarageBand (optionally, you can edit them by adding jingles or sound FX etc.) and directly drag an image on top of the audio track. This will result in the creation of a Podcast chapter that can be moved along the timeline to be shown at a specific point during the reproduction of the audio file. This operation can be repeated to create more chapters for the same episode, each of which will consists of its own image and title:Creation of enhanced audio podcast with chapters using Garage Band


Once the enhanced audio podcast is ready, it is possible to export it by selecting Share -> Export Podcast to Disk:

Export audio podcast with chapters and images to disk


The enhanced episode must be compressed using the AAC Encoder (which will produce an .m4a audio file).¬†Be sure also to select the option “Set artwork to recommended size for podcasts when exporting”:Export podcast file from GarageBand including artwork and chapters


et voilà! You will obtain an enhanced audio podcast episode!

This is the result in the Podcast app for iOS (iPhone):

Enhanced audio episode in iOS podcast app


You can download our example enhanced audio podcast episode (embedding 3 different images and chapters)and try it yourself. To do so, feel free to use the demo of Podcast Generator: there you can upload test files and play without limitations. Once you have uploaded your test file, subscribe to the demo feed using the podcast app for iOS and see the result :)

Do you need help to publish your podcast? Check out¬†my web-application called Podcast Generator. It’s free, open source and very intuitive to use. Many hosting and NAS services worldwide offer Podcast Generator¬†as a preinstalled package in their control panel so no effort is required for the installation.

Happy Podcasting!

This post also appeared on LinkedIN.

Real-time plots using websockets, python, javascript and Google Charts

There are many examples of use of websockets out there, however most of them are cumbersome or too complex for newbies.

Here is an extremely simple example of websockets I made, which consists of a server (implemented both in PERL and Python, up to you the choice) that pushes a message (i.e. randomly generated values) to the client upon a fixed time interval:

Two clients are available in this example:

  • client-JustLog.html displays on screen the log with the messages received;
  • client-Chart.html shows a bar chart (based on Google Charts) which updates in real time with the data received.


If you are running this code in a local host (i.e. your local machine) no configuration is needed. Otherwise, you can change ports and host from the config sections in the code.


  1. SERVER: choose either (PERL) or (Python) and run ONE of them from the terminal: type eitherperl or python
  2. CLIENT: Open one of the two clients (but they also work at the same time in two separate tabs) using a modern browser (e.g. tested and working with Chrome v.42+). Notice that the client must be opened after the server is running (otherwise, you will have to push the “reconnect” button).
  3. See the data pushed automatically from the server to the client via websockets :bowtie: (Optionally, you might want to use Firebug with client-Chart.html to see the console logs)


  • PERL or Python
  • A modern browser that supports websockets (e.g. Chrome v.42+)


  • The PERL implementation of the server requires Net::WebSocket::Server. In Mac OSX it can be installed using the command: sudo perl -MCPAN -e 'install Net::WebSocket::Server'
  • The Python implementation of the server requires Tornado that can be installed using pip (pip install tornado) or manually:
tar xvzf tornado-4.1.tar.gz
cd tornado-4.1
python build
sudo python install

Mailing List with Mailman and Phishing warning in Gmail

Gmail phishing alertGmail recently added a new anti-phishing feature that seems to not like too much mailing lists managed with Mailman (hosting providers often integrate this software in their control panel).

Several e-mails sent through those mailing lists are now “flagged” with the following warning:

This message may not have been sent by: Learn More Report Phishing

I currently have a couple of mailing list hosted by my personal server: due to the popularity of Gmail, this systematically displayed message is quite annoying, and tends to “alarm” some users of the mailing list.

If you are hosting a mailing list in your server, and you experience the same issue, here is a simple solution…

As Google recommends in the Gmail support section, you can create an SPF (Sender Policy Framework) record to your domain, so your mailing list will be authenticated.

To create an SPF record for your domain, access the Control Panel (e.g. CPanel) provided by your Hosting Company:

  1. Go to the section where you can edit the DNS (e.g. In Cpanel, “DNS -> Advanced DNS zone editor”)
  2. Add a new TXT record where the record name will be (NB. Do not add any www prefix, just the domain name and don’t forget the . after your domain name, it’s important!)
  3. In the TXT Data field, write: v=spf1 ip4:123.456.789.000 ~all (don’t forget to replace the IP in this example with your real IP)
  4. Leave the default value in the field TTL

(Needless to say/repeat, replace with your domain name, and 123.456.789.000 with the IP of your server).

That’s it. There are different possible values you can add to your SPF record, they may be more or less “permissive” (e.g. emails sent just from some subdomains etc…). However the aforementioned example should work for everyone, if you need something more specific then start from here and follow the links.

It may take a while to have these changes to your DNS propagated worldwide (up to 48 hours), then, once the SPF record in your domain is active, the email sent through your mailing list(s) won’t display any more the phishing warning in Gmail. That’s it :)

How to check whether your SPF record works correctly?

  • Write your domain name in the field “Domain name:” (do not put any www., use just the domain name and the extension e.g. and press “Get SPF record (if any)“.
  • If the result is positive you’ll have a response which will look like “The TXT records found for your domain are:” etc… (the page will also display a validation of the record). Otherwise, you’ll obtain this error “No type SPF records found.” (This may mean that there is something wrong in your SPF record, or that your DNS are not propagated yet).

There is also a way to check whether your SPF record is active and works properly. You can enter Gmail and give a look to the headers of the emails sent through your mailing list.

The headers of the e-mails sent to a mailing list whose domain doesn’t have an SPF record, report a section similar to this one:

Received-SPF: neutral ( is neither permitted nor denied by best guess record for domain of;

While an active SPF record in your domain would produce the following header:

Authentication-Results:; spf=pass ( domain of designates as permitted sender); dkim=neutral (body hash did not verify)

Thus avoiding the annoying Phishing warning in the Gmail webmail interface.