4
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

【JS】RSSで取得した記事を日付順にし、表示形式を変更する(Javascript・node.js)

Last updated at Posted at 2020-03-29

##解決する問題
RSSで取得した記事を、日付順にして日付の表示形式を変更する。

今回はRSSでコロナウイルスに関しての記事を取得しました。

##対象読者
・node.jsでxmlを取得する事ができる方。
・express-generatorを触った事がある方。
・xmlの表示形式の知識がある方。

express-generatorを使ってXMLを取得しているところから進めていきます。

##環境
OS: macOS
Node.js: v13.5.0
npm: 6.14.3
express: ~4.16.1
ejs: ~2.6.1,

##RSSで記事を取得した時の状況
記事を取得し表示させると日付順にならず、見づらい

hello.js↓

router.get('/',(req, res, next) => {
    var opt = {
        host: 'news.google.com',
        port: 443,
        path: '/rss/search?q=corona&q=korona&hl=ja&gl=JP&ceid=JP:ja'
    };
    http.get(opt, (res2) => {
        var body = '';
        res2.on('data',(data) => {
            body += data;
        });
        res2.on('end', () => {
            parseString(body.trim(), (err, result) => {
                var data = {
                    title: 'コロナウイルスの最新情報を表示します',
                    content: result.rss.channel[0].item
                };
                res.render('hello', data);
            })
        });
    });
});  

hello.ejs↓

<!DOCTYPE html>
<html>
    <head>
        <meta http-equiv="content-type" content="text/html; charset=UTF-8">
        <title><%= title %></title>
        <link rel='stylesheet' href="/stylesheets/style.css" />
    </head>
    
    <body>
        <header>
            <h1><%= title %></h1>
        </header>
        <div role="main">
            <% if (content != null) { %>
                <ol>
                    <% for (var i in content) { %>
                        <% var obj = content[i]; %>
                        <li><%= obj.pubDate %><a href="<%=obj.link %>"><%= obj.title %></a></li>
                        </tr>
                    <% } %>
                </ol>
            <% } %>
        </div>
    </body>
</html>
スクリーンショット 2020-03-29 15.55.27.png

(今回取得したxml
https://news.google.com/rss/search?q=corona&q=korona&hl=ja&gl=JP&ceid=JP:ja)

##解決策
###①xmlの記事の中のitemを配列に入れていく。
for in を使ってxmlのitemを配列に入れる処理をループさせます。

配列を作る、ループを作る、配列へpushという順番です。

※ソートする為に配列へ入れます。

<!-- 配列を作成 -->
<% var hash = new Array %>

<!-- xmlのitemをループ処理する -->
<% for (var i in content) { %>
    <% var obj = content[i]; %>  
    <!-- itemを配列へ追加 -->        
    <% hash.push(obj); %>
<% } %> 

※ejsの中にjsを書いています。
※content = result.rss.channel[0].item

###②配列をソートして日付順に並べる

<!-- 配列をソートして日付順に変更 -->
<% hash.sort(function(a,b) {
    return (a.pubDate < b.pubDate ? 1 : -1);
}); %>

これで配列の中のitemが、xmlのpubDateの日付順に並びました。
※こちらもejsの中にjsを書いています。
※参考にした記事は下に載っています。

###③日付の表示形式を変更
1、配列をfor inでループさせる
2、ループの中にDateオブジェクトを作成
3、日付の形式を変更
4、(西暦2020年を削除)任意
5、ループ処理の中で記事を表示する

<!-- 配列をループ処理 -->
<% for (var i in hash) { %>
    <% var obj2 = hash[i] %>

    <!-- 日付の表示形式を変更 -->
    <% 
        var date2 = new Date(obj2.pubDate);
        var b = date2.toLocaleString('ja-JP', {era:'long'});                            
        obj2.pubDate = b;
    %>
    <!-- 西暦を削除 -->
    <% var obj3_pubDate = obj2.pubDate.replace('西暦2020年', ''); %>

    <!-- 表示 -->
    <div class="center">
        <ul>
            <li>
                <a href="<%=obj2.link %>">
                    <div class="Date"><%=obj3_pubDate %></div>
                    <div class="title"><%="   " + obj2.title %></div>
                </a>
            </li>
         </ul>
    </div>
<% } %>

##表示結果
css追加前↓
スクリーンショット 2020-03-29 17.25.04.png

css追加後↓
スクリーンショット 2020-03-29 17.26.40.png

#変更後のコード
hello.ejs↓

<!DOCTYPE html>
<html lang="ja">
    <head>
        <meta charset="UTF-8">
        <meta http-equiv="content-type" content="text/html; charset=UTF-8">
        <title><%= title %></title>
        <link rel='stylesheet' href="/stylesheets/style.css" />
    </head>

    <div class="style">
        <!-- 更新日時を日本語へ変更する -->
        <% var update2 = new Date(update);
           var update3 = update2.toLocaleString('ja-JP', {era:'long'});                            
           update = update3;
        %>
        <!-- 更新日時の西暦を消す -->
        <% var update4 = update.replace('西暦2020年', ''); %>

    </div>
    
    <body>
        <header>
            <h1><%= title %>更新(<%= update4 %>)</h1>
        </header>
        <div role="main">
            <% if (content != null) { %>
                    <!-- 配列を作成 -->
                    <% var hash = new Array %>

                    <!-- xmlのitemをループ処理する -->
                    <% for (var i in content) { %>
                        <% var obj = content[i]; %>  
                        <!-- itemを配列へ追加 -->        
                        <% hash.push(obj); %>
                    <% } %> 

                    <!-- 配列をソートして日付順に変更 -->
                    <% hash.sort(function(a,b) {
                        return (a.pubDate < b.pubDate ? 1 : -1);
                    }); %>

                    <!-- 配列をループ処理 -->
                    <% for (var i in hash) { %>
                        <% var obj2 = hash[i] %>

                        <!-- 日付の表示形式を変更 -->
                        <% 
                            var date2 = new Date(obj2.pubDate);
                            var b = date2.toLocaleString('ja-JP', {era:'long'});                            
                            obj2.pubDate = b;
                        %>
                        <!-- 西暦を削除 -->
                        <% var obj3_pubDate = obj2.pubDate.replace('西暦2020年', ''); %>

                        <!-- 表示 -->
                        <div class="center">
                            <ul>
                                <li>
                                    <a href="<%=obj2.link %>">
                                        <div class="Date"><%=obj3_pubDate %></div>
                                        <div class="title"><%="   " + obj2.title %></div>
                                    </a>
                                </li>
                            </ul>
                        </div>
                    <% } %>
            <% } %>
        </div>
    </body>
</html>

hello.js↓


var express = require('express');
var router = express.Router();

var http = require('https');
var parseString = require('xml2js').parseString;

router.get('/',(req, res, next) => {
    var opt = {
        host: 'news.google.com',
        port: 443,
        path: '/rss/search?q=corona&q=Coronavirus&hl=ja&gl=JP&ceid=JP:ja'
    };
    http.get(opt, (res2) => {
        var body = '';
        res2.on('data',(data) => {
            body += data;
        });
        res2.on('end', () => {
            parseString(body.trim(), (err, result) => {
                var data = {
                    title: 'コロナウイルスの最新情報を表示します',
                    content: result.rss.channel[0].item,
                    update: result.rss.channel[0].lastBuildDate
                };
                res.render('hello', data);
            })
        });
    });
});  

module.exports = router;

##参考

配列を日付順にソートする方法
https://infoteck-life.com/a0107-js-array-sort-date/
https://www.p-nt.com/technicblog/archives/58

Dateオブジェクトの使い方入門
https://www.sejuku.net/blog/30171

Dateオブジェクトのプロパティ(日付の表示形式を参考にしました。)
https://so-zou.jp/web-app/tech/programming/javascript/grammar/object/date.htm

ループ処理(今回はfor inでループしています。)
https://qiita.com/endam/items/808a084859e3a101ab8f

文字列から指定した文字を削除する(日付の西暦2020年を削除する為に参考にしました。)
https://zukucode.com/2017/04/javascript-string-remove.html

4
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?