-
Notifications
You must be signed in to change notification settings - Fork 8
/
Copy pathZulipFeedListener.php
109 lines (92 loc) · 2.64 KB
/
ZulipFeedListener.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
<?php
require_once 'ZulipConfig.php';
require_once PHABRICATOR_INIT_SCRIPT;
function get_topic_from_content($content) {
if (preg_match("/revision (D\d+)/", $content, $matches)) {
return $matches[1];
}
return ZULIP_TOPIC_NAME; // default
}
function post_to_zulip($content) {
sleep(ZULIP_RATE_LIMITING_WAIT);
$url = ZULIP_HOST . '/v1/messages';
$topic = get_topic_from_content($content);
$data = array(
"type" => 'stream',
"to" => ZULIP_STREAM_NAME,
"subject" => $topic,
"content" => $content,
"client" => 'phabricator'
);
$request = new HTTPSFuture($url);
$request->setMethod('POST');
$request->addHeader('Authorization', 'Basic ' . base64_encode(ZULIP_USER . ':' . ZULIP_API_KEY));
$request->setData($data);
$request->resolvex();
}
function get_connected_conduit() {
// Conduit objects are Phabricator's way of talking to their server.
$uri = PHABRICATOR_HOST . '/api/';
$conduit = new ConduitClient($uri);
$conduit->callMethodSynchronous(
'conduit.connect',
array(
'client' => CLIENT,
'clientVersion' => CLIENT_VERSION,
'clientDescription' => CLIENT_DESCRIPTION,
'user' => CONDUIT_USER,
'certificate' => CONDUIT_CERT
)
);
return $conduit;
}
function get_latest_stories($conduit, $last_reported_timestamp) {
// This code can be simplified once https://secure.phabricator.com/D6903
// is deployed widely. Until then, we do this kind of awkward loop back
// through the chronologically descending results.
$after = 0;
$stories = array();
while (true) {
$chunk = $conduit->callMethodSynchronous(
'feed.query',
array(
'after' => $after,
'view' => 'text',
'limit' => QUERY_CHUNK_SIZE
)
);
if (count($chunk) == 0) {
return array_reverse($stories);
}
foreach ($chunk as $story) {
if ($story['chronologicalKey'] <= $last_reported_timestamp) {
return array_reverse($stories);
}
$stories[] = $story;
$after = $story['chronologicalKey'];
}
}
}
function get_feed() {
$conduit = get_connected_conduit();
$last_reported_timestamp = 0;
$latest = $conduit->callMethodSynchronous(
'feed.query',
array(
'limit' => 1,
'view' => 'text',
)
);
foreach ($latest as $story) {
$last_reported_timestamp = $story['chronologicalKey'];
}
while (true) {
$stories = get_latest_stories($conduit, $last_reported_timestamp);
foreach ($stories as $story) {
post_to_zulip($story['text']);
$last_reported_timestamp = $story['chronologicalKey'];
}
sleep(FEED_POLLING_INTERVAL);
}
}
get_feed();