[macOS] use SourceKit to ensure that all public symbols are exported
This commit is contained in:
4
Makefile
4
Makefile
@@ -277,6 +277,10 @@ idocument:
|
||||
darwin-style-code:
|
||||
node platform/darwin/scripts/generate-style-code.js
|
||||
style-code: darwin-style-code
|
||||
|
||||
.PHONY: check-public-symbols
|
||||
check-public-symbols:
|
||||
node platform/darwin/scripts/check-public-symbols.js macOS
|
||||
endif
|
||||
|
||||
#### Linux targets #####################################################
|
||||
|
||||
83
platform/darwin/scripts/check-public-symbols.js
Executable file
83
platform/darwin/scripts/check-public-symbols.js
Executable file
@@ -0,0 +1,83 @@
|
||||
#!/usr/bin/env node
|
||||
|
||||
'use strict';
|
||||
|
||||
const fs = require('fs');
|
||||
const path = require('path');
|
||||
const execFileSync = require('child_process').execFileSync;
|
||||
const _ = require('lodash');
|
||||
|
||||
const keyword = /\bMGL_EXPORT\b/;
|
||||
|
||||
let scanned = [];
|
||||
|
||||
function hasMissingSymbols(os) {
|
||||
let missing = false;
|
||||
let sdk = os === 'iOS' ? 'iphonesimulator' : 'macosx';
|
||||
let sysroot = execFileSync('xcrun', ['--show-sdk-path', '--sdk', sdk]).toString().trim();
|
||||
let umbrellaPath = `platform/${os.toLowerCase()}/src/Mapbox.h`;
|
||||
let docArgs = ['doc', '--objc', umbrellaPath, '--',
|
||||
'-x', 'objective-c', '-I', 'platform/darwin/src/', '-isysroot', sysroot];
|
||||
let docStr = execFileSync('sourcekitten', docArgs).toString().trim();
|
||||
let docJson = JSON.parse(docStr);
|
||||
_.forEach(docJson, function (result) {
|
||||
_.forEach(result, function (structure, path) {
|
||||
// Prevent multiple scans of the same file.
|
||||
if (scanned.indexOf(path) >= 0) return;
|
||||
scanned.push(path);
|
||||
|
||||
const src = fs.readFileSync(path, 'utf8').split('\n');
|
||||
_.forEach(structure['key.substructure'], function (substructure) {
|
||||
switch (substructure['key.kind']) {
|
||||
case 'sourcekitten.source.lang.objc.decl.class':
|
||||
if (!(keyword.test(src[substructure['key.doc.line'] - 1]) || keyword.test(src[substructure['key.doc.line'] - 2]))) {
|
||||
console.warn(`- missing symbol export for class ${substructure['key.name']} in ${path}:${substructure['key.doc.line']}:${substructure['key.doc.column']}`);
|
||||
missing = true;
|
||||
}
|
||||
break;
|
||||
case 'sourcekitten.source.lang.objc.decl.constant':
|
||||
if (!keyword.test(src[substructure['key.doc.line'] - 1])) {
|
||||
console.warn(`- missing symbol export for constant ${substructure['key.name']} in ${path}:${substructure['key.doc.line']}:${substructure['key.doc.column']}`);
|
||||
missing = true;
|
||||
}
|
||||
break;
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
return missing;
|
||||
}
|
||||
|
||||
function ensureSourceKittenIsInstalled() {
|
||||
try {
|
||||
execFileSync('which', ['sourcekitten']);
|
||||
} catch (e) {
|
||||
console.log(`Installing SourceKitten via Homebrew…`);
|
||||
execFileSync('brew', ['install', 'sourcekitten']);
|
||||
}
|
||||
}
|
||||
|
||||
if (process.argv.length < 3) {
|
||||
console.warn(`Usage: ${path.relative(process.cwd(), process.argv[1])} [macOS|iOS] ...`);
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
ensureSourceKittenIsInstalled();
|
||||
|
||||
let missing = false;
|
||||
for (var i = 2; i < process.argv.length; i++) {
|
||||
let os = process.argv[i];
|
||||
if (os == 'iOS' || os == 'macOS') {
|
||||
missing |= hasMissingSymbols(os);
|
||||
} else {
|
||||
console.warn(`Argument must be one of iOS or macOS`);
|
||||
process.exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
if (missing) {
|
||||
process.exit(1);
|
||||
} else {
|
||||
console.warn(`All symbols are correctly exported.`);
|
||||
}
|
||||
@@ -75,3 +75,6 @@ sed -n -e '/^## /,$p' platform/macos/CHANGELOG.md > "${OUTPUT}/CHANGELOG.md"
|
||||
|
||||
step "Generating API documentation…"
|
||||
make xdocument OUTPUT="${OUTPUT}/documentation"
|
||||
|
||||
step "Checking that all public symbols are exported…"
|
||||
node platform/darwin/scripts/check-public-symbols.js macOS
|
||||
|
||||
Reference in New Issue
Block a user