main.js preguntaba siempre a 8.8.8.8/1.1.1.1. Las VPN que evitan fugas de DNS (Mullvad) y las redes que bloquean DNS externos los rechazan, y entonces no se encontraba ningun pub por nombre: unirse a uno no hacia nada y no decia nada. Ahora va primero getaddrinfo, que respeta la VPN y el DNS privado de Android; a los 5 s, o si falla, tambien los publicos. Probado en Android 15 detras de Mullvad: antes no resolvia hacklab.laenre.net y ahora si.
116 lines
5.3 KiB
JavaScript
116 lines
5.3 KiB
JavaScript
console.log('[Oasis Mobile] Node.js backend starting...');
|
|
|
|
process.env.HOME = process.env.HOME || require('path').resolve(__dirname, '..', '..');
|
|
process.env.ssb_appname = process.env.ssb_appname || 'ssb';
|
|
process.env.OASIS_MOBILE = '1';
|
|
process.env.CHLORIDE_JS = '1';
|
|
|
|
const path = require('path');
|
|
const fs = require('fs');
|
|
|
|
try {
|
|
const androidInfo = JSON.parse(fs.readFileSync(path.join(__dirname, '.android.json'), 'utf8'));
|
|
if (androidInfo.versionName) process.env.OASIS_ANDROID_VERSION = String(androidInfo.versionName);
|
|
if (androidInfo.versionCode) process.env.OASIS_ANDROID_VERSION_CODE = String(androidInfo.versionCode);
|
|
process.env.OASIS_ANDROID_INSTALLER = String(androidInfo.installer || '');
|
|
} catch (e) {}
|
|
|
|
const tmpDir = path.join(process.env.HOME, 'tmp');
|
|
try { fs.mkdirSync(tmpDir, { recursive: true }); } catch (e) {}
|
|
process.env.TMPDIR = tmpDir;
|
|
process.env.TMP = tmpDir;
|
|
process.env.TEMP = tmpDir;
|
|
try { require('os').tmpdir = () => tmpDir; } catch (e) {}
|
|
|
|
try {
|
|
const dns = require('dns');
|
|
const net = require('net');
|
|
const servers = ['8.8.8.8', '1.1.1.1', '8.8.4.4'];
|
|
const systemLookup = dns.lookup;
|
|
const SYSTEM_LOOKUP_MS = 5000;
|
|
try { dns.setServers(servers); } catch (e) {}
|
|
try { if (dns.promises && dns.promises.setServers) dns.promises.setServers(servers); } catch (e) {}
|
|
|
|
const localResolve = (hostname, family) => {
|
|
if (hostname === 'localhost' || hostname === 'localhost.localdomain' || hostname === 'ip6-localhost') {
|
|
return family === 6 ? { address: '::1', family: 6 } : { address: '127.0.0.1', family: 4 };
|
|
}
|
|
const ipv = net.isIP(hostname);
|
|
if (ipv) return { address: hostname, family: ipv };
|
|
return null;
|
|
};
|
|
|
|
const safeLookup = function (hostname, options, callback) {
|
|
if (typeof options === 'function') { callback = options; options = {}; }
|
|
options = options || {};
|
|
const family = options.family === 6 ? 6 : 4;
|
|
const direct = localResolve(hostname, family);
|
|
if (direct) {
|
|
return process.nextTick(() => options.all
|
|
? callback(null, [direct])
|
|
: callback(null, direct.address, direct.family));
|
|
}
|
|
// rama movil: primero el resolutor del sistema (getaddrinfo), que es el que
|
|
// respeta la VPN y el DNS privado de Android. Upstream iba siempre a
|
|
// 8.8.8.8/1.1.1.1, y las VPN que evitan fugas de DNS (Mullvad, por ejemplo)
|
|
// o las redes que bloquean DNS externos los rechazan: no se encontraba
|
|
// ningun pub por nombre y unirse a uno "no hacia nada". Los publicos quedan
|
|
// de respaldo, para los moviles donde getaddrinfo no contesta.
|
|
// Los dos caminos compiten: el del sistema sale ya y, si en SYSTEM_LOOKUP_MS
|
|
// no ha contestado o falla, se pregunta tambien a los publicos. Gana la primera
|
|
// respuesta buena; si fallan los dos, se devuelve el error del sistema, que
|
|
// dice mas ("no existe") que el de unos servidores quiza bloqueados.
|
|
let done = false, sysErr = null, pubErr = null, sysDone = false, pubDone = false, pubStarted = false;
|
|
const finish = (err, address, fam) => {
|
|
if (done) return;
|
|
done = true;
|
|
clearTimeout(timer);
|
|
if (err) return callback(err);
|
|
if (options.all) return callback(null, Array.isArray(address) ? address : [{ address, family: fam }]);
|
|
if (Array.isArray(address)) return callback(null, address[0].address, address[0].family);
|
|
return callback(null, address, fam);
|
|
};
|
|
const bothFailed = () => { if (sysDone && pubDone) finish(sysErr || pubErr || new Error('ENOTFOUND ' + hostname)); };
|
|
const viaPublic = () => {
|
|
if (pubStarted) return;
|
|
pubStarted = true;
|
|
const resolver = family === 6 ? dns.resolve6 : dns.resolve4;
|
|
resolver.call(dns, hostname, (err, addrs) => {
|
|
pubDone = true;
|
|
if (err || !addrs || !addrs.length) { pubErr = err || new Error('ENOTFOUND ' + hostname); return bothFailed(); }
|
|
finish(null, options.all ? addrs.map((x) => ({ address: x, family })) : addrs[0], family);
|
|
});
|
|
};
|
|
const timer = setTimeout(viaPublic, SYSTEM_LOOKUP_MS);
|
|
systemLookup.call(dns, hostname, { family, all: !!options.all }, (err, address, fam) => {
|
|
sysDone = true;
|
|
if (!err) return finish(null, address, fam);
|
|
sysErr = err;
|
|
if (pubStarted) bothFailed(); else viaPublic();
|
|
});
|
|
};
|
|
|
|
dns.lookup = safeLookup;
|
|
if (dns.promises) {
|
|
dns.promises.lookup = (hostname, options) => new Promise((resolve, reject) => {
|
|
safeLookup(hostname, options || {}, (err, address, family) => {
|
|
if (err) return reject(err);
|
|
if (options && options.all) return resolve(address);
|
|
resolve({ address, family });
|
|
});
|
|
});
|
|
}
|
|
} catch (e) {}
|
|
|
|
const backendPath = path.join(__dirname, 'src', 'backend', 'backend.js');
|
|
|
|
console.log('[Oasis] Launching Oasis Social Network Utopia...');
|
|
console.log('[Oasis] Backend path:', backendPath);
|
|
console.log('[Oasis] HOME:', process.env.HOME);
|
|
|
|
try {
|
|
require(backendPath);
|
|
console.log('[Oasis] Backend started on port 3000');
|
|
} catch (error) {
|
|
console.error('[Oasis] Error starting backend:', error);
|
|
}
|