【Swift】RSSの投稿日付・時間をパースする方法

SwiftにはXMLParserと言う便利なパーサが用意されている。

これを使うとXMLをパースしてくれるので、RSSフィードをパースして簡単なニュースリーダー(iPhoneアプリ)が作れる。

試しにXcodeを使ってiPhoneアプリを開発しているのだが1つ困った問題が生じた。

日付のフォーマットが異なるのだ。

この問題を解決するためのコードを書いたのでご紹介したい。

[toc]

RSSのバージョンによる違い

RSSの時間フォーマットが複数ある。

以下の記事はPHPの話だが、詳しく述べられている。

[RSS 2.0]のときは「pubDate」が。[RSS 1.0]のときは「dc:date」が使われています。

【PHP】RSSの日時データ「pubDate」と「dc:date」を取得・表示するときの注意点。

なぜ2つの形式があるのだろうか。

開発者としては1つに統一して欲しいと思うのだが、、、。

確かに複数のサイトのXMLファイルやRDFファイル(RSS用のファイル)を見てみるとサイトによって日付・時間の形式がバラバラである。

ニュース記事を取得するサイトが1つであれば、そのサイトのXMLを見てフォーマットを合わせれば良い。

しかし複数のサイトから記事を集める場合には、RSS2.0、RSS1.0両方に対応するのがベストだろう。

  • RSS2.0の場合

pubDateの中に以下のフォーマットで格納されている。

Tue, 16 Aug 2016 15:27:33 +0000
  • RSS1.0の場合

dc:dateの中に以下のフォーマットで格納されている。

2020-05-15T15:00:00+09:00

RSS2.0,1.0に対応したコード

RSS2.0、RSS1.0のフォーマットを読み取るために以下の関数を作成した。

var date: Date = Date()
 
func convert_pubdate_date(currentString: String) {
    let dateFormatter = DateFormatter()
    dateFormatter.locale = NSLocale(localeIdentifier: "en_US_POSIX") as Locale
    dateFormatter.dateFormat = "E, d MMM yyyy HH:mm:ss Z"
    if let date = dateFormatter.date(from: currentString) {
    self.date = date
    }
}

func convert_dcdate_date(currentString: String){
    let dateFormatter = DateFormatter()
    dateFormatter.locale = NSLocale(localeIdentifier: "en_US_POSIX") as Locale
    dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
    if let date = dateFormatter.date(from: currentString){
        self.date = date
    }
}

パースしている中でそれぞれのタグが見つかったら作った関数を実行してあげれば良い。

func parser(_ parser: XMLParser, didEndElement elementName: String, namespaceURI: String?, qualifiedName qName: String?) {
    switch elementName {
    case "pubDate":
        self.item?.convert_pubdate_date(currentString: currentstring)
    case "dc:date":
        self.item?.convert_dcdate_date(currentString: currentstring)
    default:
        break
    }
}

RSSと言うのは面倒な仕様ですね。

ABOUTこの記事をかいた人

個人アプリ開発者。Python、Swift、Unityのことを発信します。月間2.5万PVブログ運営。 Twitter:@yamagablog