Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Moshikashite.typo
var _ = require('underscore');
var Moshikashite = function () {};
Moshikashite.VALID_DOMAINS = [
"gmail.com",
"yahoo.co.jp",
"docomo.ne.jp",
"ezweb.ne.jp",
"softbank.ne.jp",
"i.softbank.jp",
"hi-ho.ne.jp",
"hotmail.co.jp",
"hotmail.com",
"jcom.home.ne.jp",
"live.jp",
"nifty.com",
"ocn.jp",
"auone-net.jp",
"moneyforward.co.jp"
];
Moshikashite._validDomainsChars = null;
Moshikashite._givenEmail = null;
Moshikashite._givenDomain = null;
Moshikashite._givenDomainChars = null;
Moshikashite.typo = function (email) {
var self = this;
if (!self._prepareTypoCheck(email)) {
return false;
}
var mostSimilarDomain = self._getMostSimilarDomain();
if (_.isNumber(mostSimilarDomain.score)) {
return "もしかして" + mostSimilarDomain.domain + "?";
}
return false;
};
Moshikashite._prepareTypoCheck = function (email) {
var self = this;
self._setValidDomainsChars();
self._givenEmail = email;
self._givenDomain = self._extractDomain(self._givenEmail);
self._givenDomainChars = _.uniq(self._givenDomain);
return self._shouldTypoCheck();
}
Moshikashite._setValidDomainsChars = function () {
var self = this;
if (self._validDomainsChars === null) {
self._validDomainsChars = [];
var l = self.VALID_DOMAINS.length;
for (var i = 0; i < l; i++) {
self._validDomainsChars.push(_.uniq(self.VALID_DOMAINS[i]));
}
}
};
Moshikashite._extractDomain = function (email) {
return email.split('@')[1];
};
Moshikashite._shouldTypoCheck = function () {
// TODO: 定数のoption化
var self = this;
return (self._givenDomainChars.length > 3 && this.VALID_DOMAINS.indexOf(self._givenDomain) < 0);
};
Moshikashite._calcSimilarityScores = function () {
var self = this;
var scores = [];
var l = self.VALID_DOMAINS.length;
for (var validDomainIndex = 0; validDomainIndex < l; validDomainIndex++) {
var score = self._calcSimilarityScore(validDomainIndex);
if (score !== false) {
scores.push({ score: score, domain: self.VALID_DOMAINS[validDomainIndex]});
}
}
return scores;
};
Moshikashite._calcSimilarityScore = function (validDomainIndex) {
var self = this;
var validDomain = self.VALID_DOMAINS[validDomainIndex];
var validDomainChars = self._validDomainsChars[validDomainIndex];
// 1文字目が異なっていたらfalseを返す
if (self._givenDomain[0] !== validDomain[0]) {
return false;
}
var numOfSameChar = 0;
var validDomainCharsLength = validDomainChars.length;
for (var i = 0; i < validDomainCharsLength; i++) {
if (self._givenDomainChars.indexOf(validDomainChars[i]) >= 0) {
numOfSameChar++;
}
}
var score = numOfSameChar / validDomainCharsLength;
// TODO: 定数のoption化
if (score > 0.6 && Math.abs(validDomain.length - self._givenDomain.length) < 3) {
return score;
}
return false;
};
Moshikashite._getMostSimilarDomain = function () {
var self = this;
return _.max(
self._calcSimilarityScores(),
function (scoreAndDomain) { return scoreAndDomain.score; }
);
};
module.exports = Moshikashite;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.