-
Notifications
You must be signed in to change notification settings - Fork 53
/
index.html
285 lines (244 loc) · 7.83 KB
/
index.html
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
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="content-type" content="text/html;charset=UTF-8" />
<meta http-equiv="X-UA-Compatible" content="chrome=1">
<title>Pixel Ping</title>
<style>
body {
font-size: 16px;
line-height: 24px;
background: #eff7ff;
color: #022;
font-family: Arial;
font-family: "Palatino Linotype", "Book Antiqua", Palatino, FreeSerif, serif;
}
div.container {
width: 720px;
margin: 50px 0 50px 50px;
}
p,
li {
margin: 16px 0 16px 0;
width: 550px;
}
p.break {
margin-top: 35px;
}
a,
a:visited {
padding: 0 2px;
text-decoration: none;
background: #77dddd;
color: #003333;
}
a:active,
a:hover {
color: #000;
background: #00cccc;
}
h1,
h2,
h3,
h4,
h5,
h6 {
margin-top: 40px;
}
b.header {
font-size: 18px;
}
span.alias {
font-size: 14px;
font-style: italic;
margin-left: 20px;
}
table {
margin: 16px 0;
padding: 0;
}
tr,
td {
margin: 0;
padding: 0;
}
td {
padding: 9px 15px 9px 0;
}
td.definition {
line-height: 18px;
font-size: 14px;
}
code,
pre,
tt {
font-family: Monaco, Consolas, "Lucida Console", monospace;
font-size: 12px;
line-height: 18px;
color: #444;
}
code {
margin-left: 20px;
}
pre {
font-size: 12px;
padding: 2px 0 2px 12px;
border-left: 6px solid #55aaaa;
margin: 0px 0 10px;
}
li pre {
padding: 0;
border-left: 0;
margin: 6px 0 6px 0;
}
#diagram {
margin: 20px 0 0 0;
}
</style>
</head>
<body>
<div class="container">
<h1>Pixel Ping <sub style="font-size:150%;">☄</sub></h1>
<p>
<a href="http://github.com/documentcloud/pixel-ping/">Pixel Ping</a> is a minimalist pixel-tracker written in
<a href="http://coffeescript.org">CoffeeScript</a> for
<a href="http://nodejs.org">Node.js</a>.
</p>
<p>
If you provide embeddable applications or HTML widgets for third-party sites, are serving them statically, would like to
keep track of specific usage information, and don't want to inject something heavy like Google Analytics, perhaps Pixel
Ping can help.
</p>
<p>
<a href="docs/pixel-ping.html">The complete annotated source code</a> is also available.
</p>
<p>
<i>Pixel Ping is currently at <b>version 0.1.6</b>, and is an open-source
component of <a href="http://www.documentcloud.org/">DocumentCloud</a>.</i>
</p>
<p>
<a href="#introduction">Introduction</a> |
<a href="#installation">Installation</a> |
<a href="#usage">Usage</a> |
<a href="#changes">Change Log</a>
</p>
<h2 id="introduction">Introduction</h2>
<p>
Embeddable content that gets a lot of page views is often cached and served statically — especially for third-party
sites where traffic is unpredictable. It's not appropriate to serve a dynamic request for every hit, invoking a heavy
web stack and burying the database under lots of tiny writes. Pixel Ping builds up an in-memory hash of unique keys
to hits, where the keys are arbitrary values generated by your embedded content. At a configurable interval, Pixel
Ping flushes the keys and hits to your web application via a REST request, and your application can then analyze and
store the data.
</p>
<h2 id="installation">Installation</h2>
<ol>
<li>
Pixel Ping depends on <b>Node.js</b> and the <b>Node Package Manager</b> (npm). If you don't already have these installed,
grab the latest. Node releases can be found on the <a href="http://www.nodejs.org/#download">download page</a>. NPM
can be installed with a script:<br />
<tt>curl https://npmjs.org/install.sh | sudo sh</tt>
</li>
<li>
Install Pixel Ping via NPM:<br />
<tt>sudo npm install pixel-ping</tt><br /> As always, leave off "sudo" if you don't need it.
</li>
</ol>
<h2 id="usage">Usage</h2>
<p>
To use Pixel Ping in your embedded content, insert an image tag into the page, along with the unique key that distinguishes
hits for aggregation:
</p>
<pre>
<img src="/pixel.gif?key=[KEY]" alt="" /></pre>
<p>
The key can be any string — a model id, the URL of the page, the embed options, etc. You'll probably either use your
server-side template or a snippet of inline JavaScript to generate the key. When Pixel Ping flushes the hits to your
application, you'll receive a JSON hash of hits that looks like this:
</p>
<pre>
{
"/pages/about.html": 276,
"/articles/policy.html": 324
}</pre>
<p>
... where the key is the key you passed to the image tag, and the value is the number of hits since the previous flush. To
force a flush, send a
<tt>SIGUSR2</tt> signal to the Pixel Ping process.
</p>
<p>
Installing Pixel Ping gives you the <tt>pixel-ping</tt> command. To launch it, you pass the path to your configuration
file:
</p>
<pre>
pixel-ping path/to/config.json</pre>
<p>
In the configuration file, specify the host and port you'd like Pixel Ping to bind to, as well as the interval (in seconds)
at which to flush the hits, and the URL endpoint where your application accepts the aggregated hits and keys. For security,
you may specify an optional "secret" string, which will be passed along with each flush from Pixel Ping to your internal
API.
</p>
<pre>
{
"host": "127.0.0.1",
"port": "9187",
"interval": 600,
"endpoint": "http://www.example.com/internal/save_hits",
"discard": false
}</pre>
<p>
If the endpoint is hosted on an https server, you must specify the port number after the domain name. For example:
</p>
<pre>
{
"endpoint": "https://www.example.com:443/internal/save_hits",
}
</pre>
<p>
In addition, a user can setup SSL credentials to start the server under HTTPS. The SSL key and cert paths are required for
HTTPS. The SSL chain path is optional.
</p>
<pre>
{
"sslkey" : "/path/to/privkey.pem",
"sslcert" : "/path/to/cert.pem",
"sslca" : "/path/to/chain.pem",
}
</pre>
<h2 id="changes">Change Log</h2>
<p>
<b class="header">0.1.6</b> <i>March 25, 2019</i><br />
Fixed a bug in HTTPS support, where you previously would have to explicitly
specify port 443, thanks to
<a href="https://github.com/danielbeardsley">Daniel Beardsley</a>.
</p>
<p>
<b class="header">0.1.5</b> <i>March 25, 2019</i><br />
Fixed a data loss bug, where hits that were recorded <i>during</i> a flush
would be discarded, thanks to
<a href="https://github.com/danielbeardsley">Daniel Beardsley</a>.
</p>
<p>
<b class="header">0.1.4</b> <i>August 22, 2017</i><br />
Added HTTPS support, for both the pixel server and the endpoint flush,
thanks to Maxwell Francisco.
</p>
<p>
<b class="header">0.1.3</b> <i>May 29, 2014</i><br /> Changed the signal from USR1
(which is used by node for debugging) to USR2 and upgraded
to <tt>http.request</tt> thanks to
<a href="https://github.com/gka">Jeff Larson</a> and
<a href="https://github.com/gka">Gregor Aisch</a>.
</p>
<p>
<b class="header">0.1.2</b> <i>September 8, 2010</i><br /> Initial release.
</p>
<p>
<br />
<a href="http://documentcloud.org/" title="A DocumentCloud Project" style="background:none;">
<img src="http://jashkenas.s3.amazonaws.com/images/a_documentcloud_project.png" alt="A DocumentCloud Project" style="position:relative;left:-10px;" />
</a>
</p>
</div>
</body>
</html>