VulpesOS/gaia/shared/js/contacts/import/utilities/misc.js
OverSu b38dea0597 Publish Vulpes Preview 15 sources for desktop, Android and Tundra
Share Gaia assets and adapters, keep private profiles and development documents local, and update both public READMEs.
2026-09-30 23:13:03 +02:00

191 lines
5.3 KiB
JavaScript
Executable file

/* global mozContact, oauthflow, ImportStatusData */
'use strict';
var utils = window.utils || {};
// Scale ratio for different devices
var SCALE_RATIO = window.devicePixelRatio || 1;
var LAST_IMPORT_TIMESTAMP_SUFFIX = '_last_import_timestamp';
function scale(size) {
return Math.round(SCALE_RATIO * size);
}
if (!utils.misc) {
utils.misc = {};
utils.misc.toMozContact = function(contact) {
var outContact = contact;
if (!(contact instanceof mozContact)) {
outContact = new mozContact(contact);
outContact.id = contact.id || outContact.id;
}
return outContact;
};
// This year indicates that the year can be ignored
const FLAG_YEAR_IGNORED = 9996;
utils.misc.FLAG_YEAR_IGNORED = FLAG_YEAR_IGNORED;
utils.misc.formatDate = function(date, customFormat) {
var dateString = null;
try {
var format = customFormat || {
month: 'short',
day: 'numeric'
};
var offset = date.getTimezoneOffset() * 60 * 1000;
var normalizedDate = new Date(date.getTime() + offset);
var year = normalizedDate.getFullYear();
if (year !== FLAG_YEAR_IGNORED) {
format.year = 'numeric';
}
var f = new Intl.DateTimeFormat(navigator.languages, format);
dateString = f.format(normalizedDate);
} catch (err) {
console.error('Error parsing date: ', err);
throw err;
}
return dateString;
};
// Parses a name to obtain a givenName and a familyName
// This is useful while importing contacts from SIM card
utils.misc.parseName = function(nameString) {
// Minimum length to consider a token as significative
var MIN_LENGHT_SIGNIFICATIVE = 3;
// Minimum length of a token to consider it a familyName
var MIN_LENGHT_FN = 2;
var out = {
givenName: '',
familyName: ''
};
if (!nameString) {
return out;
}
var str = nameString.trim();
if (!str) {
return out;
}
function startsWithUpper(str) {
var firstLetter = str.charAt(0);
var capFirstLetter = firstLetter.toLocaleUpperCase();
return (capFirstLetter === firstLetter);
}
// First step of the algorithm is to split the name in its tokens
var tokens = nameString.split(/\s+/);
var significativeTokens = {};
for (var j = 0; j < tokens.length; j++) {
var token = tokens[j];
// A significative token os one with that min length and which starts with
// uppercase letter
if (token.length > MIN_LENGHT_SIGNIFICATIVE || startsWithUpper(token)) {
significativeTokens[token] = true;
}
}
var totalTokens = tokens.length;
var lastToken = totalTokens - 1;
var rolePrevToken;
var remainingTokens = Object.keys(significativeTokens).length;
var outGivenNames = [], outFamilyNames = [];
// We need to keep the totals in a different variable as a familyName
// can be composed by more than one token
var numFns = 0;
while (lastToken >= 0) {
if (significativeTokens[tokens[lastToken]]) {
remainingTokens--;
}
var currToken = tokens[lastToken],
nextToken = tokens[lastToken + 1],
prevToken = tokens[lastToken - 1];
// The last element is taken as part of the family name
if (!nextToken && prevToken) {
outFamilyNames.push(currToken);
numFns++;
rolePrevToken = 'FN';
}
else if (!prevToken) {
outGivenNames.push(currToken);
rolePrevToken = 'GN';
}
else if (nextToken) {
if (!significativeTokens[currToken]) {
if (rolePrevToken === 'FN') {
// Here the number of fns is not incremented as this is a non
// significative token
outFamilyNames.push(currToken);
}
else {
outGivenNames.push(currToken);
}
}
else if (currToken.length < MIN_LENGHT_FN) {
outGivenNames.push(currToken);
rolePrevToken = 'GN';
}
else {
// Number of familyNames will be two at most
// Preference is given to the givenName over familyName
// We prefer two givenNames instead of two family Names
if (remainingTokens >= 2 && numFns < 2) {
outFamilyNames.push(currToken);
numFns++;
rolePrevToken = 'FN';
}
else {
outGivenNames.push(currToken);
rolePrevToken = 'GN';
}
}
}
lastToken--;
}
out.givenName = outGivenNames.reverse().join(' ').trim();
out.familyName = outFamilyNames.reverse().join(' ').trim();
return out;
};
utils.misc.getPreferredPictureBox = function() {
var imgThumbSize = oauthflow.params.facebook.imgThumbSize;
var out = {
width: scale(imgThumbSize)
};
out.height = out.width;
return out;
};
utils.misc.getPreferredPictureDetail = function() {
var imgDetailWidth = oauthflow.params.facebook.imgDetailWidth;
return scale(imgDetailWidth);
};
utils.misc.setTimestamp = function(type, callback) {
ImportStatusData.put(type + LAST_IMPORT_TIMESTAMP_SUFFIX, Date.now())
.then(callback);
};
utils.misc.getTimestamp = function(type, callback) {
ImportStatusData.get(type + LAST_IMPORT_TIMESTAMP_SUFFIX)
.then(callback);
};
}