frontend-helpers 0.0.1.beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/Gemfile +18 -0
- data/Gemfile.lock +108 -0
- data/LICENSE.txt +20 -0
- data/MIT-LICENSE +20 -0
- data/README.md +97 -0
- data/Rakefile +53 -0
- data/config/services.yml +95 -0
- data/config/settings.yml +24 -0
- data/frontend-helpers.gemspec +117 -0
- data/lib/.DS_Store +0 -0
- data/lib/asset-helpers/rails.rb +4 -0
- data/lib/frontend-helpers/html5_helper.rb +19 -0
- data/lib/frontend-helpers/metatag_helper.rb +58 -0
- data/lib/frontend-helpers/services_helper.rb +89 -0
- data/lib/frontend-helpers.rb +16 -0
- data/lib/generators/frontend/install/install_generator.rb +27 -0
- data/lib/tasks/frontend-helpers_tasks.rake +4 -0
- data/script/rails +6 -0
- data/test/dummy/Rakefile +7 -0
- data/test/dummy/app/assets/javascripts/application.js +9 -0
- data/test/dummy/app/assets/stylesheets/application.css +7 -0
- data/test/dummy/app/controllers/application_controller.rb +3 -0
- data/test/dummy/app/helpers/application_helper.rb +2 -0
- data/test/dummy/app/mailers/.gitkeep +0 -0
- data/test/dummy/app/models/.gitkeep +0 -0
- data/test/dummy/app/views/layouts/application.html.erb +14 -0
- data/test/dummy/config/application.rb +42 -0
- data/test/dummy/config/boot.rb +10 -0
- data/test/dummy/config/database.yml +25 -0
- data/test/dummy/config/environment.rb +5 -0
- data/test/dummy/config/environments/development.rb +27 -0
- data/test/dummy/config/environments/production.rb +54 -0
- data/test/dummy/config/environments/test.rb +39 -0
- data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
- data/test/dummy/config/initializers/inflections.rb +10 -0
- data/test/dummy/config/initializers/mime_types.rb +5 -0
- data/test/dummy/config/initializers/secret_token.rb +7 -0
- data/test/dummy/config/initializers/session_store.rb +8 -0
- data/test/dummy/config/initializers/wrap_parameters.rb +12 -0
- data/test/dummy/config/locales/en.yml +5 -0
- data/test/dummy/config/routes.rb +58 -0
- data/test/dummy/config.ru +4 -0
- data/test/dummy/log/.gitkeep +0 -0
- data/test/dummy/public/404.html +26 -0
- data/test/dummy/public/422.html +26 -0
- data/test/dummy/public/500.html +26 -0
- data/test/dummy/public/favicon.ico +0 -0
- data/test/dummy/script/rails +6 -0
- data/test/frontend-helpers_test.rb +11 -0
- data/test/test_helper.rb +10 -0
- data/vendor/assets/javascripts/backbone/backbone.js +1149 -0
- data/vendor/assets/javascripts/backbone/index.js +2 -0
- data/vendor/assets/javascripts/backbone/underscore.js +807 -0
- data/vendor/assets/javascripts/ie/dd_belatedpng.js +13 -0
- data/vendor/assets/javascripts/ie/index.js +2 -0
- data/vendor/assets/javascripts/ie/reverse_zindex.js +1 -0
- data/vendor/assets/javascripts/jquery.async.js +77 -0
- data/vendor/assets/javascripts/jquery.cookie.js +89 -0
- data/vendor/assets/javascripts/jquery.lifestream.js +1516 -0
- data/vendor/assets/javascripts/jquery.validate.js +1166 -0
- data/vendor/assets/javascripts/log.js +8 -0
- data/vendor/assets/javascripts/modernizr.js +1116 -0
- data/vendor/assets/javascripts/shortcut.js +223 -0
- data/vendor/assets/javascripts/swfobject.js +4 -0
- data/vendor/assets/stylesheets/reset.css.sass +183 -0
- data/vendor/assets/stylesheets/variables.css.sass +21 -0
- metadata +175 -0
@@ -0,0 +1,1516 @@
|
|
1
|
+
/*!
|
2
|
+
* jQuery Lifestream Plug-in
|
3
|
+
* @version 0.1.2
|
4
|
+
* Show a stream of your online activity
|
5
|
+
*
|
6
|
+
* Copyright 2011, Christian Vuerings - http://denbuzze.com
|
7
|
+
*/
|
8
|
+
/*globals jQuery, $ */
|
9
|
+
;(function( $ ){
|
10
|
+
|
11
|
+
/**
|
12
|
+
* Create a valid YQL URL by passing in a query
|
13
|
+
* @param {String} query The query you want to convert into a valid yql url
|
14
|
+
* @return {String} A valid YQL URL
|
15
|
+
*/
|
16
|
+
var createYqlUrl = function( query ) {
|
17
|
+
return ( "http://query.yahooapis.com/v1/public/yql?q=__QUERY__&env=" +
|
18
|
+
"store://datatables.org/alltableswithkeys&format=json")
|
19
|
+
.replace( "__QUERY__" , encodeURIComponent( query ) );
|
20
|
+
};
|
21
|
+
|
22
|
+
/**
|
23
|
+
* Initialize the lifestream plug-in
|
24
|
+
* @param {Object} config Configuration object
|
25
|
+
*/
|
26
|
+
$.fn.lifestream = function( config ) {
|
27
|
+
|
28
|
+
// Make the plug-in chainable
|
29
|
+
return this.each(function() {
|
30
|
+
|
31
|
+
// The element where the lifestream is linked to
|
32
|
+
var outputElement = $(this),
|
33
|
+
|
34
|
+
// Extend the default settings with the values passed
|
35
|
+
settings = jQuery.extend({
|
36
|
+
// The name of the main lifestream class
|
37
|
+
// We use this for the main ul class e.g. lifestream
|
38
|
+
// and for the specific feeds e.g. lifestream-twitter
|
39
|
+
classname: "lifestream",
|
40
|
+
// Callback function which will be triggered when a feed is loaded
|
41
|
+
feedloaded: null,
|
42
|
+
// The amount of feed items you want to show
|
43
|
+
limit: 10,
|
44
|
+
// An array of feed items which you want to use
|
45
|
+
list: []
|
46
|
+
}, config),
|
47
|
+
|
48
|
+
// The data object contains all the feed items
|
49
|
+
data = {
|
50
|
+
count: settings.list.length,
|
51
|
+
items: []
|
52
|
+
},
|
53
|
+
|
54
|
+
// We use the item settings to pass the global settings variable to
|
55
|
+
// every feed
|
56
|
+
itemsettings = jQuery.extend( true, {}, settings ),
|
57
|
+
|
58
|
+
/**
|
59
|
+
* This method will be called every time a feed is loaded. This means
|
60
|
+
* that several DOM changes will occur. We did this because otherwise it
|
61
|
+
* takes to look before anything shows up.
|
62
|
+
* We allow 1 request per feed - so 1 DOM change per feed
|
63
|
+
* @private
|
64
|
+
* @param {Array} inputdata an array containing all the feeditems for a
|
65
|
+
* specific feed.
|
66
|
+
*/
|
67
|
+
finished = function( inputdata ) {
|
68
|
+
|
69
|
+
// Merge the feed items we have from other feeds, with the feeditems
|
70
|
+
// from the new feed
|
71
|
+
$.merge( data.items, inputdata );
|
72
|
+
|
73
|
+
// Sort the feeditems by date - we want the most recent one first
|
74
|
+
data.items.sort( function( a, b ) {
|
75
|
+
return ( b.date - a.date );
|
76
|
+
});
|
77
|
+
|
78
|
+
var items = data.items,
|
79
|
+
|
80
|
+
// We need to check whether the amount of current feed items is
|
81
|
+
// smaller than the main limit. This parameter will be used in the
|
82
|
+
// for loop
|
83
|
+
length = ( items.length < settings.limit ) ?
|
84
|
+
items.length :
|
85
|
+
settings.limit,
|
86
|
+
i = 0, item,
|
87
|
+
|
88
|
+
// We create an unordered list which will create all the feed
|
89
|
+
// items
|
90
|
+
ul = $('<ul class="' + settings.classname + '"/>');
|
91
|
+
|
92
|
+
// Run over all the feed items + add them as list items to the
|
93
|
+
// unordered list
|
94
|
+
for ( ; i < length; i++ ) {
|
95
|
+
item = items[i];
|
96
|
+
if ( item.html ) {
|
97
|
+
$('<li class="'+ settings.classname + '-'
|
98
|
+
+ item.config.service + '">').append( item.html )
|
99
|
+
.appendTo( ul );
|
100
|
+
}
|
101
|
+
}
|
102
|
+
|
103
|
+
// Change the innerHTML with a list of all the feeditems in
|
104
|
+
// chronological order
|
105
|
+
outputElement.html( ul );
|
106
|
+
|
107
|
+
// Trigger the feedloaded callback, if it is a function
|
108
|
+
if ( $.isFunction( settings.feedloaded ) ) {
|
109
|
+
settings.feedloaded();
|
110
|
+
}
|
111
|
+
|
112
|
+
},
|
113
|
+
|
114
|
+
/**
|
115
|
+
* Fire up all the feeds and pass them the right arugments.
|
116
|
+
* @private
|
117
|
+
*/
|
118
|
+
load = function() {
|
119
|
+
|
120
|
+
var i = 0, j = settings.list.length;
|
121
|
+
|
122
|
+
// We don't pass the list array to each feed because this will create
|
123
|
+
// a recursive JavaScript object
|
124
|
+
delete itemsettings.list;
|
125
|
+
|
126
|
+
// Run over all the items in the list
|
127
|
+
for( ; i < j; i++ ) {
|
128
|
+
|
129
|
+
var config = settings.list[i];
|
130
|
+
|
131
|
+
// Check whether the feed exists, if the feed is a function and if a
|
132
|
+
// user has been filled in
|
133
|
+
if ( $.fn.lifestream.feeds[config.service] &&
|
134
|
+
$.isFunction( $.fn.lifestream.feeds[config.service] )
|
135
|
+
&& config.user) {
|
136
|
+
|
137
|
+
// You'll be able to get the global settings by using
|
138
|
+
// config._settings in your feed
|
139
|
+
config._settings = itemsettings;
|
140
|
+
|
141
|
+
// Call the feed with a config object and finished callback
|
142
|
+
$.fn.lifestream.feeds[config.service]( config, finished );
|
143
|
+
}
|
144
|
+
|
145
|
+
}
|
146
|
+
|
147
|
+
};
|
148
|
+
|
149
|
+
// Load the jQuery templates plug-in if it wasn't included in the page.
|
150
|
+
// At then end we call the load method.
|
151
|
+
if( !jQuery.tmpl ) {
|
152
|
+
jQuery.getScript(
|
153
|
+
"https://raw.github.com/jquery/jquery-tmpl/master/"
|
154
|
+
+ "jquery.tmpl.min.js",
|
155
|
+
load);
|
156
|
+
} else {
|
157
|
+
load();
|
158
|
+
}
|
159
|
+
|
160
|
+
});
|
161
|
+
|
162
|
+
};
|
163
|
+
|
164
|
+
/**
|
165
|
+
* A big container which contains all available feeds
|
166
|
+
*/
|
167
|
+
$.fn.lifestream.feeds = $.fn.lifestream.feeds || {};
|
168
|
+
|
169
|
+
$.fn.lifestream.feeds.blogger = function( config, callback ) {
|
170
|
+
|
171
|
+
var template = $.extend({},
|
172
|
+
{
|
173
|
+
posted: 'posted <a href="${origLink}">${title}</a>'
|
174
|
+
},
|
175
|
+
config.template),
|
176
|
+
|
177
|
+
parseBlogger = function ( input ) {
|
178
|
+
var output = [], list, i = 0, j, item;
|
179
|
+
|
180
|
+
if ( input.query && input.query.count && input.query.count > 0
|
181
|
+
&& input.query.results.feed.entry ) {
|
182
|
+
list = input.query.results.feed.entry;
|
183
|
+
j = list.length;
|
184
|
+
for ( ; i < j; i++) {
|
185
|
+
item = list[i];
|
186
|
+
|
187
|
+
output.push({
|
188
|
+
date: new Date( item.published ),
|
189
|
+
config: config,
|
190
|
+
html: $.tmpl( template.posted, item )
|
191
|
+
});
|
192
|
+
}
|
193
|
+
}
|
194
|
+
|
195
|
+
return output;
|
196
|
+
};
|
197
|
+
|
198
|
+
$.ajax({
|
199
|
+
url: createYqlUrl('select * from xml where url="http://'
|
200
|
+
+ config.user + '.blogspot.com/feeds/posts/default"'),
|
201
|
+
dataType: "jsonp",
|
202
|
+
success: function ( data ) {
|
203
|
+
callback(parseBlogger(data));
|
204
|
+
}
|
205
|
+
});
|
206
|
+
|
207
|
+
// Expose the template.
|
208
|
+
// We use this to check which templates are available
|
209
|
+
return {
|
210
|
+
"template" : template
|
211
|
+
};
|
212
|
+
|
213
|
+
};
|
214
|
+
|
215
|
+
$.fn.lifestream.feeds.dailymotion = function( config, callback ) {
|
216
|
+
|
217
|
+
var template = $.extend({},
|
218
|
+
{
|
219
|
+
uploaded: 'uploaded a video <a href="${link}">${title[0]}</a>'
|
220
|
+
},
|
221
|
+
config.template),
|
222
|
+
|
223
|
+
parseDailymotion = function( input ) {
|
224
|
+
|
225
|
+
var output = [], list, i = 0, j, item;
|
226
|
+
|
227
|
+
if ( input.query && input.query.count && input.query.count > 0
|
228
|
+
&& input.query.results.rss.channel.item ) {
|
229
|
+
list = input.query.results.rss.channel.item;
|
230
|
+
j = list.length;
|
231
|
+
for ( ; i < j; i++) {
|
232
|
+
item = list[i];
|
233
|
+
output.push({
|
234
|
+
date: new Date ( item.pubDate ),
|
235
|
+
config: config,
|
236
|
+
html: $.tmpl( template.uploaded, item )
|
237
|
+
});
|
238
|
+
}
|
239
|
+
}
|
240
|
+
|
241
|
+
return output;
|
242
|
+
|
243
|
+
};
|
244
|
+
|
245
|
+
$.ajax({
|
246
|
+
url: createYqlUrl('select * from xml where '
|
247
|
+
+ 'url="http://www.dailymotion.com/rss/user/' + config.user + '"'),
|
248
|
+
dataType: "jsonp",
|
249
|
+
success: function( data ) {
|
250
|
+
callback(parseDailymotion(data));
|
251
|
+
}
|
252
|
+
});
|
253
|
+
|
254
|
+
// Expose the template.
|
255
|
+
// We use this to check which templates are available
|
256
|
+
return {
|
257
|
+
"template" : template
|
258
|
+
};
|
259
|
+
|
260
|
+
};
|
261
|
+
|
262
|
+
$.fn.lifestream.feeds.delicious = function( config, callback ) {
|
263
|
+
|
264
|
+
var template = $.extend({},
|
265
|
+
{
|
266
|
+
bookmarked: 'bookmarked <a href="${u}">${d}</a>'
|
267
|
+
},
|
268
|
+
config.template);
|
269
|
+
|
270
|
+
$.ajax({
|
271
|
+
url: "http://feeds.delicious.com/v2/json/" + config.user,
|
272
|
+
dataType: "jsonp",
|
273
|
+
success: function( data ) {
|
274
|
+
var output = [], i = 0, j;
|
275
|
+
if (data && data.length && data.length > 0) {
|
276
|
+
j = data.length;
|
277
|
+
for( ; i < j; i++) {
|
278
|
+
var item = data[i];
|
279
|
+
output.push({
|
280
|
+
date: new Date(item.dt),
|
281
|
+
config: config,
|
282
|
+
html: $.tmpl( template.bookmarked, item )
|
283
|
+
});
|
284
|
+
}
|
285
|
+
}
|
286
|
+
callback(output);
|
287
|
+
}
|
288
|
+
});
|
289
|
+
|
290
|
+
// Expose the template.
|
291
|
+
// We use this to check which templates are available
|
292
|
+
return {
|
293
|
+
"template" : template
|
294
|
+
};
|
295
|
+
|
296
|
+
};
|
297
|
+
|
298
|
+
$.fn.lifestream.feeds.deviantart = function( config, callback ) {
|
299
|
+
|
300
|
+
var template = $.extend({},
|
301
|
+
{
|
302
|
+
posted: 'posted <a href="${link}">${title}</a>'
|
303
|
+
},
|
304
|
+
config.template);
|
305
|
+
|
306
|
+
$.ajax({
|
307
|
+
url: createYqlUrl(
|
308
|
+
'select title,link,pubDate from rss where '
|
309
|
+
+ 'url="http://backend.deviantart.com/rss.xml?q=gallery%3A'
|
310
|
+
+ encodeURIComponent(config.user)
|
311
|
+
+ '&type=deviation'
|
312
|
+
+ '" | unique(field="title")'
|
313
|
+
),
|
314
|
+
dataType: 'jsonp',
|
315
|
+
success: function( resp ) {
|
316
|
+
var output = [],
|
317
|
+
items, item,
|
318
|
+
i = 0, j;
|
319
|
+
if (resp.query && resp.query.count > 0) {
|
320
|
+
items = resp.query.results.item;
|
321
|
+
j = items.length;
|
322
|
+
for ( ; i < j; i++) {
|
323
|
+
item = items[i];
|
324
|
+
output.push({
|
325
|
+
date: new Date(item.pubDate),
|
326
|
+
config: config,
|
327
|
+
html: $.tmpl( template.posted, item )
|
328
|
+
});
|
329
|
+
}
|
330
|
+
}
|
331
|
+
callback(output);
|
332
|
+
}
|
333
|
+
});
|
334
|
+
|
335
|
+
// Expose the template.
|
336
|
+
// We use this to check which templates are available
|
337
|
+
return {
|
338
|
+
"template" : template
|
339
|
+
};
|
340
|
+
|
341
|
+
};
|
342
|
+
|
343
|
+
$.fn.lifestream.feeds.dribbble = function( config, callback ) {
|
344
|
+
|
345
|
+
var template = $.extend({},
|
346
|
+
{
|
347
|
+
posted: 'posted a shot <a href="${url}">${title}</a>'
|
348
|
+
},
|
349
|
+
config.template);
|
350
|
+
|
351
|
+
$.ajax({
|
352
|
+
url: "http://api.dribbble.com/players/" + config.user + "/shots",
|
353
|
+
dataType: "jsonp",
|
354
|
+
success: function( data ) {
|
355
|
+
var output = [], i = 0, j;
|
356
|
+
|
357
|
+
if(data && data.total) {
|
358
|
+
j = data.shots.length;
|
359
|
+
for( ; i<j; i++) {
|
360
|
+
var item = data.shots[i];
|
361
|
+
output.push({
|
362
|
+
date: new Date(item.created_at),
|
363
|
+
config: config,
|
364
|
+
html: $.tmpl( template.posted, item )
|
365
|
+
});
|
366
|
+
}
|
367
|
+
}
|
368
|
+
|
369
|
+
callback(output);
|
370
|
+
}
|
371
|
+
});
|
372
|
+
|
373
|
+
// Expose the template.
|
374
|
+
// We use this to check which templates are available
|
375
|
+
return {
|
376
|
+
"template" : template
|
377
|
+
};
|
378
|
+
|
379
|
+
};
|
380
|
+
|
381
|
+
$.fn.lifestream.feeds.flickr = function( config, callback ) {
|
382
|
+
|
383
|
+
var template = $.extend({},
|
384
|
+
{
|
385
|
+
posted: 'posted a photo <a href="${link}">${title}</a>'
|
386
|
+
},
|
387
|
+
config.template);
|
388
|
+
|
389
|
+
$.ajax({
|
390
|
+
url: "http://api.flickr.com/services/feeds/photos_public.gne?id="
|
391
|
+
+ config.user + "&lang=en-us&format=json",
|
392
|
+
dataType: "jsonp",
|
393
|
+
jsonp: 'jsoncallback',
|
394
|
+
success: function( data ) {
|
395
|
+
var output = [], i = 0, j;
|
396
|
+
|
397
|
+
if(data && data.items && data.items.length > 0) {
|
398
|
+
j = data.items.length;
|
399
|
+
for( ; i<j; i++) {
|
400
|
+
var item = data.items[i];
|
401
|
+
output.push({
|
402
|
+
date: new Date( item.published ),
|
403
|
+
config: config,
|
404
|
+
html: $.tmpl( template.posted, item )
|
405
|
+
});
|
406
|
+
}
|
407
|
+
}
|
408
|
+
|
409
|
+
callback(output);
|
410
|
+
}
|
411
|
+
});
|
412
|
+
|
413
|
+
// Expose the template.
|
414
|
+
// We use this to check which templates are available
|
415
|
+
return {
|
416
|
+
"template" : template
|
417
|
+
};
|
418
|
+
|
419
|
+
};
|
420
|
+
|
421
|
+
$.fn.lifestream.feeds.foomark = function( config, callback ) {
|
422
|
+
|
423
|
+
var template = $.extend({},
|
424
|
+
|
425
|
+
{
|
426
|
+
bookmarked: 'bookmarked <a href="${url}">${url}</a>'
|
427
|
+
|
428
|
+
},
|
429
|
+
config.template);
|
430
|
+
|
431
|
+
$.ajax({
|
432
|
+
url: "http://api.foomark.com/urls/list/",
|
433
|
+
data: {
|
434
|
+
format: "jsonp",
|
435
|
+
username: config.user
|
436
|
+
},
|
437
|
+
dataType: "jsonp",
|
438
|
+
success: function( data ) {
|
439
|
+
|
440
|
+
var output = [], i=0, j;
|
441
|
+
if( data && data.length && data.length > 0 ) {
|
442
|
+
j = data.length;
|
443
|
+
for( ; i < j; i++ ) {
|
444
|
+
var item = data[i];
|
445
|
+
output.push({
|
446
|
+
date: new Date( item.created_at.replace(' ', 'T') ),
|
447
|
+
config: config,
|
448
|
+
html: $.tmpl( template.bookmarked, item )
|
449
|
+
});
|
450
|
+
}
|
451
|
+
}
|
452
|
+
callback( output );
|
453
|
+
}
|
454
|
+
});
|
455
|
+
|
456
|
+
// Expose the template.
|
457
|
+
// We use this to check which templates are available
|
458
|
+
return {
|
459
|
+
"template" : template
|
460
|
+
};
|
461
|
+
|
462
|
+
};
|
463
|
+
|
464
|
+
$.fn.lifestream.feeds.formspring = function( config, callback ) {
|
465
|
+
|
466
|
+
var template = $.extend({},
|
467
|
+
{
|
468
|
+
answered: 'answered a question <a href="${link}">${title}</a>'
|
469
|
+
},
|
470
|
+
config.template);
|
471
|
+
|
472
|
+
var parseFormspring = function ( input ) {
|
473
|
+
var output = [], list, i = 0, j, item;
|
474
|
+
|
475
|
+
if ( input.query && input.query.count && input.query.count > 0
|
476
|
+
&& input.query.results.rss.channel.item ) {
|
477
|
+
list = input.query.results.rss.channel.item;
|
478
|
+
j = list.length;
|
479
|
+
for ( ; i < j; i++) {
|
480
|
+
item = list[i];
|
481
|
+
|
482
|
+
output.push({
|
483
|
+
date: new Date( item.pubDate ),
|
484
|
+
config: config,
|
485
|
+
html: $.tmpl( template.answered, item )
|
486
|
+
});
|
487
|
+
}
|
488
|
+
}
|
489
|
+
|
490
|
+
return output;
|
491
|
+
};
|
492
|
+
|
493
|
+
$.ajax({
|
494
|
+
url: createYqlUrl('select * from xml where '
|
495
|
+
+ 'url="http://www.formspring.me/profile/' + config.user + '.rss"'),
|
496
|
+
dataType: "jsonp",
|
497
|
+
success: function ( data ) {
|
498
|
+
callback(parseFormspring(data));
|
499
|
+
}
|
500
|
+
});
|
501
|
+
|
502
|
+
// Expose the template.
|
503
|
+
// We use this to check which templates are available
|
504
|
+
return {
|
505
|
+
"template" : template
|
506
|
+
};
|
507
|
+
|
508
|
+
};
|
509
|
+
|
510
|
+
$.fn.lifestream.feeds.forrst = function( config, callback ) {
|
511
|
+
|
512
|
+
var template = $.extend({},
|
513
|
+
{
|
514
|
+
posted: 'posted a ${post_type} '
|
515
|
+
+ '<a href="${post_url}">${title}</a>'
|
516
|
+
},
|
517
|
+
config.template);
|
518
|
+
|
519
|
+
$.ajax({
|
520
|
+
url: "http://forrst.com/api/v2/users/posts?username=" + config.user,
|
521
|
+
dataType: "jsonp",
|
522
|
+
success: function( data ) {
|
523
|
+
var output = [], i=0, j;
|
524
|
+
if( data && data.resp.length && data.resp.length > 0 ) {
|
525
|
+
j = data.resp.length;
|
526
|
+
for( ; i < j; i++ ) {
|
527
|
+
var item = data.resp[i];
|
528
|
+
output.push({
|
529
|
+
date: new Date( item.created_at.replace(' ', 'T') ),
|
530
|
+
config: config,
|
531
|
+
html: $.tmpl( template.posted, item )
|
532
|
+
});
|
533
|
+
}
|
534
|
+
}
|
535
|
+
callback( output );
|
536
|
+
}
|
537
|
+
});
|
538
|
+
|
539
|
+
// Expose the template.
|
540
|
+
// We use this to check which templates are available
|
541
|
+
return {
|
542
|
+
"template" : template
|
543
|
+
};
|
544
|
+
|
545
|
+
};
|
546
|
+
|
547
|
+
$.fn.lifestream.feeds.foursquare = function( config, callback ) {
|
548
|
+
|
549
|
+
var template = $.extend({},
|
550
|
+
{
|
551
|
+
checkedin: 'checked in @ <a href="${link}">${title}</a>'
|
552
|
+
},
|
553
|
+
config.template),
|
554
|
+
|
555
|
+
parseFoursquare = function( input ) {
|
556
|
+
var output = [], i = 0, j;
|
557
|
+
|
558
|
+
if(input.query && input.query.count && input.query.count >0) {
|
559
|
+
j = input.query.count;
|
560
|
+
for( ; i<j; i++) {
|
561
|
+
var item = input.query.results.item[i];
|
562
|
+
output.push({
|
563
|
+
date: new Date(item.pubDate),
|
564
|
+
config: config,
|
565
|
+
html: $.tmpl( template.checkedin, item )
|
566
|
+
});
|
567
|
+
}
|
568
|
+
}
|
569
|
+
|
570
|
+
return output;
|
571
|
+
};
|
572
|
+
|
573
|
+
$.ajax({
|
574
|
+
url: createYqlUrl('select * from rss where url='
|
575
|
+
+ '"https://feeds.foursquare.com/history/'
|
576
|
+
+ config.user + '.rss"'),
|
577
|
+
dataType: 'jsonp',
|
578
|
+
success: function( data ) {
|
579
|
+
callback(parseFoursquare(data));
|
580
|
+
}
|
581
|
+
});
|
582
|
+
|
583
|
+
// Expose the template.
|
584
|
+
// We use this to check which templates are available
|
585
|
+
return {
|
586
|
+
"template" : template
|
587
|
+
};
|
588
|
+
|
589
|
+
};
|
590
|
+
|
591
|
+
$.fn.lifestream.feeds.github = function( config, callback ) {
|
592
|
+
|
593
|
+
var template = $.extend({},
|
594
|
+
{
|
595
|
+
pushed: '<a href="${status.url}" title="{{if title}}${title} '
|
596
|
+
+'by ${author} {{/if}}">pushed</a> to '
|
597
|
+
+'<a href="http://github.com/${repo}">${repo}</a>',
|
598
|
+
gist: '<a href="${status.payload.url}" title="'
|
599
|
+
+'${status.payload.desc || ""}">${status.payload.name}</a>',
|
600
|
+
commented: '<a href="${status.url}">commented</a> on '
|
601
|
+
+'<a href="http://github.com/${repo}">${repo}</a>',
|
602
|
+
pullrequest: '<a href="${status.url}">${status.payload.action}</a> '
|
603
|
+
+'pull request on <a href="http://github.com/${repo}">${repo}</a>',
|
604
|
+
created: 'created ${status.payload.ref_type || status.payload.object}'
|
605
|
+
+' <a href="${status.url}">${status.payload.ref || '
|
606
|
+
+'status.payload.object_name}</a> for '
|
607
|
+
+'<a href="http://github.com/${repo}">${repo}</a>',
|
608
|
+
createdglobal: 'created ${status.payload.object} '
|
609
|
+
+'<a href="${status.url}">${title}</a>',
|
610
|
+
deleted: 'deleted ${status.payload.ref_type} '
|
611
|
+
+'<a href="http://github.com/${status.repository.owner}/'
|
612
|
+
+'${status.repository.name}">status.payload.ref</a>'
|
613
|
+
},
|
614
|
+
config.template);
|
615
|
+
|
616
|
+
var returnRepo = function( status ) {
|
617
|
+
return status.payload.repo
|
618
|
+
|| ( status.repository ? status.repository.owner + "/"
|
619
|
+
+ status.repository.name : null )
|
620
|
+
|| status.url.split("/")[3] + "/" + status.url.split("/")[4];
|
621
|
+
},
|
622
|
+
parseGithubStatus = function( status ) {
|
623
|
+
var repo, title;
|
624
|
+
if(status.type === "PushEvent") {
|
625
|
+
title = status.payload && status.payload.shas
|
626
|
+
&& status.payload.shas.json
|
627
|
+
&& status.payload.shas.json[2];
|
628
|
+
repo = returnRepo(status);
|
629
|
+
|
630
|
+
return $.tmpl( template.pushed, {
|
631
|
+
status: status,
|
632
|
+
title: title,
|
633
|
+
author: title ? status.payload.shas.json[3] : "",
|
634
|
+
repo: returnRepo(status)
|
635
|
+
} );
|
636
|
+
}
|
637
|
+
else if (status.type === "GistEvent") {
|
638
|
+
return $.tmpl( template.gist, status );
|
639
|
+
}
|
640
|
+
else if (status.type === "CommitCommentEvent" ||
|
641
|
+
status.type === "IssueCommentEvent") {
|
642
|
+
repo = returnRepo(status);
|
643
|
+
return $.tmpl( template.commented, {
|
644
|
+
repo: repo,
|
645
|
+
status: status
|
646
|
+
} );
|
647
|
+
}
|
648
|
+
else if (status.type === "PullRequestEvent") {
|
649
|
+
repo = returnRepo(status);
|
650
|
+
return $.tmpl( template.pullrequest, {
|
651
|
+
repo: repo,
|
652
|
+
status: status
|
653
|
+
} );
|
654
|
+
}
|
655
|
+
// Github has several syntaxes for create tag events
|
656
|
+
else if (status.type === "CreateEvent" &&
|
657
|
+
(status.payload.ref_type === "tag" ||
|
658
|
+
status.payload.ref_type === "branch" ||
|
659
|
+
status.payload.object === "tag")) {
|
660
|
+
repo = returnRepo(status);
|
661
|
+
return $.tmpl( template.created, {
|
662
|
+
repo: repo,
|
663
|
+
status: status
|
664
|
+
} );
|
665
|
+
}
|
666
|
+
else if (status.type === "CreateEvent") {
|
667
|
+
title = (status.payload.object_name === "null")
|
668
|
+
? status.payload.name
|
669
|
+
: status.payload.object_name;
|
670
|
+
return $.tmpl( template.createdglobal, {
|
671
|
+
title: title,
|
672
|
+
status: status
|
673
|
+
} );
|
674
|
+
}
|
675
|
+
else if (status.type === "DeleteEvent") {
|
676
|
+
return $.tmpl( template.deleted, status );
|
677
|
+
}
|
678
|
+
|
679
|
+
},
|
680
|
+
parseGithub = function( input ) {
|
681
|
+
var output = [], i = 0, j;
|
682
|
+
|
683
|
+
if(input.query && input.query.count && input.query.count >0) {
|
684
|
+
j = input.query.count;
|
685
|
+
for( ; i<j; i++) {
|
686
|
+
var status = input.query.results.json[i].json;
|
687
|
+
output.push({
|
688
|
+
date: new Date(status.created_at),
|
689
|
+
config: config,
|
690
|
+
html: parseGithubStatus(status)
|
691
|
+
});
|
692
|
+
}
|
693
|
+
}
|
694
|
+
|
695
|
+
return output;
|
696
|
+
|
697
|
+
};
|
698
|
+
|
699
|
+
$.ajax({
|
700
|
+
url: createYqlUrl('select json.repository.owner,json.repository.name'
|
701
|
+
+ ',json.payload,json.type'
|
702
|
+
+ ',json.url, json.created_at from json where url="http://github.com/'
|
703
|
+
+ config.user + '.json"'),
|
704
|
+
dataType: 'jsonp',
|
705
|
+
success: function( data ) {
|
706
|
+
callback(parseGithub(data));
|
707
|
+
}
|
708
|
+
});
|
709
|
+
|
710
|
+
// Expose the template.
|
711
|
+
// We use this to check which templates are available
|
712
|
+
return {
|
713
|
+
"template" : template
|
714
|
+
};
|
715
|
+
|
716
|
+
};
|
717
|
+
|
718
|
+
$.fn.lifestream.feeds.googlereader = function( config, callback ) {
|
719
|
+
|
720
|
+
var template = $.extend({},
|
721
|
+
{
|
722
|
+
starred: 'starred post <a href="${link.href}">${title.content}</a>'
|
723
|
+
},
|
724
|
+
config.template),
|
725
|
+
|
726
|
+
/**
|
727
|
+
* Parse the input from google reader
|
728
|
+
*/
|
729
|
+
parseReader = function( input ) {
|
730
|
+
var output = [], list, i = 0, j;
|
731
|
+
|
732
|
+
if(input.query && input.query.count && input.query.count >0) {
|
733
|
+
list = input.query.results.feed.entry;
|
734
|
+
j = list.length;
|
735
|
+
for( ; i<j; i++) {
|
736
|
+
var item = list[i];
|
737
|
+
output.push({
|
738
|
+
date: new Date(parseInt(item["crawl-timestamp-msec"], 10)),
|
739
|
+
config: config,
|
740
|
+
html: $.tmpl( template.starred, item )
|
741
|
+
});
|
742
|
+
}
|
743
|
+
}
|
744
|
+
return output;
|
745
|
+
};
|
746
|
+
|
747
|
+
$.ajax({
|
748
|
+
url: createYqlUrl('select * from xml where url="'
|
749
|
+
+ 'www.google.com/reader/public/atom/user%2F'
|
750
|
+
+ config.user + '%2Fstate%2Fcom.google%2Fstarred"'),
|
751
|
+
dataType: 'jsonp',
|
752
|
+
success: function( data ) {
|
753
|
+
callback(parseReader(data));
|
754
|
+
}
|
755
|
+
});
|
756
|
+
|
757
|
+
// Expose the template.
|
758
|
+
// We use this to check which templates are available
|
759
|
+
return {
|
760
|
+
"template" : template
|
761
|
+
};
|
762
|
+
|
763
|
+
};
|
764
|
+
|
765
|
+
$.fn.lifestream.feeds.iusethis = function( config, callback ) {
|
766
|
+
|
767
|
+
var template = $.extend({},
|
768
|
+
{
|
769
|
+
global: '${action} <a href="${link}">${what}</a> on (${os})'
|
770
|
+
},
|
771
|
+
config.template);
|
772
|
+
|
773
|
+
var parseIusethis = function( input ) {
|
774
|
+
var output = [], list, i, j, k, l, m = 0, n, item, title, actions,
|
775
|
+
action, what, os, oss = ["iPhone", "OS X", "Windows"];
|
776
|
+
|
777
|
+
if (input.query && input.query.count && input.query.count > 0
|
778
|
+
&& input.query.results.rss) {
|
779
|
+
n = input.query.results.rss.length;
|
780
|
+
actions = ['started using', 'stopped using', 'stopped loving',
|
781
|
+
'Downloaded', 'commented on', 'updated entry for',
|
782
|
+
'started loving', 'registered'];
|
783
|
+
l = actions.length;
|
784
|
+
|
785
|
+
for( ; m < n; m++) {
|
786
|
+
|
787
|
+
os = oss[m];
|
788
|
+
list = input.query.results.rss[m].channel.item;
|
789
|
+
i = 0;
|
790
|
+
j = list.length;
|
791
|
+
|
792
|
+
for ( ; i < j; i++) {
|
793
|
+
item = list[i];
|
794
|
+
title = item.title.replace(config.user + ' ', '');
|
795
|
+
k = 0;
|
796
|
+
|
797
|
+
for( ; k < l; k++) {
|
798
|
+
if(title.indexOf(actions[k]) > -1) {
|
799
|
+
action = actions[k];
|
800
|
+
break;
|
801
|
+
}
|
802
|
+
}
|
803
|
+
|
804
|
+
what = title.split(action);
|
805
|
+
|
806
|
+
output.push({
|
807
|
+
date: new Date(item.pubDate),
|
808
|
+
config: config,
|
809
|
+
html: $.tmpl( template.global, {
|
810
|
+
action: action.toLowerCase(),
|
811
|
+
link: item.link,
|
812
|
+
what: what[1],
|
813
|
+
os: os
|
814
|
+
} )
|
815
|
+
});
|
816
|
+
}
|
817
|
+
}
|
818
|
+
}
|
819
|
+
|
820
|
+
return output;
|
821
|
+
};
|
822
|
+
|
823
|
+
$.ajax({
|
824
|
+
url: createYqlUrl('select * from xml where '
|
825
|
+
+ 'url="http://iphone.iusethis.com/user/feed.rss/' + config.user
|
826
|
+
+ '" or '
|
827
|
+
+ 'url="http://osx.iusethis.com/user/feed.rss/' + config.user
|
828
|
+
+ '" or '
|
829
|
+
+ 'url="http://win.iusethis.com/user/feed.rss/' + config.user + '"'),
|
830
|
+
dataType: "jsonp",
|
831
|
+
success: function( data ) {
|
832
|
+
callback(parseIusethis(data));
|
833
|
+
}
|
834
|
+
});
|
835
|
+
|
836
|
+
// Expose the template.
|
837
|
+
// We use this to check which templates are available
|
838
|
+
return {
|
839
|
+
"template" : template
|
840
|
+
};
|
841
|
+
|
842
|
+
};
|
843
|
+
|
844
|
+
$.fn.lifestream.feeds.lastfm = function( config, callback ) {
|
845
|
+
|
846
|
+
var template = $.extend({},
|
847
|
+
{
|
848
|
+
loved: 'loved <a href="${url}">${name}</a> by '
|
849
|
+
+ '<a href="${artist.url}">${artist.name}</a>'
|
850
|
+
},
|
851
|
+
config.template),
|
852
|
+
|
853
|
+
parseLastfm = function( input ) {
|
854
|
+
var output = [], list, i = 0, j;
|
855
|
+
|
856
|
+
if(input.query && input.query.count && input.query.count > 0
|
857
|
+
&& input.query.results.lovedtracks
|
858
|
+
&& input.query.results.lovedtracks.track) {
|
859
|
+
list = input.query.results.lovedtracks.track;
|
860
|
+
j = list.length;
|
861
|
+
for( ; i<j; i++) {
|
862
|
+
var item = list[i];
|
863
|
+
output.push({
|
864
|
+
date: new Date(parseInt((item.date.uts * 1000), 10)),
|
865
|
+
config: config,
|
866
|
+
html: $.tmpl( template.loved, item )
|
867
|
+
});
|
868
|
+
}
|
869
|
+
}
|
870
|
+
return output;
|
871
|
+
};
|
872
|
+
|
873
|
+
$.ajax({
|
874
|
+
url: createYqlUrl('select * from xml where url='
|
875
|
+
+ '"http://ws.audioscrobbler.com/2.0/user/'
|
876
|
+
+ config.user + '/lovedtracks.xml"'),
|
877
|
+
dataType: 'jsonp',
|
878
|
+
success: function( data ) {
|
879
|
+
callback(parseLastfm(data));
|
880
|
+
}
|
881
|
+
});
|
882
|
+
|
883
|
+
// Expose the template.
|
884
|
+
// We use this to check which templates are available
|
885
|
+
return {
|
886
|
+
"template" : template
|
887
|
+
};
|
888
|
+
|
889
|
+
};
|
890
|
+
|
891
|
+
$.fn.lifestream.feeds.picplz = function( config, callback ) {
|
892
|
+
|
893
|
+
var template = $.extend({},
|
894
|
+
{
|
895
|
+
uploaded: 'uploaded <a href="${url}">${title}</a>'
|
896
|
+
},
|
897
|
+
config.template);
|
898
|
+
|
899
|
+
$.ajax({
|
900
|
+
url: "http://picplz.com/api/v2/user.json?username="
|
901
|
+
+ config.user + "&include_pics=1",
|
902
|
+
dataType: "jsonp",
|
903
|
+
success: function( data ) {
|
904
|
+
var output = [], i=0, j, images;
|
905
|
+
images = data.value.users[0].pics;
|
906
|
+
if( images && images.length && images.length > 0 ) {
|
907
|
+
j = images.length;
|
908
|
+
for( ; i < j; i++ ) {
|
909
|
+
var item = images[i];
|
910
|
+
output.push({
|
911
|
+
date: new Date( ( item.date ) * 1000 ),
|
912
|
+
config: config,
|
913
|
+
html: $.tmpl( template.uploaded, {
|
914
|
+
url: item.pic_files["640r"].img_url,
|
915
|
+
title: item.caption || item.id
|
916
|
+
} )
|
917
|
+
});
|
918
|
+
}
|
919
|
+
}
|
920
|
+
callback( output );
|
921
|
+
}
|
922
|
+
});
|
923
|
+
|
924
|
+
// Expose the template.
|
925
|
+
// We use this to check which templates are available
|
926
|
+
return {
|
927
|
+
"template" : template
|
928
|
+
};
|
929
|
+
|
930
|
+
};
|
931
|
+
|
932
|
+
$.fn.lifestream.feeds.pinboard = function( config, callback ) {
|
933
|
+
|
934
|
+
var template = $.extend({},
|
935
|
+
{
|
936
|
+
bookmarked: 'bookmarked <a href="${link}">${title}</a>'
|
937
|
+
},
|
938
|
+
config.template);
|
939
|
+
|
940
|
+
var parsePinboard = function( input ) {
|
941
|
+
var output = [], list, i = 0, j, item;
|
942
|
+
|
943
|
+
if (input.query && input.query.count && input.query.count > 0) {
|
944
|
+
list = input.query.results.RDF.item;
|
945
|
+
j = list.length;
|
946
|
+
for ( ; i < j; i++) {
|
947
|
+
item = list[i];
|
948
|
+
|
949
|
+
output.push({
|
950
|
+
date: new Date(item.date),
|
951
|
+
config: config,
|
952
|
+
html: $.tmpl( template.bookmarked, item )
|
953
|
+
});
|
954
|
+
|
955
|
+
}
|
956
|
+
}
|
957
|
+
|
958
|
+
return output;
|
959
|
+
};
|
960
|
+
|
961
|
+
$.ajax({
|
962
|
+
url: createYqlUrl('select * from xml where '
|
963
|
+
+ 'url="http://feeds.pinboard.in/rss/u:' + config.user + '"'),
|
964
|
+
dataType: "jsonp",
|
965
|
+
success: function( data ) {
|
966
|
+
callback(parsePinboard(data));
|
967
|
+
}
|
968
|
+
});
|
969
|
+
|
970
|
+
// Expose the template.
|
971
|
+
// We use this to check which templates are available
|
972
|
+
return {
|
973
|
+
"template" : template
|
974
|
+
};
|
975
|
+
|
976
|
+
};
|
977
|
+
|
978
|
+
$.fn.lifestream.feeds.posterous = function( config, callback ) {
|
979
|
+
|
980
|
+
var template = $.extend({},
|
981
|
+
{
|
982
|
+
posted: 'posted <a href="${link}">${title}</a>'
|
983
|
+
},
|
984
|
+
config.template);
|
985
|
+
|
986
|
+
var parsePosterous = function ( input ) {
|
987
|
+
var output = [], list, i = 0, j, item;
|
988
|
+
|
989
|
+
if ( input.query && input.query.count && input.query.count > 0
|
990
|
+
&& input.query.results.rss.channel.item ) {
|
991
|
+
list = input.query.results.rss.channel.item;
|
992
|
+
j = list.length;
|
993
|
+
for ( ; i < j; i++) {
|
994
|
+
item = list[i];
|
995
|
+
|
996
|
+
output.push({
|
997
|
+
date: new Date( item.pubDate ),
|
998
|
+
config: config,
|
999
|
+
html: $.tmpl( template.posted, item )
|
1000
|
+
});
|
1001
|
+
}
|
1002
|
+
}
|
1003
|
+
|
1004
|
+
return output;
|
1005
|
+
};
|
1006
|
+
|
1007
|
+
$.ajax({
|
1008
|
+
url: createYqlUrl('select * from xml where '
|
1009
|
+
+ 'url="http://' + config.user + '.posterous.com/rss.xml"'),
|
1010
|
+
dataType: "jsonp",
|
1011
|
+
success: function ( data ) {
|
1012
|
+
callback(parsePosterous(data));
|
1013
|
+
}
|
1014
|
+
});
|
1015
|
+
|
1016
|
+
// Expose the template.
|
1017
|
+
// We use this to check which templates are available
|
1018
|
+
return {
|
1019
|
+
"template" : template
|
1020
|
+
};
|
1021
|
+
|
1022
|
+
};
|
1023
|
+
|
1024
|
+
$.fn.lifestream.feeds.reddit = function( config, callback ) {
|
1025
|
+
|
1026
|
+
var template = $.extend({},
|
1027
|
+
{
|
1028
|
+
commented: '<a href="http://www.reddit.com/r/${item.data.subreddit}'
|
1029
|
+
+ '/comments/${item.data.link_id.substring(3)}/u/'
|
1030
|
+
+ '${item.data.name.substring(3)}?context=3">commented '
|
1031
|
+
+ '(${score})</a> in <a href="http://www.reddit.com/r/'
|
1032
|
+
+ '${item.data.subreddit}">${item.data.subreddit}</a>',
|
1033
|
+
created: '<a href="http://www.reddit.com${item.data.permalink}">'
|
1034
|
+
+ 'created new thread (${score})</a> in '
|
1035
|
+
+ '<a href="http://www.reddit.com/r/${item.data.subreddit}">'
|
1036
|
+
+ '${item.data.subreddit}</a>'
|
1037
|
+
},
|
1038
|
+
config.template);
|
1039
|
+
|
1040
|
+
/**
|
1041
|
+
* Parsed one item from the Reddit API.
|
1042
|
+
* item.kind == t1 is a reply, t2 is a new thread
|
1043
|
+
*/
|
1044
|
+
var parseRedditItem = function( item ) {
|
1045
|
+
|
1046
|
+
var score = item.data.ups - item.data.downs,
|
1047
|
+
pass = {
|
1048
|
+
item: item,
|
1049
|
+
score: (score > 0) ? "+" + score : score
|
1050
|
+
};
|
1051
|
+
|
1052
|
+
// t1 = reply, t3 = new thread
|
1053
|
+
if (item.kind === "t1") {
|
1054
|
+
return $.tmpl( template.commented, pass );
|
1055
|
+
}
|
1056
|
+
else if (item.kind === "t3") {
|
1057
|
+
return $.tmpl( template.created, pass );
|
1058
|
+
}
|
1059
|
+
|
1060
|
+
},
|
1061
|
+
/**
|
1062
|
+
* Reddit date's are simple epochs.
|
1063
|
+
* seconds*1000 = milliseconds
|
1064
|
+
*/
|
1065
|
+
convertDate = function( date ) {
|
1066
|
+
return new Date(date * 1000);
|
1067
|
+
};
|
1068
|
+
|
1069
|
+
$.ajax({
|
1070
|
+
url: "http://www.reddit.com/user/" + config.user + ".json",
|
1071
|
+
dataType: "jsonp",
|
1072
|
+
jsonp:"jsonp",
|
1073
|
+
success: function( data ) {
|
1074
|
+
var output = [], i = 0, j;
|
1075
|
+
|
1076
|
+
if(data && data.data && data.data.children
|
1077
|
+
&& data.data.children.length > 0) {
|
1078
|
+
j = data.data.children.length;
|
1079
|
+
for( ; i<j; i++) {
|
1080
|
+
var item = data.data.children[i];
|
1081
|
+
output.push({
|
1082
|
+
date: convertDate(item.data.created),
|
1083
|
+
config: config,
|
1084
|
+
html: parseRedditItem(item)
|
1085
|
+
});
|
1086
|
+
}
|
1087
|
+
}
|
1088
|
+
|
1089
|
+
callback(output);
|
1090
|
+
}
|
1091
|
+
});
|
1092
|
+
|
1093
|
+
// Expose the template.
|
1094
|
+
// We use this to check which templates are available
|
1095
|
+
return {
|
1096
|
+
"template" : template
|
1097
|
+
};
|
1098
|
+
|
1099
|
+
};
|
1100
|
+
|
1101
|
+
$.fn.lifestream.feeds.slideshare = function( config, callback ) {
|
1102
|
+
|
1103
|
+
var template = $.extend({},
|
1104
|
+
{
|
1105
|
+
uploaded: 'uploaded a presentation <a href="${link}">${title}</a>'
|
1106
|
+
},
|
1107
|
+
config.template);
|
1108
|
+
|
1109
|
+
var parseSlideshare = function( input ) {
|
1110
|
+
var output = [], list, i = 0, j, item;
|
1111
|
+
|
1112
|
+
if (input.query && input.query.count && input.query.count > 0) {
|
1113
|
+
list = input.query.results.rss.channel.item;
|
1114
|
+
j = list.length;
|
1115
|
+
for ( ; i < j; i++) {
|
1116
|
+
item = list[i];
|
1117
|
+
|
1118
|
+
output.push({
|
1119
|
+
date: new Date(item.pubDate),
|
1120
|
+
config: config,
|
1121
|
+
html: $.tmpl( template.uploaded, item )
|
1122
|
+
});
|
1123
|
+
|
1124
|
+
}
|
1125
|
+
}
|
1126
|
+
|
1127
|
+
return output;
|
1128
|
+
};
|
1129
|
+
|
1130
|
+
$.ajax({
|
1131
|
+
url: createYqlUrl('select * from xml where '
|
1132
|
+
+ 'url="http://www.slideshare.net/rss/user/' + config.user + '"'),
|
1133
|
+
dataType: "jsonp",
|
1134
|
+
success: function( data ) {
|
1135
|
+
callback(parseSlideshare(data));
|
1136
|
+
}
|
1137
|
+
});
|
1138
|
+
|
1139
|
+
// Expose the template.
|
1140
|
+
// We use this to check which templates are available
|
1141
|
+
return {
|
1142
|
+
"template" : template
|
1143
|
+
};
|
1144
|
+
|
1145
|
+
};
|
1146
|
+
|
1147
|
+
$.fn.lifestream.feeds.stackoverflow = function( config, callback ) {
|
1148
|
+
|
1149
|
+
var template = $.extend({},
|
1150
|
+
{
|
1151
|
+
global: '<a href="${link}">${text}</a> - ${title}'
|
1152
|
+
},
|
1153
|
+
config.template);
|
1154
|
+
|
1155
|
+
var parseStackoverflowItem = function( item ) {
|
1156
|
+
var text="", title="", link="",
|
1157
|
+
stackoverflow_link = "http://stackoverflow.com/users/" + config.user,
|
1158
|
+
question_link = "http://stackoverflow.com/questions/";
|
1159
|
+
|
1160
|
+
if(item.timeline_type === "badge") {
|
1161
|
+
text = item.timeline_type + " " + item.action + ": "
|
1162
|
+
+ item.description;
|
1163
|
+
title = item.detail;
|
1164
|
+
link = stackoverflow_link + "?tab=reputation";
|
1165
|
+
}
|
1166
|
+
else if (item.timeline_type === "revision"
|
1167
|
+
|| item.timeline_type === "comment"
|
1168
|
+
|| item.timeline_type === "accepted"
|
1169
|
+
|| item.timeline_type === "askoranswered") {
|
1170
|
+
text = item.post_type + " " + item.action;
|
1171
|
+
title = item.detail || item.description || "";
|
1172
|
+
link = question_link + item.post_id;
|
1173
|
+
}
|
1174
|
+
return {
|
1175
|
+
link: link,
|
1176
|
+
title: title,
|
1177
|
+
text: text
|
1178
|
+
};
|
1179
|
+
},
|
1180
|
+
convertDate = function( date ) {
|
1181
|
+
return new Date(date * 1000);
|
1182
|
+
};
|
1183
|
+
|
1184
|
+
$.ajax({
|
1185
|
+
url: "http://api.stackoverflow.com/1.1/users/" + config.user
|
1186
|
+
+ "/timeline?"
|
1187
|
+
+ "jsonp",
|
1188
|
+
dataType: "jsonp",
|
1189
|
+
jsonp: 'jsonp',
|
1190
|
+
success: function( data ) {
|
1191
|
+
var output = [], i = 0, j;
|
1192
|
+
|
1193
|
+
if(data && data.total && data.total > 0 && data.user_timelines) {
|
1194
|
+
j = data.user_timelines.length;
|
1195
|
+
for( ; i<j; i++) {
|
1196
|
+
var item = data.user_timelines[i];
|
1197
|
+
output.push({
|
1198
|
+
date: convertDate(item.creation_date),
|
1199
|
+
config: config,
|
1200
|
+
html: $.tmpl( template.global, parseStackoverflowItem(item) )
|
1201
|
+
});
|
1202
|
+
}
|
1203
|
+
}
|
1204
|
+
|
1205
|
+
callback(output);
|
1206
|
+
}
|
1207
|
+
});
|
1208
|
+
|
1209
|
+
// Expose the template.
|
1210
|
+
// We use this to check which templates are available
|
1211
|
+
return {
|
1212
|
+
"template" : template
|
1213
|
+
};
|
1214
|
+
|
1215
|
+
};
|
1216
|
+
|
1217
|
+
$.fn.lifestream.feeds.tumblr = function( config, callback ) {
|
1218
|
+
|
1219
|
+
var template = $.extend({},
|
1220
|
+
{
|
1221
|
+
posted: 'posted a ${type} <a href="${url}">${title}</a>'
|
1222
|
+
},
|
1223
|
+
config.template),
|
1224
|
+
|
1225
|
+
/**
|
1226
|
+
* get title text
|
1227
|
+
*/
|
1228
|
+
getTitle = function( post ) {
|
1229
|
+
var title = post["regular-title"]
|
1230
|
+
|| post["quote-text"]
|
1231
|
+
|| post["conversation-title"]
|
1232
|
+
|| post["photo-caption"]
|
1233
|
+
|| post["video-caption"]
|
1234
|
+
|| post["audio-caption"]
|
1235
|
+
|| post["regular-body"]
|
1236
|
+
|| post["link-text"]
|
1237
|
+
|| post.type
|
1238
|
+
|| "";
|
1239
|
+
|
1240
|
+
// remove tags
|
1241
|
+
return title.replace( /<.+?>/gi, " ");
|
1242
|
+
},
|
1243
|
+
createTumblrOutput = function( config, post ) {
|
1244
|
+
return {
|
1245
|
+
date: new Date(post.date),
|
1246
|
+
config: config,
|
1247
|
+
html: $.tmpl( template.posted, {
|
1248
|
+
type: post.type,
|
1249
|
+
url: post.url,
|
1250
|
+
title: getTitle(post)
|
1251
|
+
} )
|
1252
|
+
};
|
1253
|
+
},
|
1254
|
+
parseTumblr = function( input ) {
|
1255
|
+
var output = [], i = 0, j, post;
|
1256
|
+
if(input.query && input.query.count && input.query.count > 0) {
|
1257
|
+
// If a user only has one post, post is a plain object, otherwise it
|
1258
|
+
// is an array
|
1259
|
+
if ( $.isArray(input.query.results.posts.post) ) {
|
1260
|
+
j = input.query.results.posts.post.length;
|
1261
|
+
for( ; i < j; i++) {
|
1262
|
+
post = input.query.results.posts.post[i];
|
1263
|
+
output.push(createTumblrOutput(config, post));
|
1264
|
+
}
|
1265
|
+
}
|
1266
|
+
else if ( $.isPlainObject(input.query.results.posts.post) ) {
|
1267
|
+
output.push(createTumblrOutput(config,input.query.results.posts.post));
|
1268
|
+
}
|
1269
|
+
}
|
1270
|
+
return output;
|
1271
|
+
};
|
1272
|
+
|
1273
|
+
$.ajax({
|
1274
|
+
url: createYqlUrl('select *'
|
1275
|
+
+ ' from tumblr.posts where username="'+ config.user +'"'),
|
1276
|
+
dataType: 'jsonp',
|
1277
|
+
success: function( data ) {
|
1278
|
+
callback(parseTumblr(data));
|
1279
|
+
}
|
1280
|
+
});
|
1281
|
+
|
1282
|
+
// Expose the template.
|
1283
|
+
// We use this to check which templates are available
|
1284
|
+
return {
|
1285
|
+
"template" : template
|
1286
|
+
};
|
1287
|
+
|
1288
|
+
};
|
1289
|
+
|
1290
|
+
$.fn.lifestream.feeds.twitter = function( config, callback ) {
|
1291
|
+
|
1292
|
+
var template = $.extend({},
|
1293
|
+
{
|
1294
|
+
posted: '{{html tweet}}'
|
1295
|
+
},
|
1296
|
+
config.template),
|
1297
|
+
|
1298
|
+
/**
|
1299
|
+
* Add links to the twitter feed.
|
1300
|
+
* Hashes, @ and regular links are supported.
|
1301
|
+
* @private
|
1302
|
+
* @param {String} tweet A string of a tweet
|
1303
|
+
* @return {String} A linkified tweet
|
1304
|
+
*/
|
1305
|
+
linkify = function( tweet ) {
|
1306
|
+
|
1307
|
+
var link = function( t ) {
|
1308
|
+
return t.replace(
|
1309
|
+
/[a-z]+:\/\/[a-z0-9-_]+\.[a-z0-9-_:~%&\?\/.=]+[^:\.,\)\s*$]/ig,
|
1310
|
+
function( m ) {
|
1311
|
+
return '<a href="' + m + '">'
|
1312
|
+
+ ( ( m.length > 25 ) ? m.substr( 0, 24 ) + '...' : m )
|
1313
|
+
+ '</a>';
|
1314
|
+
}
|
1315
|
+
);
|
1316
|
+
},
|
1317
|
+
at = function( t ) {
|
1318
|
+
return t.replace(
|
1319
|
+
/(^|[^\w]+)\@([a-zA-Z0-9_]{1,15})/g,
|
1320
|
+
function( m, m1, m2 ) {
|
1321
|
+
return m1 + '<a href="http://twitter.com/' + m2 + '">@'
|
1322
|
+
+ m2 + '</a>';
|
1323
|
+
}
|
1324
|
+
);
|
1325
|
+
},
|
1326
|
+
hash = function( t ) {
|
1327
|
+
return t.replace(
|
1328
|
+
/(^|[^\w'"]+)\#([a-zA-Z0-9_]+)/g,
|
1329
|
+
function( m, m1, m2 ) {
|
1330
|
+
return m1 + '<a href="http://search.twitter.com/search?q=%23'
|
1331
|
+
+ m2 + '">#' + m2 + '</a>';
|
1332
|
+
}
|
1333
|
+
);
|
1334
|
+
};
|
1335
|
+
|
1336
|
+
return hash(at(link(tweet)));
|
1337
|
+
|
1338
|
+
},
|
1339
|
+
/**
|
1340
|
+
* Parse the input from twitter
|
1341
|
+
*/
|
1342
|
+
parseTwitter = function( input ) {
|
1343
|
+
var output = [], i = 0, j;
|
1344
|
+
|
1345
|
+
if(input.query && input.query.count && input.query.count >0) {
|
1346
|
+
j = input.query.count;
|
1347
|
+
for( ; i<j; i++) {
|
1348
|
+
var status = input.query.results.statuses[i].status;
|
1349
|
+
output.push({
|
1350
|
+
date: new Date(status.created_at),
|
1351
|
+
config: config,
|
1352
|
+
html: $.tmpl( template.posted, {
|
1353
|
+
tweet: linkify(status.text)
|
1354
|
+
} )
|
1355
|
+
});
|
1356
|
+
}
|
1357
|
+
}
|
1358
|
+
return output;
|
1359
|
+
};
|
1360
|
+
|
1361
|
+
$.ajax({
|
1362
|
+
url: createYqlUrl('select status.id, status.created_at, status.text'
|
1363
|
+
+ ' from twitter.user.timeline where screen_name="'+ config.user +'"'),
|
1364
|
+
dataType: 'jsonp',
|
1365
|
+
success: function( data ) {
|
1366
|
+
callback(parseTwitter(data));
|
1367
|
+
}
|
1368
|
+
});
|
1369
|
+
|
1370
|
+
// Expose the template.
|
1371
|
+
// We use this to check which templates are available
|
1372
|
+
return {
|
1373
|
+
"template" : template
|
1374
|
+
};
|
1375
|
+
|
1376
|
+
};
|
1377
|
+
|
1378
|
+
$.fn.lifestream.feeds.vimeo = function( config, callback ) {
|
1379
|
+
|
1380
|
+
var template = $.extend({},
|
1381
|
+
{
|
1382
|
+
posted: 'posted <a href="${url}" title="${description}">${title}</a>'
|
1383
|
+
},
|
1384
|
+
config.template),
|
1385
|
+
|
1386
|
+
parseVimeo = function( input ) {
|
1387
|
+
var output = [], i = 0, j, item;
|
1388
|
+
|
1389
|
+
if (input) {
|
1390
|
+
j = input.length;
|
1391
|
+
for( ; i < j; i++) {
|
1392
|
+
item = input[i];
|
1393
|
+
output.push({
|
1394
|
+
date: new Date( item.upload_date.replace(' ', 'T') ),
|
1395
|
+
config: config,
|
1396
|
+
html: $.tmpl( template.posted, {
|
1397
|
+
url: item.url,
|
1398
|
+
description: item.description.replace(/"/g, "'")
|
1399
|
+
.replace( /<.+?>/gi, ""),
|
1400
|
+
title: item.title
|
1401
|
+
} )
|
1402
|
+
});
|
1403
|
+
}
|
1404
|
+
}
|
1405
|
+
|
1406
|
+
return output;
|
1407
|
+
};
|
1408
|
+
|
1409
|
+
$.ajax({
|
1410
|
+
url: "http://vimeo.com/api/v2/" + config.user + "/videos.json",
|
1411
|
+
dataType: "jsonp",
|
1412
|
+
crossDomain: true,
|
1413
|
+
success: function( data ) {
|
1414
|
+
callback(parseVimeo(data));
|
1415
|
+
}
|
1416
|
+
});
|
1417
|
+
|
1418
|
+
// Expose the template.
|
1419
|
+
// We use this to check which templates are available
|
1420
|
+
return {
|
1421
|
+
"template" : template
|
1422
|
+
};
|
1423
|
+
|
1424
|
+
};
|
1425
|
+
|
1426
|
+
$.fn.lifestream.feeds.wordpress = function( config, callback ) {
|
1427
|
+
|
1428
|
+
var template = $.extend({},
|
1429
|
+
{
|
1430
|
+
posted: 'posted <a href="${link}">${title}</a>'
|
1431
|
+
},
|
1432
|
+
config.template);
|
1433
|
+
|
1434
|
+
var parseWordpress = function ( input ) {
|
1435
|
+
var output = [], list, i = 0, j, item;
|
1436
|
+
|
1437
|
+
if ( input.query && input.query.count && input.query.count > 0
|
1438
|
+
&& input.query.results.rss.channel.item ) {
|
1439
|
+
list = input.query.results.rss.channel.item;
|
1440
|
+
j = list.length;
|
1441
|
+
for ( ; i < j; i++) {
|
1442
|
+
item = list[i];
|
1443
|
+
|
1444
|
+
output.push({
|
1445
|
+
date: new Date( item.pubDate ),
|
1446
|
+
config: config,
|
1447
|
+
html: $.tmpl( template.posted, item )
|
1448
|
+
});
|
1449
|
+
}
|
1450
|
+
}
|
1451
|
+
|
1452
|
+
return output;
|
1453
|
+
};
|
1454
|
+
|
1455
|
+
$.ajax({
|
1456
|
+
url: createYqlUrl('select * from xml where '
|
1457
|
+
+ 'url="http://' + config.user + '.wordpress.com/feed"'),
|
1458
|
+
dataType: "jsonp",
|
1459
|
+
success: function ( data ) {
|
1460
|
+
callback(parseWordpress(data));
|
1461
|
+
}
|
1462
|
+
});
|
1463
|
+
|
1464
|
+
// Expose the template.
|
1465
|
+
// We use this to check which templates are available
|
1466
|
+
return {
|
1467
|
+
"template" : template
|
1468
|
+
};
|
1469
|
+
|
1470
|
+
};
|
1471
|
+
|
1472
|
+
$.fn.lifestream.feeds.youtube = function( config, callback ) {
|
1473
|
+
|
1474
|
+
var template = $.extend({},
|
1475
|
+
{
|
1476
|
+
favorited: 'favorited <a href="${video.player.default}" '
|
1477
|
+
+ 'title="${video.description}">${video.title}</a>'
|
1478
|
+
},
|
1479
|
+
config.template),
|
1480
|
+
|
1481
|
+
parseYoutube = function( input ) {
|
1482
|
+
var output = [], i = 0, j, item;
|
1483
|
+
|
1484
|
+
if(input.data && input.data.items) {
|
1485
|
+
j = input.data.items.length;
|
1486
|
+
for( ; i<j; i++) {
|
1487
|
+
item = input.data.items[i];
|
1488
|
+
output.push({
|
1489
|
+
date: new Date(item.created),
|
1490
|
+
config: config,
|
1491
|
+
html: $.tmpl( template.favorited, item )
|
1492
|
+
});
|
1493
|
+
}
|
1494
|
+
}
|
1495
|
+
|
1496
|
+
return output;
|
1497
|
+
};
|
1498
|
+
|
1499
|
+
$.ajax({
|
1500
|
+
url: "http://gdata.youtube.com/feeds/api/users/" + config.user
|
1501
|
+
+ "/favorites?v=2&alt=jsonc",
|
1502
|
+
dataType: 'jsonp',
|
1503
|
+
success: function( data ) {
|
1504
|
+
callback(parseYoutube(data));
|
1505
|
+
}
|
1506
|
+
});
|
1507
|
+
|
1508
|
+
// Expose the template.
|
1509
|
+
// We use this to check which templates are available
|
1510
|
+
return {
|
1511
|
+
"template" : template
|
1512
|
+
};
|
1513
|
+
|
1514
|
+
};
|
1515
|
+
|
1516
|
+
}( jQuery ));
|