|
|
|
@@ -59,8 +59,6 @@ const braveExtensionMessagesPath = path.resolve(path.join(srcDir, 'brave', 'comp
|
|
|
|
|
const braveRewardsExtensionMessagesPath = path.resolve(path.join(srcDir, 'brave', 'components', 'brave_rewards', 'resources', 'extension', 'brave_rewards', '_locales', 'en_US', 'messages.json'))
|
|
|
|
|
const braveAndroidBraveStringsPath = path.resolve(path.join(srcDir, 'brave', 'browser', 'ui', 'android', 'strings', 'android_brave_strings.grd'))
|
|
|
|
|
|
|
|
|
|
const srcGit = path.resolve(path.join(srcDir, '.git'))
|
|
|
|
|
|
|
|
|
|
// Helper function to find all grdp parts in a grd.
|
|
|
|
|
function getGrdPartsFromGrd(path) {
|
|
|
|
|
const grd = new JSDOM(fs.readFileSync(path, 'utf8'))
|
|
|
|
@@ -73,21 +71,17 @@ function getGrdPartsFromGrd(path) {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Helper function to create a mapping for grd and all of its grdp parts.
|
|
|
|
|
function AddGrd(chromiumPath, bravePath, exclude = new Set()) {
|
|
|
|
|
if (!fs.existsSync(srcGit)) {
|
|
|
|
|
// Chromium repository has not been initialized yet.
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
function addGrd(chromiumPath, bravePath, exclude = new Set()) {
|
|
|
|
|
if (verboseLogFindGrd)
|
|
|
|
|
console.log("Adding mappings for GRD: " + chromiumPath)
|
|
|
|
|
if (!fs.existsSync(chromiumPath)) {
|
|
|
|
|
const err = new Error(`addGrd: Error. File not found at path "${chromiumPath}"`)
|
|
|
|
|
console.error(err)
|
|
|
|
|
throw err
|
|
|
|
|
}
|
|
|
|
|
let mapping = {
|
|
|
|
|
[chromiumPath]: bravePath
|
|
|
|
|
}
|
|
|
|
|
if (!fs.existsSync(chromiumPath)) {
|
|
|
|
|
const err = new Error(`AddGrd: Error. File not found at path "${chromiumPath}"`)
|
|
|
|
|
console.error(err)
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
const grdps = getGrdPartsFromGrd(chromiumPath)
|
|
|
|
|
if (grdps.length) {
|
|
|
|
|
const chromiumDir = path.dirname(chromiumPath)
|
|
|
|
@@ -104,102 +98,6 @@ function AddGrd(chromiumPath, bravePath, exclude = new Set()) {
|
|
|
|
|
return mapping
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Add all GRD mappings here.
|
|
|
|
|
// Brave specific only grd and grdp files should NOT be added.
|
|
|
|
|
// Using AddGrd will add GRD and all of its GRDPs.
|
|
|
|
|
// TODO(petemill): Do not do this file processing in the module root, do it behind a function.
|
|
|
|
|
console.log(chalk.italic('Recursing through GRD to find GRDP files...'))
|
|
|
|
|
const grdsWithAutoAddedGrdps = {
|
|
|
|
|
...AddGrd(chromiumComponentsStringsPath, braveComponentsStringsPath),
|
|
|
|
|
...AddGrd(chromiumGeneratedResourcesPath, braveGeneratedResourcesPath, chromiumGeneratedResourcesExcludes),
|
|
|
|
|
...AddGrd(androidChromeStringsPath, braveAndroidChromeStringsPath)
|
|
|
|
|
}
|
|
|
|
|
console.log(chalk.italic('Done recursing through GRD to find GRDP files.'))
|
|
|
|
|
|
|
|
|
|
// When adding new grd or grdp files, never add a grdp part path without a parent grd path.
|
|
|
|
|
// Group them with a leading and trailing newline to keep this file organized.
|
|
|
|
|
// The first 3 are added explicitly because we change the file names.
|
|
|
|
|
const chromiumToAutoGeneratedBraveMapping = {
|
|
|
|
|
[chromiumStringsPath]: braveStringsPath,
|
|
|
|
|
[chromiumSettingsPartPath]: braveSettingsPartPath,
|
|
|
|
|
|
|
|
|
|
[chromiumComponentsChromiumStringsPath]: braveComponentsBraveStringsPath,
|
|
|
|
|
|
|
|
|
|
...grdsWithAutoAddedGrdps
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Same as with chromiumToAutoGeneratedBraveMapping but maps in the opposite direction
|
|
|
|
|
module.exports.autoGeneratedBraveToChromiumMapping = Object.keys(chromiumToAutoGeneratedBraveMapping)
|
|
|
|
|
.reduce((obj, key) => ({ ...obj, [chromiumToAutoGeneratedBraveMapping[key]]: key }), {})
|
|
|
|
|
|
|
|
|
|
// All paths which are not generated
|
|
|
|
|
module.exports.braveNonGeneratedPaths = [
|
|
|
|
|
braveSpecificGeneratedResourcesPath, braveResourcesComponentsStringsPath, braveExtensionMessagesPath, braveRewardsExtensionMessagesPath, braveAndroidBraveStringsPath
|
|
|
|
|
]
|
|
|
|
|
|
|
|
|
|
// All paths which are generated
|
|
|
|
|
module.exports.braveAutoGeneratedPaths = Object.values(chromiumToAutoGeneratedBraveMapping)
|
|
|
|
|
|
|
|
|
|
// Brave specific strings and Chromium mapped Brave strings will be here.
|
|
|
|
|
// But you only need to add the Brave specific strings manually here.
|
|
|
|
|
module.exports.allBravePaths = module.exports.braveNonGeneratedPaths.concat(module.exports.braveAutoGeneratedPaths)
|
|
|
|
|
|
|
|
|
|
// Get all GRD and JSON paths whether they are generatd or not
|
|
|
|
|
// Push and pull scripts for l10n use this.
|
|
|
|
|
// Transifex manages files per grd and not per grd or grdp.
|
|
|
|
|
// This is because only 1 xtb is created per grd per locale even if it has multiple grdp files.
|
|
|
|
|
module.exports.braveTopLevelPaths = module.exports.allBravePaths.filter((x) => ['grd', 'json'].includes(x.split('.').pop()))
|
|
|
|
|
|
|
|
|
|
// Helper function to retrieve ethereum-remote-client paths relative
|
|
|
|
|
// to the Brave paths
|
|
|
|
|
module.exports.getEthereumRemoteClientPaths = function (extensionPath) {
|
|
|
|
|
let basePath = extensionPath
|
|
|
|
|
if (!basePath) {
|
|
|
|
|
basePath = '../../../ethereum-remote-client'
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return [
|
|
|
|
|
`${basePath}/app/_locales/en/messages.json`
|
|
|
|
|
]
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Helper function to retrieve Greaselion script paths relative to the
|
|
|
|
|
// Brave paths.
|
|
|
|
|
//
|
|
|
|
|
// Greaselion.json consists of an array of Greaselion rules,
|
|
|
|
|
// specifying scripts to inject into given sites based on certain
|
|
|
|
|
// preconditions. If the rule contains a "messages" key, then the
|
|
|
|
|
// script contains user-visible strings that require translation. This
|
|
|
|
|
// helper function gathers those messages.json files for transmission
|
|
|
|
|
// to Transifex.
|
|
|
|
|
module.exports.getGreaselionScriptPaths = function (extensionPath) {
|
|
|
|
|
let basePath = extensionPath
|
|
|
|
|
if (!basePath) {
|
|
|
|
|
basePath = '../../../brave-site-specific-scripts'
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const jsonContent = fs.readFileSync(`${basePath}/Greaselion.json`, 'utf8')
|
|
|
|
|
if (!jsonContent) {
|
|
|
|
|
console.error('Missing Greaselion.json')
|
|
|
|
|
return []
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const greaselionRules = JSON.parse(jsonContent)
|
|
|
|
|
if (!greaselionRules) {
|
|
|
|
|
console.error('Malformed Greaselion.json')
|
|
|
|
|
return []
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
let paths = []
|
|
|
|
|
greaselionRules.forEach((rule) => {
|
|
|
|
|
if (rule.messages) {
|
|
|
|
|
paths.push(`${basePath}/${rule.messages}/en_US/messages.json`)
|
|
|
|
|
}
|
|
|
|
|
})
|
|
|
|
|
|
|
|
|
|
return paths
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Helper functions that's, for a given pair of chromium to brave GRD mapping
|
|
|
|
|
// from the supplied map, determines which GRDP parts are no longer present in
|
|
|
|
|
// the chromium GRD file.
|
|
|
|
@@ -223,30 +121,161 @@ function getRemovedGRDParts(mapping) {
|
|
|
|
|
return removedMap
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Helper function to pretty print removed GRDP file names.
|
|
|
|
|
module.exports.logRemovedGRDParts = function (mapping) {
|
|
|
|
|
if (mapping.size) {
|
|
|
|
|
console.log("\n**************************************************************************")
|
|
|
|
|
console.log("The following GRDP files are no longer in the corresponding Chromium GRDs:\n")
|
|
|
|
|
for (const [grd, grdps] of mapping.entries()) {
|
|
|
|
|
console.log(" From " + grd + ":")
|
|
|
|
|
for (const grdp of grdps) {
|
|
|
|
|
console.log(" - " + grdp)
|
|
|
|
|
}
|
|
|
|
|
// Add all GRD mappings here.
|
|
|
|
|
function getAutoGeneratedGrdMappings() {
|
|
|
|
|
if (typeof(getAutoGeneratedGrdMappings.mappings) === 'undefined') {
|
|
|
|
|
console.log(chalk.italic('Recursing through GRD to find GRDP files...'))
|
|
|
|
|
// Brave specific only grd and grdp files should NOT be added.
|
|
|
|
|
// Using AddGrd will add GRD and all of its GRDPs.
|
|
|
|
|
getAutoGeneratedGrdMappings.mappings = {
|
|
|
|
|
...addGrd(chromiumComponentsStringsPath, braveComponentsStringsPath),
|
|
|
|
|
...addGrd(chromiumGeneratedResourcesPath, braveGeneratedResourcesPath, chromiumGeneratedResourcesExcludes),
|
|
|
|
|
...addGrd(androidChromeStringsPath, braveAndroidChromeStringsPath)
|
|
|
|
|
}
|
|
|
|
|
console.log(chalk.italic('Done recursing through GRD to find GRDP files.'))
|
|
|
|
|
}
|
|
|
|
|
return getAutoGeneratedGrdMappings.mappings
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// This simply reads Chromium files that are passed to it and replaces branding strings
|
|
|
|
|
// with Brave specific branding strings.
|
|
|
|
|
// Do not use this for filtering XML, instead use chromium-rebase-l10n.py.
|
|
|
|
|
// Only add idempotent replacements here (i.e. don't append replace A with AX here)
|
|
|
|
|
module.exports.rebaseBraveStringFilesOnChromiumL10nFiles = async function (path) {
|
|
|
|
|
const removedMap = getRemovedGRDParts(grdsWithAutoAddedGrdps)
|
|
|
|
|
const ops = Object.entries(chromiumToAutoGeneratedBraveMapping).map(async ([sourcePath, destPath]) => {
|
|
|
|
|
let contents = await new Promise(resolve => fs.readFile(sourcePath, 'utf8', (err, data) => resolve(data)))
|
|
|
|
|
await new Promise(resolve => fs.writeFile(destPath, contents, 'utf8', resolve))
|
|
|
|
|
})
|
|
|
|
|
await Promise.all(ops)
|
|
|
|
|
return removedMap
|
|
|
|
|
function getChromiumToAutoGeneratedBraveMapping() {
|
|
|
|
|
if (typeof(getChromiumToAutoGeneratedBraveMapping.mapping) === 'undefined') {
|
|
|
|
|
// When adding new grd or grdp files, never add a grdp part path without a parent grd path.
|
|
|
|
|
// Group them with a leading and trailing newline to keep this file organized.
|
|
|
|
|
// The first 3 are added explicitly because we change the file names.
|
|
|
|
|
getChromiumToAutoGeneratedBraveMapping.mapping = {
|
|
|
|
|
[chromiumStringsPath]: braveStringsPath,
|
|
|
|
|
[chromiumSettingsPartPath]: braveSettingsPartPath,
|
|
|
|
|
|
|
|
|
|
[chromiumComponentsChromiumStringsPath]: braveComponentsBraveStringsPath,
|
|
|
|
|
|
|
|
|
|
...getAutoGeneratedGrdMappings()
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
return getChromiumToAutoGeneratedBraveMapping.mapping
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const l10nUtil = {
|
|
|
|
|
// Same as with chromiumToAutoGeneratedBraveMapping but maps in the opposite direction
|
|
|
|
|
getAutoGeneratedBraveToChromiumMapping: () => {
|
|
|
|
|
if (typeof(l10nUtil.getAutoGeneratedBraveToChromiumMapping.mapping) === 'undefined') {
|
|
|
|
|
const chromiumToAutoGeneratedBraveMapping = getChromiumToAutoGeneratedBraveMapping()
|
|
|
|
|
l10nUtil.getAutoGeneratedBraveToChromiumMapping.mapping = Object.keys(
|
|
|
|
|
chromiumToAutoGeneratedBraveMapping).reduce((obj, key) => (
|
|
|
|
|
{ ...obj, [chromiumToAutoGeneratedBraveMapping[key]]: key }), {})
|
|
|
|
|
}
|
|
|
|
|
return l10nUtil.getAutoGeneratedBraveToChromiumMapping.mapping
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// All paths which are generated
|
|
|
|
|
getBraveAutoGeneratedPaths: () => {
|
|
|
|
|
return Object.values(getChromiumToAutoGeneratedBraveMapping())
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// All paths which are not generated
|
|
|
|
|
getBraveNonGeneratedPaths: () => {
|
|
|
|
|
if (typeof(l10nUtil.getBraveNonGeneratedPaths.paths) === 'undefined') {
|
|
|
|
|
l10nUtil.getBraveNonGeneratedPaths.paths = [
|
|
|
|
|
braveSpecificGeneratedResourcesPath,
|
|
|
|
|
braveResourcesComponentsStringsPath,
|
|
|
|
|
braveExtensionMessagesPath,
|
|
|
|
|
braveRewardsExtensionMessagesPath,
|
|
|
|
|
braveAndroidBraveStringsPath
|
|
|
|
|
]
|
|
|
|
|
}
|
|
|
|
|
return l10nUtil.getBraveNonGeneratedPaths.paths
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// Brave specific strings and Chromium mapped Brave strings will be here.
|
|
|
|
|
// But you only need to add the Brave specific strings manually here.
|
|
|
|
|
getAllBravePaths: () => {
|
|
|
|
|
return l10nUtil.getBraveNonGeneratedPaths().concat(l10nUtil.getBraveAutoGeneratedPaths())
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// Get all GRD and JSON paths whether they are generatd or not
|
|
|
|
|
// Push and pull scripts for l10n use this.
|
|
|
|
|
// Transifex manages files per grd and not per grd or grdp.
|
|
|
|
|
// This is because only 1 xtb is created per grd per locale even if it has multiple grdp files.
|
|
|
|
|
getBraveTopLevelPaths: () => {
|
|
|
|
|
return l10nUtil.getAllBravePaths().filter((x) => ['grd', 'json'].includes(x.split('.').pop()))
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// Helper function to retrieve ethereum-remote-client paths relative
|
|
|
|
|
// to the Brave paths
|
|
|
|
|
getEthereumRemoteClientPaths: (extensionPath) => {
|
|
|
|
|
let basePath = extensionPath
|
|
|
|
|
if (!basePath) {
|
|
|
|
|
basePath = '../../../ethereum-remote-client'
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return [
|
|
|
|
|
`${basePath}/app/_locales/en/messages.json`
|
|
|
|
|
]
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// Helper function to retrieve Greaselion script paths relative to the
|
|
|
|
|
// Brave paths.
|
|
|
|
|
//
|
|
|
|
|
// Greaselion.json consists of an array of Greaselion rules,
|
|
|
|
|
// specifying scripts to inject into given sites based on certain
|
|
|
|
|
// preconditions. If the rule contains a "messages" key, then the
|
|
|
|
|
// script contains user-visible strings that require translation. This
|
|
|
|
|
// helper function gathers those messages.json files for transmission
|
|
|
|
|
// to Transifex.
|
|
|
|
|
getGreaselionScriptPaths: (extensionPath) => {
|
|
|
|
|
let basePath = extensionPath
|
|
|
|
|
if (!basePath) {
|
|
|
|
|
basePath = '../../../brave-site-specific-scripts'
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const jsonContent = fs.readFileSync(`${basePath}/Greaselion.json`, 'utf8')
|
|
|
|
|
if (!jsonContent) {
|
|
|
|
|
console.error('Missing Greaselion.json')
|
|
|
|
|
return []
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const greaselionRules = JSON.parse(jsonContent)
|
|
|
|
|
if (!greaselionRules) {
|
|
|
|
|
console.error('Malformed Greaselion.json')
|
|
|
|
|
return []
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
let paths = []
|
|
|
|
|
greaselionRules.forEach((rule) => {
|
|
|
|
|
if (rule.messages) {
|
|
|
|
|
paths.push(`${basePath}/${rule.messages}/en_US/messages.json`)
|
|
|
|
|
}
|
|
|
|
|
})
|
|
|
|
|
|
|
|
|
|
return paths
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// Helper function to pretty print removed GRDP file names.
|
|
|
|
|
logRemovedGRDParts: (mapping) => {
|
|
|
|
|
if (mapping.size) {
|
|
|
|
|
console.log("\n**************************************************************************")
|
|
|
|
|
console.log("The following GRDP files are no longer in the corresponding Chromium GRDs:\n")
|
|
|
|
|
for (const [grd, grdps] of mapping.entries()) {
|
|
|
|
|
console.log(" From " + grd + ":")
|
|
|
|
|
for (const grdp of grdps) {
|
|
|
|
|
console.log(" - " + grdp)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
// This simply reads Chromium files that are passed to it and replaces branding strings
|
|
|
|
|
// with Brave specific branding strings.
|
|
|
|
|
// Do not use this for filtering XML, instead use chromium-rebase-l10n.py.
|
|
|
|
|
// Only add idempotent replacements here (i.e. don't append replace A with AX here)
|
|
|
|
|
rebaseBraveStringFilesOnChromiumL10nFiles: async (path) => {
|
|
|
|
|
const removedMap = getRemovedGRDParts(getAutoGeneratedGrdMappings())
|
|
|
|
|
const ops = Object.entries(getChromiumToAutoGeneratedBraveMapping()).map(async ([sourcePath, destPath]) => {
|
|
|
|
|
let contents = await new Promise(resolve => fs.readFile(sourcePath, 'utf8', (err, data) => resolve(data)))
|
|
|
|
|
await new Promise(resolve => fs.writeFile(destPath, contents, 'utf8', resolve))
|
|
|
|
|
})
|
|
|
|
|
await Promise.all(ops)
|
|
|
|
|
return removedMap
|
|
|
|
|
},
|
|
|
|
|
} // const l10nUtil
|
|
|
|
|
|
|
|
|
|
module.exports = l10nUtil
|
|
|
|
|