Skip to content

Instantly share code, notes, and snippets.

@pasiaj
Created July 31, 2013 19:57
Show Gist options
  • Star 10 You must be signed in to star a gist
  • Fork 4 You must be signed in to fork a gist
  • Save pasiaj/6125565 to your computer and use it in GitHub Desktop.
Save pasiaj/6125565 to your computer and use it in GitHub Desktop.
A phantomjs script to: a) Login to Linkedin.com b) Scrape all your contacts c) Visit all the contacts d) Automatically endorse all contacts' skills.
var auth = {
user: "USERNAME",
pass: "PASSWORD"
};
function ParallelRunner (list, func, runners) {
function createSlots(runners) {
var slots = [];
for (var i = 0; i < runners; i++) {
slots.push( objReturner() );
}
return slots;
}
function objReturner() {
return { free: true };
}
function toArray(obj) {
return Array.prototype.slice.call(obj);
}
function bind(scope, fn /*, variadic args to curry */ ) {
var args = Array.prototype.slice.call(arguments, 2);
return function() {
return fn.apply(scope, args.concat(toArray(arguments)));
};
}
function _next() {
var slot = this.getFreeSlot();
if (slot !== null) {
slot.free = false;
var cb = function() {
slot.free = true;
};
if (list.length !== 0) {
var next = list.pop();
func(next, cb);
} else {}
}
}
this.start = function() {
interval = setInterval(this.next, 100);
};
this.stop = function(){
clearInterval(interval);
};
function _getFreeSlot() {
for (var i = slots.length - 1; i >= 0; i--) {
if (slots[i].free) {
return slots[i];
}
}
return null;
}
runners = runners || 3;
var slots = createSlots(runners),
interval;
// Something weird happens with objects returned by PhantomJS page.evaluate()
// Fix em by rebuilding the objects. ONLY WORKS w/ SIMPLE OBJECTS!!!
list = JSON.parse(JSON.stringify(list));
this.next = bind(this, _next);
this.getFreeSlot = bind(this, _getFreeSlot);
}
function visitAndEndorse(name, cb) {
var np = require("webpage").create();
np.onConsoleMessage = function(msg) {
console.log(msg);
};
np.open(name.href, function(status) {
if (status === "success") {
np.evaluate(function() {
function click(el) {
var ev = document.createEvent("MouseEvent");
ev.initMouseEvent(
"click",
true /* bubble */ , true /* cancelable */ ,
window, null,
0, 0, 0, 0, /* coordinates */
false, false, false, false, /* modifier keys */
0 /*left*/ , null
);
el.dispatchEvent(ev);
}
var name = document.querySelector(".full-name");
if (name !== null) {
console.log("Visited " + name.textContent);
}
setTimeout(function() {
var endorse = document.querySelector(".btn-action.endorse-skills");
if (endorse !== null) {
console.log("Endorsed " + name.textContent);
click(endorse);
} else {
console.log("No endorse");
}
}, 3000);
});
window.setTimeout(function() {
np.close();
cb();
}, 6000);
}
});
}
var page = require("webpage").create();
var names = [];
page.onConsoleMessage = function(msg) {
console.log(msg);
};
page.open("http://www.linkedin.com/people/connections", function(status) {
if (status === "success") {
page.evaluate(function() {
function click(el) {
var ev = document.createEvent("MouseEvent");
ev.initMouseEvent(
"click",
true /* bubble */ , true /* cancelable */ ,
window, null,
0, 0, 0, 0, /* coordinates */
false, false, false, false, /* modifier keys */
0 /*left*/ , null
);
el.dispatchEvent(ev);
}
var button = document.querySelector("#register-custom-nav a");
click(button);
});
window.setTimeout(function() {
page.evaluate(function(auth) {
document.querySelector("#session_key-login").value = auth.user;
document.querySelector("#session_password-login").value = auth.pass;
document.querySelector("#login").submit();
console.log("Login submitted!");
}, auth);
}, 1400);
window.setTimeout(function() {
console.log("Get names");
names = page.evaluate(function() {
var all = document.querySelectorAll(".conx-list li");
var list = [];
for (var i = all.length - 1; i >= 0; i--) {
var item = all[i];
if (item.hasOwnProperty("id")) {
var nameInputs = item.getElementsByTagName("input");
if (nameInputs.length > 0) {
console.log(nameInputs[0].value, item.id);
list.push({
name: nameInputs[0].value,
href: "http://www.linkedin.com/profile/view?id=" + item.id
});
}
}
}
console.log("Got " + list.length + " names");
return list;
});
var a = new ParallelRunner(names, visitAndEndorse, 3);
a.start();
}, 6000);
}
});
@menriquez
Copy link

this script doesn't seem to be working anymore...when i run it it says i have no contacts and just hangs.

i could attempt to fix it but i would just like to verify it im not doing something wrong...of course i entered my login info where indicated.

@pasiaj
Copy link
Author

pasiaj commented Jun 8, 2014

I'm sorry, I missed your comment earlier. Thereseems to be a problem with the code: No contacts are found. I haven't had the time to look into it, yet.

@nobelove
Copy link

can you update the code please, not working :(

@nomankhn1
Copy link

I ran many times but getting this.

./phantomjs linkedin.js
Login submitted!
Get names
Got 0 names

and after that it hangs.

@nomankhn1
Copy link

I am using phantomjs version => phantomjs-2.1.1-linux-i686

@nomankhn1
Copy link

any update?

@BMLande
Copy link

BMLande commented Sep 25, 2017

hello friends , any updte on above scripts??

@BMLande
Copy link

BMLande commented Sep 25, 2017

can you help m,e on following isuues,
i return phantomjs script to scrap my connections information , but when i am passing the address as follows:
phantomjs printli.js https://www.linkedin.com/mynetwork/invite-connect/connections/

internally this will redirect to linkden login page :-(
if any help please help ,e... thanks

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment