Skip to content

Commit

Permalink
Update itunes module to iOS 11 podcasts spec
Browse files Browse the repository at this point in the history
Apple released new guidlines for the itunes RSS spec for podcasts: http://podcasts.apple.com/resources/spec/ApplePodcastsSpecUpdatesiOS11.pdf

The specific technical changes are the addition of the following attributes:

Channel level: The following was added:

itunes:type :: type of podcast 'episodic' (default)  or 'serial'.

Item level: The following was added:

itunes:season :: a non-zero integer number for a season identifier
itunes:episode :: a non-zero integer episode number within the season
itunes:episodeType :: one of 'full' (default) 'bonus' or 'trailer'

All new values are optional.
  • Loading branch information
razyalov authored and mishako committed Sep 11, 2017
1 parent 6b4dd5b commit 4a427c7
Show file tree
Hide file tree
Showing 9 changed files with 160 additions and 5 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -45,4 +45,26 @@ public interface EntryInformation extends ITunes {
public Integer getOrder();

public void setOrder(Integer order);

/**
* Get the episode type
* @see #setEpisodeType(String) setEpisodeType(episodeType) for details
*/
public String getEpisodeType();

/**
* Set the episode type to one of full (default), trailer or bonus. See the <a href="http://podcasts.apple.com/resources/spec/ApplePodcastsSpecUpdatesiOS11.pdf">new spec by Apple</a> for details.
* @param episodeType
*/
public void setEpisodeType(String episodeType);

public Integer getSeason();

public void setSeason(Integer season);

public Integer getEpisode();

public void setEpisode(Integer episode);


}
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,9 @@ public class EntryInformationImpl extends AbstractITunesObject implements EntryI
private Duration duration;
private boolean closedCaptioned;
private Integer order;
private String episodeType;
private Integer season;
private Integer episode;

public EntryInformationImpl() {
}
Expand Down Expand Up @@ -81,6 +84,34 @@ public void setOrder(Integer order) {
this.order = order;
}

/**
* Get the episode type
*
* @see #setEpisodeType(String) setEpisodeType(episodeType) for details
*/
@Override
public String getEpisodeType() { return episodeType; }

/**
* Set the episode type to one of full (default), trailer or bonus. See see the <a href="http://podcasts.apple.com/resources/spec/ApplePodcastsSpecUpdatesiOS11.pdf">new spec by Apple</a> for details.
*
* @param episodeType
*/
@Override
public void setEpisodeType(String episodeType) { this.episodeType = episodeType; }

@Override
public Integer getSeason() { return season; }

@Override
public void setSeason(Integer season) { this.season = season; }

@Override
public Integer getEpisode() { return episode; }

@Override
public void setEpisode(Integer episode) { this.episode = episode; }

/**
* Defined by the ROME module API
*
Expand Down Expand Up @@ -114,6 +145,9 @@ public void copyFrom(final CopyFrom obj) {
setSummary(info.getSummary());
setClosedCaptioned(info.getClosedCaptioned());
setOrder(info.getOrder());
setEpisodeType(info.getEpisodeType());
setSeason(info.getSeason());
setEpisode(info.getEpisode());
}

/**
Expand All @@ -138,6 +172,12 @@ public String toString() {
sb.append(getClosedCaptioned());
sb.append(" order: ");
sb.append(getOrder());
sb.append(" season: ");
sb.append(getSeason());
sb.append(" episode: ");
sb.append(getEpisode());
sb.append(" episodeType: ");
sb.append(getEpisodeType());
sb.append("]");
sb.append(super.toString());

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -75,4 +75,19 @@ public interface FeedInformation extends ITunes {
* @return Returns the owner name for the feed
*/
public String getOwnerName();

/**
* Set the type of podcast to either Episodic (original type of podcasts) or Serial (should be consumed from oldest to newest)
* @see #getType() getType() for more details
* @param type the type (Either 'serial' or 'episodic')
*/
public void setType(String type);

/**
* Return the type of podcast (either Episodic or Serial) as introduced in the new Apple Podcast spec for iOS 11.
* For more information see the <a href="http://podcasts.apple.com/resources/spec/ApplePodcastsSpecUpdatesiOS11.pdf">new spec by Apple</a>
* @return either 'episodic' (old school podcasts) or 'serial' (should be listened to from oldest to newest)
*/
public String getType();

}
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ public class FeedInformationImpl extends AbstractITunesObject implements FeedInf
private List<Category> categories;
private boolean complete;
private String newFeedUrl;
private String type;

public FeedInformationImpl() {
}
Expand Down Expand Up @@ -125,6 +126,22 @@ public void setOwnerEmailAddress(final String ownerEmailAddress) {
this.ownerEmailAddress = ownerEmailAddress;
}

/**
* Set the type of podcast to either Episodic (original type of podcasts) or Serial (should be consumed from oldest to newest)
* @see #getType() getType() for more details
* @param type the type (Either 'serial' or 'episodic')
*/
@Override
public void setType(final String type) { this.type = type; }

/**
* Return the type of podcast (either Episodic or Serial) as introduced in the new Apple Podcast spec for iOS 11.
* For more information see the <a href="http://podcasts.apple.com/resources/spec/ApplePodcastsSpecUpdatesiOS11.pdf">new spec by Apple</a>
* @return either 'episodic' (old school podcasts) or 'serial' (should be listened to from oldest to newest)
*/
@Override
public String getType() { return type; }

/**
* Required by the ROME API
*
Expand Down Expand Up @@ -161,6 +178,7 @@ public void copyFrom(final CopyFrom obj) {
setOwnerName(info.getOwnerName());
setSubtitle(info.getSubtitle());
setSummary(info.getSummary());
setType(info.getType());
}

/**
Expand Down Expand Up @@ -189,6 +207,8 @@ public String toString() {
sb.append(getComplete());
sb.append(" newFeedUrl: ");
sb.append(getNewFeedUrl());
sb.append(" type: ");
sb.append(getType());
sb.append("]");
sb.append(super.toString());

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,10 @@ public void generate(final Module module, final Element element) {
element.addContent(category);
}

if (info.getType() != null) {
element.addContent(generateSimpleElement("type",info.getType()));
}

if (info.getComplete()) {
element.addContent(generateSimpleElement("complete", "yes"));
}
Expand All @@ -104,6 +108,15 @@ public void generate(final Module module, final Element element) {
if (info.getOrder() != null) {
element.addContent(generateSimpleElement("order", info.getOrder().toString()));
}
if (info.getEpisodeType() != null) {
element.addContent(generateSimpleElement("episodeType", info.getEpisodeType()));
}
if (info.getSeason() != null && info.getSeason() > 0) {
element.addContent(generateSimpleElement("season", info.getSeason().toString()));
}
if (info.getEpisode() != null && info.getEpisode() > 0) {
element.addContent(generateSimpleElement("episode", info.getEpisode().toString()));
}
}

if (itunes.getAuthor() != null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,11 @@ public com.rometools.rome.feed.module.Module parse(final Element element, final
feedInfo.setNewFeedUrl(newFeedUrl.getTextTrim());
}

final Element type = element.getChild("type", ns);
if (type != null) {
feedInfo.setType(type.getTextTrim());
}

} else if (element.getName().equals("item")) {
final EntryInformationImpl entryInfo = new EntryInformationImpl();
module = entryInfo;
Expand Down Expand Up @@ -138,6 +143,26 @@ public com.rometools.rome.feed.module.Module parse(final Element element, final
final Integer o = Integer.valueOf(order.getValue().trim());
entryInfo.setOrder(o);
}

final Element season = element.getChild("season", ns);

if (season != null && season.getValue() != null) {
final Integer o = Integer.valueOf(season.getValue().trim());
entryInfo.setSeason(o);
}

final Element episode = element.getChild("episode", ns);

if (episode != null && episode.getValue() != null) {
final Integer o = Integer.valueOf(episode.getValue().trim());
entryInfo.setEpisode(o);
}

final Element episodeType = element.getChild("episodeType", ns);

if (episodeType != null && episodeType.getValue() != null) {
entryInfo.setEpisodeType(episodeType.getTextTrim());
}
}
if (module != null) {
// All these are common to both Channel and Item
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,7 @@ public void testCreate() throws Exception {
fi.setOwnerName("sales.com");
fi.getCategories().add(new Category("Shopping"));
fi.setOwnerEmailAddress("patti@sales.com");
fi.setType("serial");
feed.getModules().add(fi);

final SyndFeedOutput output = new SyndFeedOutput();
Expand Down
16 changes: 13 additions & 3 deletions rome-modules/src/test/resources/itunes/leshow.xml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
<description>A weekly, hour-long romp through the worlds of media, politics, sports and show business, leavened with an eclectic mix of mysterious music, hosted by Harry Shearer.</description>
<itunes:subtitle>An hour&#39;s worth of Harry Shearer</itunes:subtitle>
<itunes:summary>A weekly, hour-long romp through the worlds of media, politics, sports and show business, leavened with an eclectic mix of mysterious music, hosted by Harry Shearer.</itunes:summary>
<itunes:type>serial</itunes:type>
<language>en</language>

<copyright>KCRW 2005</copyright>
Expand Down Expand Up @@ -65,7 +66,10 @@

<itunes:duration>46:34</itunes:duration>

<itunes:keywords></itunes:keywords>
<itunes:keywords></itunes:keywords>
<itunes:season>1</itunes:season>
<itunes:episode>1</itunes:episode>
<itunes:episodeType>full</itunes:episodeType>
</item>


Expand Down Expand Up @@ -103,7 +107,10 @@

<itunes:duration>44:00</itunes:duration>

<itunes:keywords></itunes:keywords>
<itunes:keywords></itunes:keywords>
<itunes:season>1</itunes:season>
<itunes:episode>2</itunes:episode>
<itunes:episodeType>trailer</itunes:episodeType>
</item>


Expand Down Expand Up @@ -141,7 +148,10 @@

<itunes:duration>48:33</itunes:duration>

<itunes:keywords></itunes:keywords>
<itunes:keywords></itunes:keywords>
<itunes:season>1</itunes:season>
<itunes:episode>2</itunes:episode>
<itunes:episodeType>bonus</itunes:episodeType>
</item>


Expand Down
13 changes: 11 additions & 2 deletions rome-modules/src/test/resources/xml/leshow.xml
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
<itunes:summary>A weekly, hour-long romp through the worlds of media, politics, sports and show business, leavened with an eclectic mix of mysterious music, hosted by Harry Shearer.</itunes:summary>
<itunes:complete>yes</itunes:complete>
<itunes:new-feed-url>http://example.org</itunes:new-feed-url>
<itunes:type>serial</itunes:type>
<language>en</language>

<copyright>KCRW 2005</copyright>
Expand Down Expand Up @@ -71,10 +72,12 @@
<itunes:isClosedCaptioned>yes</itunes:isClosedCaptioned>
<itunes:order>2</itunes:order>
<itunes:image href="http://example.org/image.png"></itunes:image>
<itunes:season>1</itunes:season>
<itunes:episode>1</itunes:episode>
<itunes:episodeType>full</itunes:episodeType>
</item>


<item>
<item>
<title>le Show</title>
<itunes:author>Harry Shearer</itunes:author>
<description>
Expand Down Expand Up @@ -109,6 +112,9 @@
<itunes:duration>44:00</itunes:duration>

<itunes:keywords></itunes:keywords>
<itunes:season>1</itunes:season>
<itunes:episode>2</itunes:episode>
<itunes:episodeType>trailer</itunes:episodeType>
</item>


Expand Down Expand Up @@ -147,6 +153,9 @@
<itunes:duration>48:33</itunes:duration>

<itunes:keywords></itunes:keywords>
<itunes:season>1</itunes:season>
<itunes:episode>2</itunes:episode>
<itunes:episodeType>bonus</itunes:episodeType>
</item>


Expand Down

0 comments on commit 4a427c7

Please sign in to comment.