-
Notifications
You must be signed in to change notification settings - Fork 0
/
apply.ts
92 lines (74 loc) · 2.87 KB
/
apply.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
import { join } from 'node:path'
import { readFileSync, unlinkSync, existsSync, writeFileSync } from 'node:fs'
import { EOL } from 'node:os'
import { SpawnSyncReturns } from 'node:child_process'
import glob from 'fast-glob'
import { basePath, log } from './helper'
const removeRejectedFiles = (location: string) => {
const rejectedFiles = glob.sync(['android/**/*.rej', 'ios/**/*.rej'], {
dot: true,
cwd: location,
})
rejectedFiles.forEach((fileName) => {
const filePath = join(location, fileName)
unlinkSync(filePath)
})
}
const collectRejectedHunks = (location: string) => {
const rejectedFiles = glob.sync(['android/**/*.rej', 'ios/**/*.rej'], {
dot: true,
cwd: location,
})
const rejectedHunks = []
rejectedFiles.forEach((fileName) => {
const filePath = join(location, fileName)
const originalFileName = fileName.replace('.rej', '')
let contents = readFileSync(filePath, 'utf-8')
if (contents) {
// Inject file header, so that it can be applied like a patch.
const contentsSplitByLine = contents.split(/\r?\n/)
contentsSplitByLine.splice(1, 0, `--- a/${originalFileName}\n+++ b/${originalFileName}`)
contents = contentsSplitByLine.join(EOL)
rejectedHunks.push(contents)
}
unlinkSync(filePath)
})
return rejectedHunks
}
export const applyPatch = (
location: string,
git: (...args: string[]) => SpawnSyncReturns<Buffer>
) => {
const patchPath = join(basePath(), 'patch/current.patch')
const rejectedHunksPath = join(basePath(), 'patch/rejected-hunks.patch')
if (existsSync(rejectedHunksPath)) {
log(
'Removing patch/rejected-hunks.patch, assuming appropriate changes have been made in current.patch'
)
}
// https://git-scm.com/docs/git-apply
git('apply', '--reject', patchPath)
let rejectedHunks = collectRejectedHunks(location)
if (rejectedHunks.length) {
writeFileSync(rejectedHunksPath, rejectedHunks.join(EOL))
// Check if some of the rejected hunks have already been applied, by applying them in reverse.
git('apply', '--reject', '--reverse', rejectedHunksPath)
unlinkSync(rejectedHunksPath)
rejectedHunks = collectRejectedHunks(location)
// Fully apply patch again, to restore previous reverses and ignoring rejcts.
git('apply', '--reject', patchPath)
removeRejectedFiles(location)
if (rejectedHunks.length) {
writeFileSync(rejectedHunksPath, rejectedHunks.join(EOL))
log('Unable to apply some changes in the patch')
log('Problematic parts have been moved to patch/rejected-hunks.patch')
log('There are two ways to fix this:')
log('1) Fix the problematic parts in patch/current.patch and try again')
log(
'2) Manually apply the proper changes in /ios or /android and run"npx numic patch" to update the patch and then try again'
)
return
}
}
log('Patch successfully applied')
}