2

Twitter gemを使用してツイートを取り込むための簡単なJekyllプラグインを作成しました(以下を参照)。プラグインのrubyスクリプトを開いているGithubサイトに残したいのですが、Twitter APIが最近変更されたため、gemに認証資格が必要になりました。

require 'twitter'   # Twitter API
require 'redcarpet' # Formatting links

module Jekyll
  class TwitterFeed < Liquid::Tag
    def initialize(tag_name, text, tokens)
      super
      input = text.split(/, */ )
      @user = input[0]
      @count = input[1]
      if input[1] == nil
        @count = 3
      end
    end
    def render(context)
      # Initialize a redcarpet markdown renderer to autolink urls
      # Could use octokit instead to get GFM
      markdown = Redcarpet::Markdown.new(Redcarpet::Render::HTML,
                                                 :autolink => true, 
                                                 :space_after_headers => true)

      ## Attempt to load credentials externally here:
      require '~/.twitter_auth.rb'

      out = "<ul>"
      tweets = @client.user_timeline(@user)
      for i in 0 ... @count.to_i
      out = out + "<li>" + markdown.render(tweets[i].text) +
        " <a href=\"http://twitter.com/" + @user + "/statuses/" + 
        tweets[i].id.to_s + "\">"  + tweets[i].created_at.strftime("%I:%M %Y/%m/%d") + 
        "</a> " + "</li>"
      end
      out + "</ul>"
    end
  end
end
Liquid::Template.register_tag('twitter_feed', Jekyll::TwitterFeed)

回線を入れ替えたら

      require '~/.twitter_auth.rb'

ここtwitter_auth.rbに次のようなものが含まれています:

require 'twitter'
@client = Twitter::Client.new(
:consumer_key => "CEoYXXXXXXXXXXX",
:consumer_secret => "apnHXXXXXXXXXXXXXXXXXXXXXXXX",
:oauth_token => "105XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX",
:oauth_token_secret => "BJ7AlXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
)

これらのコンテンツを上記のスクリプトに直接配置すると、プラグインスクリプトは問題なく機能します。しかし、それらを外部ファイルに移動して、図のように読み込もうとすると、Jekyllは認証に失敗します。から呼び出すと、この関数は問題なく機能しているように見えるirbので、Jekyllビルド中に機能しない理由がわかりません。

4

1 に答える 1

2

どのように機能するかについて混乱するかもしれないと思いますrequire。を呼び出すとrequire、最初にRubyはファイルがすでに必要かどうかをチェックし、必要な場合は直接戻ります。requireそうでない場合は、ファイルの内容が実行されますが、ステートメントと同じスコープではありません。言い換えると、を使用することは、ステートメントをファイルの内容に置き換えることと同じでrequire ありません(たとえば、Cの動作方法です)。require#include

あなたの場合、~/.twitter_auth.rbファイルが必要な場合、インスタンス変数が作成されますが、フォームと呼ばれるインスタンスのインスタンス変数としてではなく@client、最上位mainオブジェクトのインスタンス変数として作成されます。TwitterFeedrequire

オブジェクトを定数に割り当てて、メソッドから参照できるようにすることができます。Twitter::Clientrender

MyClient = Twitter::Client.new{...

その後

require '~/twitter_auth.rb'
@client = MyClient
...

私はこれを何が起こっているのかを説明するものとして提案するだけでrequire、それは本当に良いテクニックではありません。

より良いオプションは、ホームディレクトリに単純なデータ形式でクレデンシャルを保持し、スクリプトからそれらを読み取り、それらを使用してTwitterクライアントを作成することだと思います。この場合、Yamlがおそらくその仕事をします。

まず、次のようなものに~/twitter_auth.rb置き換えます。~/twitter_auth.yaml

:consumer_key: "CEoYXXXXXXXXXXX"
:consumer_secret: "apnHXXXXXXXXXXXXXXXXXXXXXXXX"
:oauth_token: "105XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
:oauth_token_secret: "BJ7AlXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

次に、クラスのどこにあるかを次のようrequre "~/twitter_auth.rb"に置き換えます(require 'yaml'ファイルの先頭にも必要です)。

@client = Twitter::Client.new(YAML.load_file("~/twitter_auth.yaml"))
于 2013-01-12T23:33:34.210 に答える