mirror of
https://github.com/LalleSX/4chan-XZ.git
synced 2026-01-30 09:48:12 +01:00
clean up
This commit is contained in:
parent
b25d2023ca
commit
3a102f64d7
6263
CHANGELOG.md
6263
CHANGELOG.md
File diff suppressed because it is too large
Load Diff
@ -1,49 +0,0 @@
|
||||
## Reporting bugs
|
||||
|
||||
Bug reports and feature requests for 4chan X are tracked at **https://github.com/ccd0/4chan-x/issues?q=is%3Aopen+sort%3Aupdated-desc**.
|
||||
|
||||
You can submit a bug report / feature request via your Github account.
|
||||
|
||||
If you're reporting a bug, the more detail you can give, the better. If I can't reproduce your bug, I probably won't be able to fix it. You can help by doing the following:
|
||||
|
||||
1. Include precise steps to reproduce the problem, with the expected and actual results.
|
||||
2. Make sure your browser, 4chan X, and userscript manager (e.g. Greasemonkey, ViolentMoney, or Tampermonkey) are up to date. **Include the versions you're using in bug reports.**
|
||||
3. Open your console with Shift+Control+J (⇧⌘J on OS X Firefox, ⌘⌥J on OS X Chromium), and **look for error messages**, especially ones that occur at the same time as the bug. Include these in your bug report. If you're using Firefox, be sure to check the browser console (Shift+Control+J), not just the web console (Shift+Control+K) as errors may not show up in the latter. Messages about "Content Security Policy" are expected and can be ignored.
|
||||
4. If other people (including me) aren't having your problem, **test whether it happens in a fresh profile**. Here are instructions for [Firefox](https://support.mozilla.org/en-US/kb/profile-manager-create-and-remove-firefox-profiles) and [Chromium](https://developer.chrome.com/devtools/docs/clean-testing-environment).
|
||||
5. **Please mention any other extensions / scripts you are using.** To check if a bug is due to a conflict with another extension, temporarily disable any other extensions and userscripts. If the bug goes away, turn them back on one by one until you find the one causing the problem.
|
||||
6. To test if the bug occurs under the default settings or only with specific settings, back up your settings and reset them using the **Export** and **Reset Settings** links in the settings panel. If the bug only occurs under specific settings, upload your exported settings to a site like https://paste.installgentoo.com/, and link to it in your bug report. If your settings contains sensitive information (e.g. personas), edit the text file manually.
|
||||
7. Test if the bug occurs using the **native extension** with 4chan X disabled. If it does, it's likely a problem with 4chan or your browser rather than with 4chan X.
|
||||
|
||||
## Development & Contribution
|
||||
|
||||
### Get started
|
||||
|
||||
- Install [git](https://git-scm.com/), [node.js](https://nodejs.org/), [npm](https://www.npmjs.com/) (usually distributed with node), and GNU Make (on Windows, the [MinGW](http://www.mingw.org/) port will work, and the [GnuWin](http://gnuwin32.sourceforge.net/) port has been reported to work as well).
|
||||
- Clone 4chan X: `git clone https://github.com/ccd0/4chan-x.git`<br>(If this is taking too long, you can add `--depth 100` to fetch only recent history.)
|
||||
- Open the directory: `cd 4chan-x`
|
||||
- Fetch needed dependencies with: `npm install`
|
||||
|
||||
### Build
|
||||
|
||||
- Build with `make`.
|
||||
|
||||
### Contribute
|
||||
|
||||
- 4chan X is mostly written in [CoffeeScript](http://coffeescript.org/). If you're already familiar with Javascript, it doesn't take long to pick up.
|
||||
- Edit the sources in the src/ directory (not the compiled scripts in builds/).
|
||||
- Fetch needed dependencies with: `npm install`
|
||||
- Compile the script with: `make`
|
||||
- Install the compiled script (found in the testbuilds/ directory), and test your changes.
|
||||
- Make sure you have set your name and email as you want them, as they will be published in your commit message:<br>`git config user.name yourname`<br>`git config user.email youremail`
|
||||
- Commit your changes: `git commit -a`
|
||||
- Open a pull request by doing any of the following:
|
||||
- Fork this repository on Github, push your changes to your fork, and make a pull request through the Github website.
|
||||
- Push your changes to any online Git repository, and send an email with an explanation of your changes and the URL, branch, and commit you want me to pull from.
|
||||
- Export your changes via `git bundle` (e.g. `git bundle create file.bundle master..your-branch`), and upload them to a file host. Then send an email with an explanation of your changes and the URL of the file.
|
||||
|
||||
Pull requests to archive.json should be sent upstream: https://github.com/4chenz/archives.json
|
||||
4chan X updates from there automatically.
|
||||
|
||||
### More info
|
||||
|
||||
Further documentation is available at https://github.com/ccd0/4chan-x/wiki/Developer-Documentation.
|
||||
@ -1 +0,0 @@
|
||||
Chromium 73.0.3683.75 built on Debian buster/sid, running on Debian buster/sid
|
||||
74
template.jst
74
template.jst
@ -1,74 +0,0 @@
|
||||
<!doctype html>
|
||||
<html><head>
|
||||
<meta charset="utf-8">
|
||||
<title>4chan X</title>
|
||||
<link rel="stylesheet" href="web.css">
|
||||
<link rel="icon" href="img/icon.gif">
|
||||
<link rel="chrome-webstore-item" href="https://chrome.google.com/webstore/detail/ohnjgmpcibpbafdlkimncjhflgedgpam">
|
||||
</head><body>
|
||||
<div id="header">
|
||||
<h1 id="4chan-x">4chan X</h1>
|
||||
<div id="links">
|
||||
<a href="https://github.com/ccd0/4chan-x">Source Code</a>
|
||||
<a href="https://github.com/ccd0/4chan-x/blob/master/CHANGELOG.md">Changelog</a>
|
||||
<a href="https://github.com/ccd0/4chan-x/wiki/Frequently-Asked-Questions">FAQ</a>
|
||||
<a href="https://github.com/ccd0/4chan-x/wiki/Privacy">Privacy</a>
|
||||
<a href="https://github.com/ccd0/4chan-x/issues">Report Bugs</a>
|
||||
</div>
|
||||
</div>
|
||||
<a class="screenshot" href="img/screenshot.png"><img src="img/screenshot.png" alt="Screenshot"></a>
|
||||
<%=
|
||||
content
|
||||
.match(/<\/h1>([^]*)<h2 id="more-information"/)[1]
|
||||
.replace(
|
||||
/(<h3 id="(.*?)">)(.*?)(<\/h3>[^]*?)(?=<h)/g,
|
||||
'<input hidden type="checkbox" id="$2-hide"><div>$1<label for="$2-hide">$3</label>$4</div>'
|
||||
)
|
||||
%>
|
||||
<script>
|
||||
function imagePreview() {
|
||||
this.removeEventListener('mouseover', imagePreview, false);
|
||||
var img = new Image();
|
||||
img.src = this.href;
|
||||
img.alt = 'preview';
|
||||
var span = document.createElement('span');
|
||||
span.className = 'hover';
|
||||
span.appendChild(img);
|
||||
this.parentNode.insertBefore(span, this.nextSibling);
|
||||
}
|
||||
function storeInstall(e) {
|
||||
if (!e.shiftKey && !e.altKey && !e.ctrlKey && !e.metaKey && e.button === 0) {
|
||||
var url = this.href;
|
||||
chrome.webstore.install(url, function(){}, function(){
|
||||
location.href = url;
|
||||
});
|
||||
e.preventDefault();
|
||||
}
|
||||
}
|
||||
for (var i = 0; i < document.links.length; i++) {
|
||||
var link = document.links[i];
|
||||
if (/\.png$/.test(link.pathname) && !link.querySelector('.hover')) {
|
||||
link.addEventListener('mouseover', imagePreview, false);
|
||||
} else if (window.chrome && link.host === 'chrome.google.com') {
|
||||
link.addEventListener('click', storeInstall, false);
|
||||
}
|
||||
}
|
||||
var engine = (function() {
|
||||
if (/Edge\//.test(navigator.userAgent)) return 'edge';
|
||||
if (/Chrome\//.test(navigator.userAgent)) return 'blink';
|
||||
if (/WebKit\//.test(navigator.userAgent)) return 'webkit';
|
||||
if (/Gecko\/|Goanna/.test(navigator.userAgent)) return 'gecko';
|
||||
if (/Presto\//.test(navigator.userAgent)) return 'presto';
|
||||
})();
|
||||
var engines = {'firefox': 'gecko', 'chromium': 'blink presto', 'safari': 'webkit', 'webkitgtk-qtwebkit-qtwebengine': 'webkit', 'ms-edge': 'edge', 'other-browsers': ''};
|
||||
if (location.hash.slice(1) in engines) {
|
||||
for (browser in engines) {
|
||||
document.getElementById(browser + '-hide').checked = (browser !== location.hash.slice(1));
|
||||
}
|
||||
} else if (engine) {
|
||||
for (browser in engines) {
|
||||
document.getElementById(browser + '-hide').checked = (engines[browser].indexOf(engine) < 0);
|
||||
}
|
||||
}
|
||||
</script>
|
||||
</body></html>
|
||||
@ -1,6 +0,0 @@
|
||||
{
|
||||
"esnext": true,
|
||||
"undef": true,
|
||||
"unused": true,
|
||||
"node": true
|
||||
}
|
||||
@ -1,19 +0,0 @@
|
||||
#!/usr/bin/env python3
|
||||
import urllib.request, urllib.error, json
|
||||
banners = []
|
||||
for ext in ['jpg', 'png', 'gif']:
|
||||
for i in range(300):
|
||||
banner = str(i) + '.' + ext
|
||||
req = urllib.request.Request('http://s.4cdn.org/image/title/' + banner, method='HEAD')
|
||||
try:
|
||||
try:
|
||||
status = urllib.request.urlopen(req).status
|
||||
except urllib.error.URLError:
|
||||
status = urllib.request.urlopen(req).status
|
||||
except urllib.error.HTTPError as e:
|
||||
status = e.status
|
||||
print(banner, status)
|
||||
if status == 200:
|
||||
banners.append(banner)
|
||||
with open('src/config/banners.json', 'w') as f:
|
||||
f.write(json.dumps(banners))
|
||||
@ -1,26 +0,0 @@
|
||||
var fs = require('fs');
|
||||
|
||||
function bump(version, level) {
|
||||
var parts = version.split('.');
|
||||
var i;
|
||||
for (i = 0; i < level; i++) {
|
||||
parts[i] = (parts[i] || '0');
|
||||
}
|
||||
parts[level-1] = +parts[level-1] + 1;
|
||||
for (i = level; i < parts.length; i++) {
|
||||
parts[i] = '0';
|
||||
}
|
||||
return parts.join('.');
|
||||
}
|
||||
|
||||
function setversion(version) {
|
||||
var data = {version: version, date: new Date()};
|
||||
fs.writeFileSync('version.json', JSON.stringify(data, null, 2));
|
||||
}
|
||||
|
||||
var level = +process.argv[2];
|
||||
var v = JSON.parse(fs.readFileSync('version.json', 'utf8'));
|
||||
var oldversion = v.version;
|
||||
var version = bump(oldversion, level);
|
||||
setversion(version);
|
||||
console.log(`Version updated from v${oldversion} to v${version}.`);
|
||||
@ -1,30 +0,0 @@
|
||||
var fs = require('fs');
|
||||
var template = require('./template.js');
|
||||
var coffee = require('coffeescript');
|
||||
|
||||
for (var name of process.argv.slice(2)) {
|
||||
try {
|
||||
var parts = name.match(/^tmp\/([^_]*)(?:_(.*))?-(.*)\.(.*)\.js$/);
|
||||
var sourceName = `src/${parts[1]}/${parts[3]}.${parts[4]}`;
|
||||
var script = fs.readFileSync(sourceName, 'utf8');
|
||||
script = script.replace(/\r\n/g, '\n');
|
||||
script = template(script, {type: parts[2]}, sourceName);
|
||||
if (parts[4] === 'coffee') {
|
||||
var definesVar = /^[$A-Z][$\w]*$/.test(parts[3]);
|
||||
if (definesVar) {
|
||||
script = `${script}\nreturn ${parts[3]};\n`;
|
||||
}
|
||||
script = coffee.compile(script);
|
||||
if (definesVar) {
|
||||
script = `${parts[3]} = ${script}`;
|
||||
}
|
||||
}
|
||||
script += '\n';
|
||||
fs.writeFileSync(name, script);
|
||||
} catch (err) {
|
||||
console.error(`Error processing ${name}`);
|
||||
throw err;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1,18 +0,0 @@
|
||||
var fs = require('fs');
|
||||
|
||||
var names = [];
|
||||
for (var d of fs.readdirSync('src')) {
|
||||
for (var f of fs.readdirSync(`src/${d}`)) {
|
||||
var m = f.match(/^([$A-Z][$\w]*)\.(?:coffee|js)$/);
|
||||
if (m) names.push(m[1]);
|
||||
}
|
||||
}
|
||||
var decl = `var ${names.sort().join(', ')};\n`;
|
||||
var oldDecl;
|
||||
try {
|
||||
oldDecl = fs.readFileSync('tmp/declaration.js', 'utf8');
|
||||
} catch(err) {
|
||||
}
|
||||
if (decl !== oldDecl) {
|
||||
fs.writeFileSync('tmp/declaration.js', decl, 'utf8');
|
||||
}
|
||||
@ -1,10 +0,0 @@
|
||||
var fs = require('fs');
|
||||
var md = require('markdown-it')({linkify: true}).use(require('markdown-it-anchor'), {slugify: s => String(s).trim().toLowerCase().replace(/\W+/g, '-')});
|
||||
var template = require('lodash.template');
|
||||
|
||||
var readme = fs.readFileSync('README.md', 'utf8');
|
||||
var content = md.render(readme);
|
||||
var webtemplate = fs.readFileSync('template.jst', 'utf8');
|
||||
var output = template(webtemplate)({content: content});
|
||||
output = output.replace(/\r\n/g, '\n');
|
||||
fs.writeFileSync('test.html', output);
|
||||
@ -1,247 +0,0 @@
|
||||
/* jshint evil: true */
|
||||
var fs = require('fs');
|
||||
var path = require('path');
|
||||
var _template = require('lodash.template');
|
||||
var esprima = require('esprima');
|
||||
|
||||
// disable ES6 delimiters
|
||||
var _templateSettings = {interpolate: /<%=([\s\S]+?)%>/g};
|
||||
|
||||
// Functions used in templates.
|
||||
var tools = {};
|
||||
|
||||
var read = tools.read = filename => fs.readFileSync(filename, 'utf8').replace(/\r\n/g, '\n');
|
||||
var readJSON = tools.readJSON = filename => JSON.parse(read(filename));
|
||||
tools.readBase64 = filename => fs.readFileSync(filename).toString('base64');
|
||||
|
||||
tools.readHTML = function(filename) {
|
||||
var text = read(filename).replace(/^ +/gm, '').replace(/\r?\n/g, '');
|
||||
text = _template(text, _templateSettings)(pkg); // package.json data only; no recursive imports
|
||||
return tools.html(text);
|
||||
};
|
||||
|
||||
tools.multiline = function(text) {
|
||||
return text.replace(/\n+/g, '\n').split(/^/m).map(JSON.stringify).join('+').replace(/"\+"/g, '\\\n');
|
||||
};
|
||||
|
||||
// Convert JSONify-able object to Javascript expression.
|
||||
var constExpression = data => JSON.stringify(data).replace(/`/g, '\\`');
|
||||
|
||||
function TextStream(text) {
|
||||
this.text = text;
|
||||
}
|
||||
|
||||
TextStream.prototype.eat = function(regexp) {
|
||||
var match = regexp.exec(this.text);
|
||||
if (match && match.index === 0) {
|
||||
this.text = this.text.slice(match[0].length);
|
||||
}
|
||||
return match;
|
||||
};
|
||||
|
||||
function parseHTMLTemplate(stream, context) {
|
||||
var template = stream.text; // text from beginning, for error messages
|
||||
var expression = new HTMLExpression(context);
|
||||
var match;
|
||||
|
||||
try {
|
||||
|
||||
while (stream.text) {
|
||||
// Literal HTML
|
||||
if ((match = stream.eat(
|
||||
// characters not indicating start or end of placeholder, using backslash as escape
|
||||
/^(?:[^\\{}]|\\.)+(?!{)/
|
||||
))) {
|
||||
var unescaped = match[0].replace(/\\(.)/g, '$1');
|
||||
expression.addLiteral(unescaped);
|
||||
|
||||
// Placeholder
|
||||
} else if ((match = stream.eat(
|
||||
// symbol identifying placeholder type and first argument (enclosed by {})
|
||||
// backtick not allowed in arguments as it can end embedded JS in Coffeescript
|
||||
/^([^}]){([^}`]*)}/
|
||||
))) {
|
||||
var type = match[1];
|
||||
var args = [match[2]];
|
||||
if (type === '?') {
|
||||
// conditional expression can take up to two subtemplate arguments
|
||||
for (var i = 0; i < 2 && stream.eat(/^{/); i++) {
|
||||
var subtemplate = parseHTMLTemplate(stream, context);
|
||||
args.push(subtemplate);
|
||||
if (!stream.eat(/^}/)) {
|
||||
throw new Error(`Unexpected characters in subtemplate (${stream.text})`);
|
||||
}
|
||||
}
|
||||
}
|
||||
expression.addPlaceholder(new Placeholder(type, args));
|
||||
|
||||
// No match: end of subtemplate (} next) or error
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return expression.build();
|
||||
|
||||
} catch(err) {
|
||||
throw new Error(`${err.message}: ${template}`);
|
||||
}
|
||||
}
|
||||
|
||||
function HTMLExpression(context) {
|
||||
this.parts = [];
|
||||
this.startContext = this.endContext = (context || '');
|
||||
}
|
||||
|
||||
HTMLExpression.prototype.addLiteral = function(text) {
|
||||
this.parts.push(constExpression(text));
|
||||
this.endContext = (
|
||||
this.endContext
|
||||
.replace(/(=['"])[^'"<>]*/g, '$1') // remove values from quoted attributes (no '"<> allowed)
|
||||
.replace(/(<\w+)( [\w-]+((?=[ >])|=''|=""))*/g, '$1') // remove attributes from tags
|
||||
.replace(/^([^'"<>]+|<\/?\w+>)*/, '') // remove text (no '"<> allowed) and tags
|
||||
);
|
||||
};
|
||||
|
||||
HTMLExpression.prototype.addPlaceholder = function(placeholder) {
|
||||
if (!placeholder.allowed(this.endContext)) {
|
||||
throw new Error(`Illegal insertion of placeholder (type ${placeholder.type}) into HTML template (at ${this.endContext})`);
|
||||
}
|
||||
this.parts.push(placeholder.build());
|
||||
};
|
||||
|
||||
HTMLExpression.prototype.build = function() {
|
||||
if (this.startContext !== this.endContext) {
|
||||
throw new Error(`HTML template is ill-formed (at ${this.endContext})`);
|
||||
}
|
||||
return (this.parts.length === 0 ? '""' : this.parts.join(' + '));
|
||||
};
|
||||
|
||||
function Placeholder(type, args) {
|
||||
this.type = type;
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
Placeholder.prototype.allowed = function(context) {
|
||||
switch(this.type) {
|
||||
case '$':
|
||||
// escaped text allowed outside tags or in quoted attributes
|
||||
return (context === '' || /\=['"]$/.test(context));
|
||||
case '&':
|
||||
case '@':
|
||||
// contents of one/many HTML element or template allowed outside tags only
|
||||
return (context === '');
|
||||
case '?':
|
||||
// conditionals allowed anywhere so long as their contents don't change context (checked by HTMLExpression.prototype.build)
|
||||
return true;
|
||||
}
|
||||
throw new Error(`Unrecognized placeholder type (${this.type})`);
|
||||
};
|
||||
|
||||
Placeholder.prototype.build = function() {
|
||||
// first argument is always JS expression; validate it so we don't accidentally break out of placeholders
|
||||
var expr = this.args[0];
|
||||
var ast;
|
||||
try {
|
||||
ast = esprima.parse(expr);
|
||||
} catch (err) {
|
||||
throw new Error(`Invalid JavaScript in template (${expr})`);
|
||||
}
|
||||
if (!(ast.type === 'Program' && ast.body.length == 1 && ast.body[0].type === 'ExpressionStatement')) {
|
||||
throw new Error(`JavaScript in template is not an expression (${expr})`);
|
||||
}
|
||||
switch(this.type) {
|
||||
case '$': return `E(${expr})`; // $ : escaped text
|
||||
case '&': return `(${expr}).innerHTML`; // & : contents of HTML element or template (of form {innerHTML: "safeHTML"})
|
||||
case '@': return `E.cat(${expr})`; // @ : contents of array of HTML elements or templates (see src/General/Globals.coffee for E.cat)
|
||||
case '?':
|
||||
return `((${expr}) ? ${this.args[1] || '""'} : ${this.args[2] || '""'})`; // ? : conditional expression
|
||||
}
|
||||
throw new Error(`Unrecognized placeholder type (${this.type})`);
|
||||
};
|
||||
|
||||
// HTML template generator with placeholders of forms ${}, &{}, @{}, and ?{}{}{} (see Placeholder.prototype.build)
|
||||
// that checks safety of generated expressions at compile time.
|
||||
tools.html = function(template) {
|
||||
var stream = new TextStream(template);
|
||||
var output = parseHTMLTemplate(stream);
|
||||
if (stream.text) {
|
||||
throw new Error(`Unexpected characters in template (${stream.text}): ${template}`);
|
||||
}
|
||||
return `{innerHTML: ${output}}`;
|
||||
};
|
||||
|
||||
function includesDir(templateName) {
|
||||
var dir = path.dirname(templateName);
|
||||
var subdir = path.basename(templateName).replace(/\.[^.]+$/, '');
|
||||
if (fs.readdirSync(dir).indexOf(subdir) >= 0) {
|
||||
return path.join(dir, subdir);
|
||||
} else {
|
||||
return dir;
|
||||
}
|
||||
}
|
||||
|
||||
function resolvePath(includeName, templateName) {
|
||||
var dir;
|
||||
if (includeName[0] === '/') {
|
||||
dir = process.cwd();
|
||||
} else {
|
||||
dir = includesDir(templateName);
|
||||
}
|
||||
return path.join(dir, includeName);
|
||||
}
|
||||
|
||||
function wrapTool(tool, templateName) {
|
||||
return function(includeName) {
|
||||
return tool(resolvePath(includeName, templateName));
|
||||
};
|
||||
}
|
||||
|
||||
function loadModules(templateName) {
|
||||
var dir = includesDir(templateName);
|
||||
var moduleNames = fs.readdirSync(dir).filter(f => /\.inc$/.test(f));
|
||||
var modules = {};
|
||||
for (var name of moduleNames) {
|
||||
var code = read(path.join(dir, name));
|
||||
modules[name.replace(/\.inc$/, '')] = new Function(code)();
|
||||
}
|
||||
return modules;
|
||||
}
|
||||
|
||||
// Import variables from package.json.
|
||||
var pkg = readJSON('package.json');
|
||||
|
||||
function interpolate(text, data, filename) {
|
||||
var context = {}, key;
|
||||
for (key in tools) {
|
||||
context[key] = /^read/.test(key) ? wrapTool(tools[key], filename) : tools[key];
|
||||
}
|
||||
for (key in pkg) {
|
||||
context[key] = pkg[key];
|
||||
}
|
||||
if (data) {
|
||||
for (key in data) {
|
||||
context[key] = data[key];
|
||||
}
|
||||
}
|
||||
context.files = fs.readdirSync(includesDir(filename));
|
||||
context.require = loadModules(filename);
|
||||
return _template(text, _templateSettings)(context);
|
||||
}
|
||||
|
||||
module.exports = interpolate;
|
||||
|
||||
if (require.main === module) {
|
||||
(function() {
|
||||
// Take variables from command line.
|
||||
var data = {};
|
||||
for (var i = 4; i < process.argv.length; i++) {
|
||||
var m = process.argv[i].match(/(.*?)=(.*)/);
|
||||
data[m[1]] = m[2];
|
||||
}
|
||||
|
||||
var text = read(process.argv[2]);
|
||||
text = interpolate(text, data, process.argv[2]);
|
||||
fs.writeFileSync(process.argv[3], text);
|
||||
})();
|
||||
}
|
||||
@ -1,11 +0,0 @@
|
||||
var fs = require('fs');
|
||||
|
||||
var pkg = JSON.parse(fs.readFileSync('package.json', 'utf8'));
|
||||
|
||||
console.log(
|
||||
Object.keys(pkg.devDependencies).filter(
|
||||
name => !/^=/.test(pkg.devDependencies[name])
|
||||
).map(
|
||||
name => `${name}@${process.argv[2] || pkg.devDependencies[name]}`
|
||||
).join(' ')
|
||||
);
|
||||
@ -1,40 +0,0 @@
|
||||
var fs = require('fs');
|
||||
var child_process = require('child_process');
|
||||
|
||||
var pkg = JSON.parse(fs.readFileSync('package.json', 'utf8'));
|
||||
var v = JSON.parse(fs.readFileSync('version.json', 'utf8'));
|
||||
|
||||
var name = pkg.name;
|
||||
var oldVersions = pkg.meta.oldVersions;
|
||||
var version = v.version;
|
||||
var date = v.date;
|
||||
|
||||
var branch = version.replace(/\.\d+$/, '');
|
||||
var headerLevel = branch.replace(/(\.0)*$/, '').split('.').length;
|
||||
var headerPrefix = new Array(headerLevel + 1).join('#');
|
||||
var separator = `${headerPrefix} v${branch}`;
|
||||
|
||||
var today = date.split('T')[0];
|
||||
var filename = `/builds/${name}-noupdate`;
|
||||
var ffLink = `${oldVersions}${version}${filename}.user.js`;
|
||||
var crLink = `${oldVersions}${version}${filename}.crx`;
|
||||
var line = `**v${version}** *(${today})* - [[Userscript](${ffLink})] [[Chrome extension](${crLink})]`;
|
||||
|
||||
var changelog = fs.readFileSync('CHANGELOG.md', 'utf8');
|
||||
|
||||
var breakPos = changelog.indexOf(separator);
|
||||
if (breakPos >= 0) {
|
||||
breakPos += separator.length;
|
||||
} else {
|
||||
breakPos = Math.max(changelog.indexOf('\n\n#'), 0);
|
||||
line = `${separator}\n\n${line}`;
|
||||
}
|
||||
|
||||
var prevVersion = changelog.substr(breakPos).match(/\*\*v([\d\.]+)\*\*/)[1];
|
||||
if (prevVersion.replace(/\.\d+$/, '') !== branch) {
|
||||
line += `\n- Based on v${prevVersion}.`;
|
||||
}
|
||||
line += '\n- ' + child_process.execSync(`git log --pretty=format:%s ${prevVersion}..HEAD`).toString().replace(/\n/g, '\n- ');
|
||||
|
||||
fs.writeFileSync('CHANGELOG.md', `${changelog.substr(0, breakPos)}\n\n${line}${changelog.substr(breakPos)}`, 'utf8');
|
||||
console.log(`Changelog updated for v${version}.`);
|
||||
@ -1,38 +0,0 @@
|
||||
var fs = require('fs');
|
||||
var child_process = require('child_process');
|
||||
var request = require('request');
|
||||
|
||||
var pkg = JSON.parse(fs.readFileSync('package.json', 'utf8'));
|
||||
var v = JSON.parse(child_process.execSync('git show stable:version.json').toString());
|
||||
var secrets = JSON.parse(fs.readFileSync(`../${pkg.meta.path}.keys/chrome-store.json`, 'utf8'));
|
||||
var refresh = JSON.parse(fs.readFileSync(`../${pkg.meta.path}.keys/refresh-token.json`, 'utf8'));
|
||||
|
||||
import('chrome-webstore-upload').then(chromeWebstoreUpload => {
|
||||
var webStore = chromeWebstoreUpload.default({
|
||||
extensionId: pkg.meta.chromeStoreID,
|
||||
clientId: secrets.installed.client_id,
|
||||
clientSecret: secrets.installed.client_secret,
|
||||
refreshToken: refresh.refresh_token
|
||||
});
|
||||
|
||||
request(`https://chrome.google.com/webstore/detail/${pkg.meta.chromeStoreID}`, function (error, response, body) {
|
||||
|
||||
if (body && body.indexOf(`<meta itemprop="version" content="${v.version}"/>`) > 0 && process.argv[2] !== 'force') {
|
||||
console.log(`Version ${v.version} already uploaded.`);
|
||||
return;
|
||||
}
|
||||
|
||||
var myZipFile = fs.createReadStream(`dist/builds/${pkg.name}.zip`);
|
||||
var token;
|
||||
webStore.fetchToken().then(t => {
|
||||
token = t;
|
||||
return webStore.uploadExisting(myZipFile, token);
|
||||
}).then(() =>
|
||||
webStore.publish()
|
||||
).catch(res => {
|
||||
console.error(res);
|
||||
process.exit(1);
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
@ -1,24 +0,0 @@
|
||||
var fs = require('fs');
|
||||
var JSZip = require('jszip');
|
||||
|
||||
var pkg = JSON.parse(fs.readFileSync('package.json', 'utf8'));
|
||||
var v = JSON.parse(fs.readFileSync('version.json', 'utf8'));
|
||||
var channel = process.argv[2] || '';
|
||||
|
||||
var zip = new JSZip();
|
||||
for (var file of ['script.js', 'eventPage.js', 'icon16.png', 'icon48.png', 'icon128.png', 'manifest.json']) {
|
||||
zip.file(
|
||||
file,
|
||||
fs.readFileSync(`testbuilds/crx${channel}/${file}`),
|
||||
{date: new Date(v.date)}
|
||||
);
|
||||
}
|
||||
zip.generateAsync({
|
||||
type: 'nodebuffer',
|
||||
compression: 'DEFLATE',
|
||||
compressionOptions: {level: 9},
|
||||
}).then(function(output) {
|
||||
fs.writeFileSync(`testbuilds/${pkg.name}${channel}.crx.zip`, output);
|
||||
}, function() {
|
||||
process.exit(1);
|
||||
});
|
||||
Loading…
x
Reference in New Issue
Block a user