Github show user email addresses

By Johan Sundström Last update Aug 6, 2009 — Installed 68 times.

There are 2 previous versions of this script.

// ==UserScript==
// @name           Github show user email addresses
// @namespace      http://code.google.com/p/ecmanaut/
// @url            http://userscripts.org/scripts/source/55131.user.js
// @description    Tries showing email addresses of github users.
// @require        http://ecmanaut.googlecode.com/svn/trunk/lib/md5.js
// @require        http://ecmanaut.googlecode.com/svn/trunk/lib/gm/$x$X.js
// @require        http://ecmanaut.googlecode.com/svn/trunk/lib/gm/node.js
// @include        http://github.com/*
// @include        https://github.com/*
// @include        http://groups.google.com/group/*/manage_members
// ==/UserScript==

var me = '"Github show user email addresses" user script';
var debug = "undefined" != typeof this.gravatar;

XML.setSettings({
  ignoreProcessingInstructions: false,
  ignoreWhitespace: false, // don't collapse our carefully injected whitespace
  ignoreComments: false,
  prettyPrinting: false, prettyIndent: 2
});

switch (location.hostname) {
  case "github.com": // do things in the UI
    var identity = $X('//div[@class="identity"][h1 and img]');
    var gravatar = $X('img[starts-with(@src,"http://www.gravatar.com/avatar")]',
                      identity);
    var mailhash = gravatar && gravatar.src.match(/[0-9a-f]{32}/);
    var usernick = $X('h1', identity);
    var repoinfo = $X('//div[@class="info"][contains(../@class,"vcard")]');

    if (usernick && mailhash) {
      mailhash = mailhash[0];

      var user = mail_from_hash(mailhash, usernick.textContent);
      if (user) {
        maybe_prepend("Email", user.mail);
        if (user.name)
          maybe_prepend("Name", user.name);
      } else if (debug) {
        node({ prepend: identity, tag: <>Email MD5: { mailhash }</> });
        usernick.style.marginTop = "-18px";
      }
    }
    break;

  case "groups.google.com": // build gravatar db
    var form = $X('//form[@name="memberexport"][contains(@action,".csv")]');
    if (form) GM_xmlhttpRequest({
      method: form.method || "GET",
      url:    form.action + '?Action.Export=Export member list',
      onload: got_mail_csv
    });
    break;
}

function mail_from_hash(hash, nick) {
  var data = JSON.parse(GM_getValue(hash, "null"));
  if (data) {
    var info = { mail: data[0] };
    var name = trim(data[1]);
    if (name != trim(nick))
      info.name = name;
    return info;
  }

  var common = [
    "gmail.com",
    "google.com",
    "hotmail.com",
    "yahoo.com"
  ];
  for each (var host in common) {
    var mail = nick +"@"+ host;
    if (MD5.hex(mail) == hash)
      return { mail: mail };
  }

  return null;
}

function got_mail_csv({ responseText: csv }) {
  function maybe_store_address(line) {
    var match = /^([^,@]+@[^,@]+),\x22([^\x22]+)\x22/.exec(line);
    if (match) {
      GM_setValue(MD5.hex(match[1]), JSON.stringify(match.slice(1)));
    }
  }
  csv.split(/[\n\r]+/g).forEach(maybe_store_address);
}

function maybe_prepend(key, value) {
  var tag = key == "Email" ? <a href={ "mailto:"+ value }>{ value }</a> : value;
  var present = $X('div[@class="field"]/div[preceding-sibling::label[.="' +
                   key +':"]]', repoinfo);
  if (present && textContent(present) != value)
    node({ append: present,
           tag: <><br/><i title={"added by "+ me}>{ tag }</i></> });
  if (!present)
    node({ prepend: repoinfo, tag: <div class="field" title={"added by "+ me}
             style="font-style: italic">
             <label>{ key }:</label>
             <div>{ tag }</div>
           </div> });
}

function textContent(node) {
  if (/^script$/i.test(node.nodeName))
    return "";
  if ((node.childNodes || []).length)
    return Array.map(node.childNodes, textContent).join("");
  return trim(node.textContent);
}

function trim(s) {
  return s.replace(/^\s+|\s+$/g, "");
}