Rename extension, add non-ascii hack, fix context menu links, lint,

refactor
This commit is contained in:
Ilya Ig. Petrov 2016-12-29 14:24:11 +00:00
parent 85859b3f4b
commit 091a542b5d
37 changed files with 296 additions and 238 deletions

View File

@ -13,6 +13,7 @@ module.exports = {
}, },
"parserOptions": { "parserOptions": {
"sourceType": "script", "sourceType": "script",
"ecmaVersion": 2017,
"ecmaFeatures": { "ecmaFeatures": {
"impliedStrict": false "impliedStrict": false
} }

View File

@ -1 +0,0 @@
# Перемещено [сюда](https://rebrand.ly/ac-support)

Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.1 KiB

View File

@ -1,215 +0,0 @@
'use strict';
chrome.runtime.getBackgroundPage( (backgroundPage) =>
backgroundPage.apis.errorHandlers.installListenersOnAsync(window, 'POPUP', () => {
const getStatus = () => document.querySelector('#status');
const setStatusTo = (msg) => {
getStatus().innerHTML = msg;
};
const antiCensorRu = backgroundPage.apis.antiCensorRu;
const errorHandlers = backgroundPage.apis.errorHandlers;
// SET DATE
const setDate = () => {
let dateForUser = 'никогда';
if( antiCensorRu.lastPacUpdateStamp ) {
let diff = Date.now() - antiCensorRu.lastPacUpdateStamp;
let units = 'мс';
const gauges = [
[1000, 'с'],
[60, 'мин'],
[60, 'ч'],
[24, 'дн'],
[7, ' недель'],
[4, ' месяцев'],
];
for(const g of gauges) {
const diffy = Math.floor(diff / g[0]);
if (!diffy)
break;
diff = diffy;
units = g[1];
}
dateForUser = diff + units + ' назад';
}
const dateElement = document.querySelector('.update-date');
dateElement.innerText = dateForUser + ' / ' + (antiCensorRu.pacUpdatePeriodInMinutes/60) + 'ч';
dateElement.title = new Date(antiCensorRu.lastPacUpdateStamp)
.toLocaleString('ru-RU');
};
setDate();
chrome.storage.onChanged.addListener(
(changes) => changes.lastPacUpdateStamp.newValue && setDate()
);
// CLOSE BUTTON
document.querySelector('.close-button').onclick = () => window.close();
// RADIOS
const currentProviderRadio = () => {
const id = antiCensorRu.currentPacProviderKey || 'none';
return document.querySelector('#'+id);
};
const checkChosenProvider = () => currentProviderRadio().checked = true;
const showError = (err) => {
let clarification = err.clarification;
const ifNotCritical = clarification && clarification.ifNotCritical;
let message = err.message || '';
while( clarification ) {
message = (clarification && (clarification.message + ' ')) + message;
clarification = clarification.prev;
}
message = message.trim();
setStatusTo(
`<span style="color:red">
${ifNotCritical ? 'Некритичная ошибка.' : 'Ошибка!'}
</span>
<br/>
<span style="font-size: 0.9em; color: darkred">${message}</span>
<a href class="link-button">
[Ещё&nbsp;подробнее]
</a>`
);
getStatus().querySelector('.link-button').onclick = function() {
errorHandlers.viewErrorVoid(err);
return false;
};
};
const enableDisableInputs = function() {
const inputs = document.querySelectorAll('input');
for ( let i = 0; i < inputs.length; i++ ) {
inputs[i].disabled = !inputs[i].disabled;
}
};
const conduct = (beforeStatus, operation, afterStatus, onSuccess) => {
setStatusTo(beforeStatus);
enableDisableInputs();
operation((err) => {
if (err) {
showError(err);
} else {
setStatusTo(afterStatus);
onSuccess && onSuccess();
}
enableDisableInputs();
});
};
const ul = document.querySelector('#list-of-providers');
const _firstChild = ul.firstChild;
for( const providerKey of Object.keys(antiCensorRu.pacProviders).sort() ) {
const li = document.createElement('li');
li.innerHTML = `
<input type="radio" name="pacProvider" id="${providerKey}">
<label for="${providerKey}">${providerKey}</label>
<a href class="link-button checked-radio-panel"
id="update-${providerKey}">[обновить]</a>`;
li.querySelector('.link-button').onclick =
() => {
conduct(
'Обновляем...', (cb) => antiCensorRu.syncWithPacProviderAsync(cb),
'Обновлено.'
);
return false;
};
ul.insertBefore( li, _firstChild );
}
checkChosenProvider();
const radios = [].slice.apply(
document.querySelectorAll('[name=pacProvider]')
);
for(const radio of radios) {
radio.onclick = function(event) {
if (
event.target.id === (antiCensorRu.currentPacProviderKey || 'none')
) {
return false;
}
const pacKey = event.target.id;
if (pacKey === 'none') {
conduct(
'Отключение...',
(cb) => antiCensorRu.clearPacAsync(cb),
'Отключено.',
checkChosenProvider
);
} else {
conduct(
'Установка...',
(cb) => antiCensorRu.installPacAsync(pacKey, cb),
'PAC-скрипт установлен.',
checkChosenProvider
);
}
return false;
};
}
const conpanel = document.getElementById('list-of-handlers');
errorHandlers.getEventsMap().forEach( (value, name) => {
const li = document.createElement('li');
li.innerHTML = `
<input type="checkbox" id="if-on-${name}"/>
<label for="if-on-${name}">${value}</label>`;
const box = li.querySelector('input');
box.checked = backgroundPage.apis.errorHandlers.isOn(name);
box.onclick = function() {
const id = this.id.replace('if-on-', '');
return backgroundPage.apis.errorHandlers.switchVoid(
this.checked ? 'on' : 'off',
id
);
};
conpanel.appendChild(li);
});
if( errorHandlers.ifNotControlled ) {
document.getElementById('which-extension').innerHTML = backgroundPage.utils.messages.whichExtensionHtml();
document.querySelectorAll('.if-not-controlled').forEach( (node) => {
node.style.display = 'block';
});
}
setStatusTo('');
if (antiCensorRu.ifFirstInstall) {
const id = antiCensorRu.currentPacProviderKey || 'none';
document.querySelector('#update-' + id).click();
}
document.documentElement.style.display = '';
})
);

View File

@ -5,7 +5,7 @@
"main": "index.js", "main": "index.js",
"scripts": { "scripts": {
"test": "echo \"Error: no test specified\" && exit 1", "test": "echo \"Error: no test specified\" && exit 1",
"lint": "./node_modules/.bin/eslint ./extension/**/*.js --ignore-pattern vendor" "lint": "./node_modules/.bin/eslint ./runet-censorship-bypass/extension/**/*.js --ignore-pattern vendor"
}, },
"author": "Ilya Ig. Petrov", "author": "Ilya Ig. Petrov",
"license": "GPLv3", "license": "GPLv3",

View File

@ -122,7 +122,9 @@
this.ifNotControlled = window.utils.areSettingsNotControlledFor(details); this.ifNotControlled = window.utils.areSettingsNotControlledFor(details);
if (this.ifNotControlled) { if (this.ifNotControlled) {
chrome.browserAction.setIcon( {path: './icons/default-grayscale-128.png'} ); chrome.browserAction.setIcon({
path: './icons/default-grayscale-128.png',
});
} else { } else {
chrome.browserAction.setIcon( {path: './icons/default-128.png'} ); chrome.browserAction.setIcon( {path: './icons/default-128.png'} );
} }
@ -201,7 +203,9 @@
chrome.notifications.clear(notId); chrome.notifications.clear(notId);
if(notId === 'no-control') { if(notId === 'no-control') {
return openAndFocus( window.utils.messages.searchSettingsForUrl('proxy') ); return openAndFocus(
window.utils.messages.searchSettingsForUrl('proxy')
);
} }
const errors = handlers.idToError; const errors = handlers.idToError;
handlers.viewErrorVoid(errors); handlers.viewErrorVoid(errors);

View File

@ -113,9 +113,9 @@
/* /*
Don't use in system configs! Because Win does poor caching. Don't use in system configs! Because Win does poor caching.
Url is encoded to counter abuse. Url is encoded to counter abuse.
Version: 0.15 Version: 0.17
*/ */
pacUrl: '\x68\x74\x74\x70\x73\x3a\x2f\x2f\x64\x72\x69\x76\x65\x2e\x67\x6f\x6f\x67\x6c\x65\x2e\x63\x6f\x6d\x2f\x75\x63\x3f\x65\x78\x70\x6f\x72\x74\x3d\x64\x6f\x77\x6e\x6c\x6f\x61\x64\x26\x69\x64\x3d\x30\x42\x2d\x5a\x43\x56\x53\x76\x75\x4e\x57\x66\x30\x62\x7a\x4e\x55\x52\x32\x46\x34\x52\x46\x38\x77\x4f\x55\x30', pacUrl: '\x68\x74\x74\x70\x73\x3a\x2f\x2f\x64\x72\x69\x76\x65\x2e\x67\x6f\x6f\x67\x6c\x65\x2e\x63\x6f\x6d\x2f\x75\x63\x3f\x65\x78\x70\x6f\x72\x74\x3d\x64\x6f\x77\x6e\x6c\x6f\x61\x64\x26\x69\x64\x3d\x30\x42\x2d\x5a\x43\x56\x53\x76\x75\x4e\x57\x66\x30\x54\x44\x46\x52\x4f\x47\x35\x46\x62\x55\x39\x4f\x64\x44\x67',
proxyHosts: ['proxy.antizapret.prostovpn.org', 'gw2.anticenz.org'], proxyHosts: ['proxy.antizapret.prostovpn.org', 'gw2.anticenz.org'],
proxyIps: { proxyIps: {
'195.123.209.38': 'proxy.antizapret.prostovpn.org', '195.123.209.38': 'proxy.antizapret.prostovpn.org',
@ -224,7 +224,7 @@
const pacProvider = this.getPacProvider(key); const pacProvider = this.getPacProvider(key);
const pacSetPromise = new Promise( const pacSetPromise = new Promise(
(resolve, reject) => setPacScriptFromProvider( (resolve, reject) => setPacScriptFromProviderAsync(
pacProvider, pacProvider,
(err, res) => { (err, res) => {
@ -444,7 +444,10 @@
}); });
function setPacAsync(pacData, cb = throwIfError) { function setPacAsync(
{pacData = mandatory(), pacUrl = mandatory()},
cb = throwIfError
) {
const config = { const config = {
mode: 'pac_script', mode: 'pac_script',
@ -454,20 +457,44 @@
}, },
}; };
console.log('Setting chrome proxy settings...'); console.log('Setting chrome proxy settings...');
chrome.proxy.settings.set( {value: config}, () => { chrome.proxy.settings.set( {value: config}, async () => {
const err = checkChromeError(); let err = checkChromeError();
let asciiErr;
if (err) { if (err) {
return cb(err); if (err.message.startsWith('\'pacScript.data\' supports only ASCII')) {
asciiErr = err;
asciiErr.clarification = {ifNotCritical: true};
err = await new Promise((resolve) => {
chrome.proxy.settings.set({
value: {
mode: 'pac_script',
pacScript: {
url: pacUrl,
},
},
},
() => resolve( checkChromeError() )
);
});
}
if (err) {
return cb(err);
}
} }
chrome.proxy.settings.get({}, (details) => { chrome.proxy.settings.get({}, (details) => {
if ( window.utils.areSettingsNotControlledFor( details ) ) { if ( window.utils.areSettingsNotControlledFor( details ) ) {
console.warn('Failed, other extension is in control.'); console.warn('Failed, other extension is in control.');
return cb({clarification: {message: window.utils.messages.whichExtensionHtml() }}); return cb({clarification: {
message: window.utils.messages.whichExtensionHtml(),
}});
} }
console.log('Successfuly set PAC in proxy settings..'); console.log('Successfuly set PAC in proxy settings..');
cb(); cb(asciiErr);
}); });
}); });
@ -606,15 +633,16 @@
} }
function setPacScriptFromProvider(provider, cb = throwIfError) { function setPacScriptFromProviderAsync(provider, cb = throwIfError) {
cb = asyncLogGroup( cb = asyncLogGroup(
'Getting pac script from provider...', provider.pacUrl, 'Getting pac script from provider...', provider.pacUrl,
cb cb
); );
const pacUrl = provider.pacUrl;
httpGet( httpGet(
provider.pacUrl, pacUrl,
(err, pacData) => { (err, pacData) => {
if (err) { if (err) {
@ -625,7 +653,7 @@
}; };
return cb(err); return cb(err);
} }
setPacAsync(pacData, cb); setPacAsync({pacData, pacUrl}, cb);
} }
); );

View File

@ -12,12 +12,18 @@
createMenuLinkEntry( createMenuLinkEntry(
'Сайт доступен из-за границы? Is up?', 'Сайт доступен из-за границы? Is up?',
(tab) => 'http://isup.me/' + new URL(tab.url).hostname (tab) => `data:text/html;charset=utf8,<title>Запрашиваю...</title>
<form class='tracker-form' method='POST'
action='https://www.host-tracker.com/ru/InstantCheck/Create'>
<input name='InstantCheckUrl' value='${new URL(tab.url).hostname}'
type='hidden'>
</form>
<script>document.querySelector('.tracker-form').submit()<\/script>`
); );
createMenuLinkEntry( createMenuLinkEntry(
'Сайт в реестре блокировок?', 'Сайт в реестре блокировок?',
(tab) => 'https://antizapret.info/index.php?search=' + tab.url (tab) => 'https://antizapret.info/index.php?search=' + new URL(tab.url).hostname
); );
createMenuLinkEntry( createMenuLinkEntry(

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.3 KiB

View File

@ -1,10 +1,10 @@
{ {
"manifest_version": 2, "manifest_version": 2,
"name": "__MSG_extName__", "name": "__MSG_extName__ 0.17",
"default_locale": "ru", "default_locale": "ru",
"description": "__MSG_extDesc__", "description": "__MSG_extDesc__",
"version": "0.0.0.16", "version": "0.0.0.17",
"icons": { "icons": {
"128": "/icons/default-128.png" "128": "/icons/default-128.png"
}, },
@ -33,7 +33,7 @@
] ]
}, },
"browser_action": { "browser_action": {
"default_title": "Этот сайт благословлён", "default_title": "Этот сайт благословлён 0.17",
"default_popup": "/pages/choose-pac-provider/index.html" "default_popup": "/pages/choose-pac-provider/index.html"
}, },
"options_ui": { "options_ui": {

View File

@ -56,6 +56,7 @@
} }
.if-not-controlled { .if-not-controlled {
display: none; display: none;
color: red;
} }
</style> </style>
</head> </head>

View File

@ -0,0 +1,220 @@
'use strict';
chrome.runtime.getBackgroundPage( (backgroundPage) =>
backgroundPage.apis.errorHandlers.installListenersOnAsync(
window, 'POPUP', () => {
const getStatus = () => document.querySelector('#status');
const setStatusTo = (msg) => {
getStatus().innerHTML = msg;
};
const antiCensorRu = backgroundPage.apis.antiCensorRu;
const errorHandlers = backgroundPage.apis.errorHandlers;
// SET DATE
const setDate = () => {
let dateForUser = 'никогда';
if( antiCensorRu.lastPacUpdateStamp ) {
let diff = Date.now() - antiCensorRu.lastPacUpdateStamp;
let units = 'мс';
const gauges = [
[1000, 'с'],
[60, 'мин'],
[60, 'ч'],
[24, 'дн'],
[7, ' недель'],
[4, ' месяцев'],
];
for(const g of gauges) {
const diffy = Math.floor(diff / g[0]);
if (!diffy)
break;
diff = diffy;
units = g[1];
}
dateForUser = diff + units + ' назад';
}
const dateElement = document.querySelector('.update-date');
dateElement.innerText = dateForUser + ' / ' +
(antiCensorRu.pacUpdatePeriodInMinutes/60) + 'ч';
dateElement.title = new Date(antiCensorRu.lastPacUpdateStamp)
.toLocaleString('ru-RU');
};
setDate();
chrome.storage.onChanged.addListener(
(changes) => changes.lastPacUpdateStamp.newValue && setDate()
);
// CLOSE BUTTON
document.querySelector('.close-button').onclick = () => window.close();
// RADIOS
const currentProviderRadio = () => {
const id = antiCensorRu.currentPacProviderKey || 'none';
return document.querySelector('#'+id);
};
const checkChosenProvider = () => currentProviderRadio().checked = true;
const showError = (err) => {
let clarification = err.clarification;
const ifNotCritical = clarification && clarification.ifNotCritical;
let message = err.message || '';
while( clarification ) {
message = (clarification && (clarification.message + ' ')) + message;
clarification = clarification.prev;
}
message = message.trim();
setStatusTo(
`<span style="color:red">
${ifNotCritical ? 'Некритичная ошибка.' : 'Ошибка!'}
</span>
<br/>
<span style="font-size: 0.9em; color: darkred">${message}</span>
<a href class="link-button">
[Ещё&nbsp;подробнее]
</a>`
);
getStatus().querySelector('.link-button').onclick = function() {
errorHandlers.viewErrorVoid(err);
return false;
};
};
const enableDisableInputs = function() {
const inputs = document.querySelectorAll('input');
for ( let i = 0; i < inputs.length; i++ ) {
inputs[i].disabled = !inputs[i].disabled;
}
};
const conduct = (beforeStatus, operation, afterStatus, onSuccess) => {
setStatusTo(beforeStatus);
enableDisableInputs();
operation((err) => {
if (err) {
showError(err);
} else {
setStatusTo(afterStatus);
onSuccess && onSuccess();
}
enableDisableInputs();
});
};
const ul = document.querySelector('#list-of-providers');
const _firstChild = ul.firstChild;
for(
const providerKey of Object.keys(antiCensorRu.pacProviders).sort()
) {
const li = document.createElement('li');
li.innerHTML = `
<input type="radio" name="pacProvider" id="${providerKey}">
<label for="${providerKey}">${providerKey}</label>
<a href class="link-button checked-radio-panel"
id="update-${providerKey}">[обновить]</a>`;
li.querySelector('.link-button').onclick =
() => {
conduct(
'Обновляем...', (cb) => antiCensorRu.syncWithPacProviderAsync(cb),
'Обновлено.'
);
return false;
};
ul.insertBefore( li, _firstChild );
}
checkChosenProvider();
const radios = [].slice.apply(
document.querySelectorAll('[name=pacProvider]')
);
for(const radio of radios) {
radio.onclick = function(event) {
if (
event.target.id === (antiCensorRu.currentPacProviderKey || 'none')
) {
return false;
}
const pacKey = event.target.id;
if (pacKey === 'none') {
conduct(
'Отключение...',
(cb) => antiCensorRu.clearPacAsync(cb),
'Отключено.',
checkChosenProvider
);
} else {
conduct(
'Установка...',
(cb) => antiCensorRu.installPacAsync(pacKey, cb),
'PAC-скрипт установлен.',
checkChosenProvider
);
}
return false;
};
}
const conpanel = document.getElementById('list-of-handlers');
errorHandlers.getEventsMap().forEach( (value, name) => {
const li = document.createElement('li');
li.innerHTML = `
<input type="checkbox" id="if-on-${name}"/>
<label for="if-on-${name}">${value}</label>`;
const box = li.querySelector('input');
box.checked = backgroundPage.apis.errorHandlers.isOn(name);
box.onclick = function() {
const id = this.id.replace('if-on-', '');
return backgroundPage.apis.errorHandlers.switchVoid(
this.checked ? 'on' : 'off',
id
);
};
conpanel.appendChild(li);
});
if( errorHandlers.ifNotControlled ) {
document.getElementById('which-extension').innerHTML
= backgroundPage.utils.messages.whichExtensionHtml();
document.querySelectorAll('.if-not-controlled').forEach( (node) => {
node.style.display = 'block';
});
}
setStatusTo('');
if (antiCensorRu.ifFirstInstall) {
const id = antiCensorRu.currentPacProviderKey || 'none';
document.querySelector('#update-' + id).click();
}
document.documentElement.style.display = '';
})
);

View File

@ -29,6 +29,7 @@
<nav> <nav>
<button id="read-button">READ</button> <button id="read-button">READ</button>
<button id="save-button">SAVE</button> <button id="save-button">SAVE</button>
<button id="clear-button">CLEAR</button>
<span id="status">Press READ button to read PAC from settings</span> <span id="status">Press READ button to read PAC from settings</span>
</nav> </nav>
<div id="editor"></div> <div id="editor"></div>

View File

@ -14,7 +14,7 @@ chrome.proxy.settings.onChange.addListener(
(details) => setStatusTo(red( details.levelOfControl + '!') ) (details) => setStatusTo(red( details.levelOfControl + '!') )
); );
document.querySelector('#read-button').onclick = () => { function _read() {
chrome.proxy.settings.get({}, (details) => { chrome.proxy.settings.get({}, (details) => {
@ -30,7 +30,9 @@ document.querySelector('#read-button').onclick = () => {
}); });
}; }
document.querySelector('#read-button').onclick = _read;
document.querySelector('#save-button').onclick = () => { document.querySelector('#save-button').onclick = () => {
@ -45,3 +47,14 @@ document.querySelector('#save-button').onclick = () => {
}; };
document.querySelector('#clear-button').onclick = () => {
chrome.proxy.settings.clear({}, () => {
alert('Cleared! Reading...');
_read();
});
};

View File

Before

Width:  |  Height:  |  Size: 77 KiB

After

Width:  |  Height:  |  Size: 77 KiB

View File

Before

Width:  |  Height:  |  Size: 85 KiB

After

Width:  |  Height:  |  Size: 85 KiB