Qiita
Ruby
Heroku

非公式Qiita新着記事一覧

概要

Qiitaのデザインが新しくなってから新着記事一覧がなくなりました。QiitaのAPIを叩けば一覧を取ることはできますが、それをちゃんとWebページで見られるようにします。

ここに出来上がっているものがあります。
非公式Qiita新着記事一覧
(2017/12/13追記)
公式版が出たので公開停止致しました:)
https://qiita.com/items

前置き

使用するAPIはこれです。これで新着20件がとれます。

https://qiita.com/api/v2/items?page=1&per_page=20

認証不要で取得できます。なお、QiitaのAPI仕様によると

認証している状態ではユーザごとに1時間に1000回まで、認証していない状態ではIPアドレスごとに1時間に60回までリクエストを受け付けます。

ということなので、アクセスがある毎にAPIを叩くのではなく、サーバー(heroku)上で定期的(今回は10分置き)にAPIを叩き→静的htmlを生成し、みんなにはそれを見てもらいます。エコです。

なお、Qiitaブログによると

これまでご提供していた、全タグの新着記事が表示される「すべて」フィードにつきましては現在再度ご用意すべく開発中です。ご不便おかけいたしますが少々おまちくださいませ。

とのことなので、今回の私の労力はいずれ無駄になるでしょう:D

使うもの

  • Ruby(Railsじゃないよ)
    • RestClient(API叩く用)
    • JSON
    • ERB(静的HTML生成用)
  • Heroku(クラウド実行環境)
    • Heroku Scheduler(定期的にコマンドを実行するためのアドオン)
  • git(Herokuにスクリプトをアップするのに必要)
  • FC2web(ただのWebサーバ)
  • ubuntu(私の開発環境)

Heroku上での流れ

  1. QiitaのAPIを叩き静的HTMLを生成するスクリプトを定期実行
  2. 生成したHTMLファイルをFC2WebサーバへFTPアップロード

わざわざ生成したHTMLファイルを別のWebサーバへアップロードするのは、Heroku上で出力したファイルは一時ファイルとしてしか存在できないらしいからです。

ではさっそく作っていきます。適当な作業ディレクトリを作ってそこで作業します。

静的HTMLのベースとなるERBテンプレート

template.erb
<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <title>Qiita新着リスト(非公式)</title>
    <link rel="stylesheet" href="style.css">
    <!-- bootstrap関連 -->
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta.2/css/bootstrap.min.css" integrity="sha384-PsH8R72JQ3SOdhVi3uxftmaW6Vc51MKb0q5P2rRUpPvrszuE4W1povHYgTpBfshb" crossorigin="anonymous">
    <script src="https://code.jquery.com/jquery-3.2.1.slim.min.js" integrity="sha384-KJ3o2DKtIkvYIK3UENzmM7KCkRr/rE9/Qpg6aAZGJwFDMVNA/GpGFF93hXpG5KkN" crossorigin="anonymous"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.3/umd/popper.min.js" integrity="sha384-vFJXuSJphROIrBnz7yo7oB41mKfc8JzQZiCq4NCceLEaO4IHwicKwpJf9c9IpFgh" crossorigin="anonymous"></script>
    <script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta.2/js/bootstrap.min.js" integrity="sha384-alpBpkh1PFOepccYVYDB4do5UnbKysX5WZXm3XxPqe5iKTfUKjNkCk9SaVuEZflJ" crossorigin="anonymous"></script>
  </head>

  <body>
    <div class="container">
      <ul class="list-unstyled item">
        <li>Qiita新着リスト(非公式)</li>
        <%= list %>
      </ul>
      最終更新:<%= Time.now.strftime("%Y-%m-%d %X") %>
    </div>
  </body>

</html>

Gemfile

RestClientとJSONを使うのでGemfileを作ってbundlerで入れておきます。このGemfileはherokuにスクリプトを配置するときにも必要です。

Gemfile
source "https://rubygems.org"

gem "rest-client"
gem "json"
ruby "2.3.1"

Gemfileを作ったら

bundle install

bundleコマンドがない人はインストールして下さいね。ubuntuなら

gem install bundler

API取得→静的HTML生成スクリプト

getNewList.rb
require 'rest-client'
require 'json'
require 'erb'

url = "https://qiita.com/api/v2/items?page=1&per_page=20"

# APIを叩きます
res = RestClient.get url
res_json = JSON.parse(res.body)

# 取得したJSONからタイトル、記事URL、投稿者のID・アイコン画像URL・
# プロフィールURL、投稿日時を取得し、リストタグを生成
list = ""
res_json.each do |data|

  title = data["title"]
  url = data["url"]
  id = data["user"]["id"]
  img_url = data["user"]["profile_image_url"]
  profile_url = "https://qiita.com/#{id}"
  created_at = DateTime.parse(data["created_at"]).strftime("%Y-%m-%d %X")

  list.concat(<<-EOS
    <li>
      <a href="#{profile_url}">
        <img src="#{img_url}" class="rounded float-left">
      </a>

      <div>
        <a href="#{url}">#{title}</a><br />
        <small class="text-muted">by <a href="#{profile_url}">#{id}</a> #{created_at}</small>
      </div>
    </li>
  EOS
  )
end

# ERBのテンプレートへリストタグを埋め込み静的HTMLを生成します
erb = ERB.new(File.open("template.erb").read)
File.write("newList.html", erb.result(binding))

FC2Webサーバの準備

Webサーバならどこでもいいのですが、FTPアップロードできるところを準備します。最初Xdomainというところで作ったのですが、なぜかHeroku上でFTPアップロードのスクリプトが503ログインエラーで動かず。日本以外からのFTP接続をブロックしてたりするのかもしれません。(なにげにここでずっとハマってました。)

HTMLファイルをFTPアップロードするスクリプト

putFtp.rb
require 'net/ftp'

file = "newList.html"

ftp = Net::FTP.new('FTPサーバURL','FTPアカウント','パスワード')
ftp.passive = true
ftp.put(file)
ftp.close

スタイルシート

見栄えを整えるようです。基本はbootstrapで。作ったらFC2Webサーバへアップロードしておきます。

style.css
a:link { 
  color: #000;
}

a:visited { 
  color: #000;
}

ul.item li {
  border-bottom: 1px solid #e8e8e8;
  padding: 16px;
}

ul.item img {
  width: 40px;
  height: 40px;
  margin-right: 8px;
}

ul.item div {
  line-height: 1.2;
}

以上で必要なファイルはできました。

git設定

まず、Herokuへアップする前に作成したファイルたちをgit管理下に設定します。

git init
git add .
git commit -m "initial commit"

Herokuへアップロード

Herokuアカウントの作成方法はぐぐってもらえばすぐわかります。

まずHeroku環境に新規アプリ用の箱作りと、若干の設定をします。

heroku login
heroku create qiita-new-list

# herokuでrubyを実行するためのパッケージ的な何か?
heroku buildpacks:set heroku/ruby

# タイムゾーンの設定です。生成するHTMLの中で生成日時を埋め込むため。
heroku config:add TZ=Asia/Tokyo

続いてスクリプトをアップロードします。

git push heroku master

動作確認してみましょう。

heroku run "ruby getNewList.rb; ruby putFtp.rb"

FC2WebサーバにHTMLファイルができていれば成功です。

Heroku Schedulerの設定

これはHerokuで定期的にコマンドを実行するためのアドオンです。

スケッチ.png

スケッチ2.png

スケッチ3.png

Provisionのときに面倒なことにクレジットカードの登録をせよとでます。プランはフリーなので請求されることはないとは思いますが、登録しないと使えません。なお、Vプリカでもいけました。

次にスケジューラの設定をします。簡単です。

スケッチ4.png

↓でHTMLを生成するスクリプトとFTPアップロードするスクリプトを設定しています。実行間隔は10分置き。

スケッチ5.png

以上です。このなかなかcron的な定期実行機能を持っていて無料で使えるとこってまずないですよね。Herokuさんありがとう:)