2

私の php プロジェクトは、現在のページの送信のタイトルを取得するために reddit JSON API を使用しています。

現在、ページが読み込まれるたびにいくつかのコードを実行していますが、実際の API 制限はありませんが、いくつかの問題が発生しています。

何とかサブミッションのタイトルをローカルに保存したいと思います。これを行うための最良の方法をお勧めできますか? サイトは appfog で実行されています。あなたは何をお勧めします?

これは私の現在のコードです:

<?php

/* settings */

$url="http://".$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI'];

$reddit_url = 'http://www.reddit.com/api/info.{format}?url='.$url;

$format = 'json'; //use XML if you'd like...JSON FTW!
$title = '';

/* action */
$content = get_url(str_replace('{format}',$format,$reddit_url)); //again, can be xml or json
if($content) {
    if($format == 'json') {
        $json = json_decode($content,true);
        foreach($json['data']['children'] as $child) { // we want all children for this example
            $title= $child['data']['title'];
        }
    }
}

/* output */


/* utility function:  go get it! */
function get_url($url) {
    $ch = curl_init();
    curl_setopt($ch,CURLOPT_URL,$url);
    curl_setopt($ch,CURLOPT_RETURNTRANSFER,1);
    curl_setopt($ch,CURLOPT_CONNECTTIMEOUT,1);
    $content = curl_exec($ch);
    curl_close($ch);
    return $content;
}
?>

ありがとう!

4

4 に答える 4

4

序章

ここにあなたのコードの修正版があります

$url = "http://stackoverflow.com/";
$loader = new Loader();
$loader->parse($url);
printf("<h4>New List : %d</h4>", count($loader));
printf("<ul>");
foreach ( $loader as $content ) {
    printf("<li>%s</li>", $content['title']);
}
printf("</ul>");

出力

新しいリスト : 7

  • Joel Spolsky と Jeff Atwood による新しいポッドキャスト。
  • サンプルコードの良いサイト/Pyhton
  • stackoverflow.com には明らかに、インターネットの歴史の中でこれまでに考えられた最高の Web コードがあり、reddit はそれをコピーし始めたほうがよいでしょう。
  • プログラマー向けの reddit のような OpenID を使用した Web サイト
  • 素晴らしい開発者サイト。あなたの質問に答えて、知っている人に聞いてください。
  • スタック オーバーフローが一般公開されました
  • プログラミングQ&Aサイト、Stack Overflow。& Reddit は、インターフェースから多くのことを学ぶことができます!

簡単なデモ

問題

ここで達成したいことがいくつかあります。

  • 何とかサブミッションのタイトルをローカルに保存したい
  • 現在、ページが読み込まれるたびにいくつかのコードを実行しています

私が理解していることから、必要なのは データの単純なキャッシュコピーであるため、常にURLをロードする必要はありません。

シンプルなソリューション

使用できる単純なキャッシュ システムはmemcache ..

例A

$url = "http://stackoverflow.com/";

// Start cache
$m = new Memcache();
$m->addserver("localhost");
$cache = $m->get(sha1($url));

if ($cache) {
    // Use cache copy
    $loader = $cache;
    printf("<h2>Cache List: %d</h2>", count($loader));
} else {

    // Start a new Loader
    $loader = new Loader();
    $loader->parse($url);
    printf("<h2>New List : %d</h2>", count($loader));
    $m->set(sha1($url), $loader);
}

// Oupput all listing
printf("<ul>");
foreach ( $loader as $content ) {
    printf("<li>%s</li>", $content['title']);
}
printf("</ul>");

例 B

Last Modification Dateドキュメントが変更された場合にのみ新しいコピーを保存するように、キャッシュキーとして使用できます

$headers = get_headers(sprintf("http://www.reddit.com/api/info.json?url=%s",$url), true);
$time = strtotime($headers['Date']); // get last modification date 
$cache = $m->get($time);

if ($cache) {
    $loader = $cache;
}

クラスが実装しJsonSerializableているため、結果を json エンコードし、MongoDB や MySQL などのデータベースに保存することもできます。

 $data = json_encode($loader);
 // Save to DB 

使用クラス

class Loader implements IteratorAggregate, Countable, JsonSerializable {
    private $request = "http://www.reddit.com/api/info.json?url=%s";
    private $data = array();
    private $total;

    function parse($url) {
        $content = json_decode($this->getContent(sprintf($this->request, $url)), true);
        $this->data = array_map(function ($v) {
            return $v['data'];
        }, $content['data']['children']);
        $this->total = count($this->data);
    }

    public function getIterator() {
        return new ArrayIterator($this->data);
    }

    public function count() {
        return $this->total;
    }

    public function getType() {
        return $this->type;
    }

    public function jsonSerialize() {
        return $this->data;
    }


    function getContent($url) {
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 1);
        $content = curl_exec($ch);
        curl_close($ch);
        return $content;
    }
}
于 2012-12-11T17:23:17.503 に答える
0

私は通常、次のようにデータをそのままフラットファイルとして保存します。

<?php
define('TEMP_DIR', 'temp/');
define('TEMP_AGE', 3600);

function getinfo($url) {
    $temp = TEMP_DIR . urlencode($url) . '.json';

    if(!file_exists($temp) OR time() - filemtime($temp) > TEMP_AGE) {
        $info = "http://www.reddit.com/api/info.json?url=$url";
        $json = file_get_contents($info);
        file_put_contents($temp, $json);
        }
    else {
        $json = file_get_contents($temp);
        }

    $json = json_decode($json, true);
    $titles = array();
    foreach($json['data']['children'] as $child) {
        $titles[] = $child['data']['title'];
        }
    return $titles;
    }

$test = getinfo('http://imgur.com/');
print_r($test);

PS。私file_get_contentsはjsonデータを取得するために使用しますが、curlを使用する独自の理由があるかもしれません. また、私はフォーマットをチェックしません.明らかにあなたはjsonを好みます.

于 2012-12-17T05:23:52.483 に答える
0

この後:

if($format == 'json') {
    $json = json_decode($content,true);
    foreach($json['data']['children'] as $child) { // we want all children for this example
        $title = $child['data']['title'];
    }
}

}`

次に、json ファイルに保存し、localfolder の Web サイト パスにダンプします。

$storeTitle = array('title'=>$title)

$fp = fopen('../pathToJsonFile/title.json'), 'w');
fwrite($fp, json_encode($storeTitle));
fclose($fp);

次に、いつでもjsonファイルを呼び出してデコードし、タイトルを変数に抽出して使用できます

于 2012-12-16T10:32:06.730 に答える
0

あなたの質問が正確に何であるかはわかりませんが、最初にポップするのは次のとおりです。

foreach($json['data']['children'] as $child) { // we want all children for this example
    $title= $child['data']['title'];
}

本当に上書きします$titleか? $child実際には、最後のタイトルのみが保持されます。

さて、あなたの質問に。毎回リクエストを再発行する必要がないように、リクエストされた URL のコンテンツをキャッシュする何らかのメカニズムを探しているのではないでしょうか? 私は appFog の経験はありません。

私の提案は、(処理された)応答を次のいずれかにキャッシュすることです。

  • TTL が短い APC 共有メモリ
  • 一時ファイル
  • データベース

URL + 引数のハッシュをルックアップ キーとして使用できます。内部でこのチェックを行うget_url()と、コードの他の部分を変更する必要がなく、LOC が 3 つまでしかかかりません。

于 2012-12-10T10:50:10.137 に答える