|
import path from 'path' |
|
import fs from 'fs-extra' |
|
|
|
import { readConfigJsonAsync } from '@expo/config' |
|
|
|
import * as ExponentTools from '@expo/xdl/build/detach/ExponentTools' |
|
import StandaloneContext from '@expo/xdl/build/detach/StandaloneContext' |
|
import * as IosPlist from '@expo/xdl/build/detach/IosPlist' |
|
// @ts-ignore IosWorkspace not yet converted to TypeScript |
|
import * as IosWorkspace from '@expo/xdl/build/detach/IosWorkspace' |
|
|
|
const projectRoot = path.resolve(__dirname, '..') |
|
const exportedAndroidManifset = path.resolve(projectRoot, 'exported-assets/android-index.json') |
|
const exportedIosManifset = path.resolve(projectRoot, 'exported-assets/ios-index.json') |
|
const exportedBundles = path.resolve(projectRoot, 'exported-assets/bundles') |
|
const releaseChannel = 'ejected-automation' |
|
|
|
;(async () => { |
|
const { exp } = await readConfigJsonAsync(projectRoot) |
|
|
|
// manifest *must* come from `exp.host`, otherwise the android app will crash with |
|
// Could not load app: java.lang.Exception: Could not load embedded manifest. Are you sure this experience has been published? |
|
// java.lang.NullPointerException: Attempt to invoke virtual method 'int java.lang.String.length()' on a null object reference |
|
const manifestBaseUrl = '//exp.host/@me/project' |
|
const manifestUrl = 'https:' + manifestBaseUrl |
|
const manifestInitialUrl = 'exp:' + manifestBaseUrl |
|
const androidManifest = await readJSON(exportedAndroidManifset) |
|
const iosManifest = await readJSON(exportedIosManifset) |
|
|
|
if (exp.ios && exp.ios.publishManifestPath) { |
|
iosManifest.updates = { enabled: false } |
|
|
|
iosManifest.releaseChannel = releaseChannel |
|
|
|
await writeJSON(exp.ios.publishManifestPath, iosManifest) |
|
const exportedIosBundle = path.resolve(exportedBundles, iosManifest.bundleUrl.replace(/^.+\/bundles\//, '')) |
|
await copyFile(exportedIosBundle, exp.ios.publishBundlePath) |
|
|
|
const context = StandaloneContext.createUserContext(projectRoot, exp) |
|
const { supportingDirectory } = IosWorkspace.getPaths(context) |
|
await IosPlist.modifyAsync(supportingDirectory, 'EXShell', (shellPlist: any) => { |
|
shellPlist.releaseChannel = releaseChannel |
|
shellPlist.areRemoteUpdatesEnabled = false |
|
shellPlist.manifestUrl = manifestInitialUrl |
|
return shellPlist |
|
}) |
|
} |
|
|
|
if (exp.android && exp.android.publishManifestPath) { |
|
androidManifest.updates = { enabled: false } |
|
|
|
androidManifest.releaseChannel = releaseChannel |
|
|
|
await writeJSON(exp.android.publishManifestPath, androidManifest) |
|
const exportedAndroidBundle = path.resolve(exportedBundles, androidManifest.bundleUrl.replace(/^.+\/bundles\//, '')) |
|
await copyFile(exportedAndroidBundle, exp.android.publishBundlePath) |
|
|
|
const constantsPath = path.join( |
|
projectRoot, |
|
'android', |
|
'app', |
|
'src', |
|
'main', |
|
'java', |
|
'host', |
|
'exp', |
|
'exponent', |
|
'generated', |
|
'AppConstants.java', |
|
) |
|
await ExponentTools.deleteLinesInFileAsync( |
|
'START EMBEDDED RESPONSES', |
|
'END EMBEDDED RESPONSES', |
|
constantsPath, |
|
) |
|
await ExponentTools.regexFileAsync( |
|
'// ADD EMBEDDED RESPONSES HERE', |
|
`// ADD EMBEDDED RESPONSES HERE |
|
// START EMBEDDED RESPONSES |
|
embeddedResponses.add(new Constants.EmbeddedResponse("${manifestUrl}", "assets://shell-app-manifest.json", "application/json")); |
|
embeddedResponses.add(new Constants.EmbeddedResponse("${androidManifest.bundleUrl}", "assets://shell-app.bundle", "application/javascript")); |
|
// END EMBEDDED RESPONSES`, |
|
constantsPath, |
|
) |
|
await ExponentTools.regexFileAsync( |
|
/RELEASE_CHANNEL = "[^"]*"/, |
|
`RELEASE_CHANNEL = "${releaseChannel}"`, |
|
constantsPath, |
|
) |
|
await ExponentTools.regexFileAsync( |
|
/ARE_REMOTE_UPDATES_ENABLED = true/, |
|
'ARE_REMOTE_UPDATES_ENABLED = false', |
|
constantsPath, |
|
) |
|
await ExponentTools.regexFileAsync( |
|
/INITIAL_URL = "[^"]*"/, |
|
`INITIAL_URL = "${manifestInitialUrl}"`, |
|
constantsPath, |
|
) |
|
|
|
const mainActivitiyPath = path.join( |
|
projectRoot, |
|
'android', |
|
'app', |
|
'src', |
|
'main', |
|
'java', |
|
'host', |
|
'exp', |
|
'exponent', |
|
'MainActivity.java', |
|
) |
|
await ExponentTools.regexFileAsync( |
|
/return "exp:\/\/[^"]*";/, |
|
`return "${manifestInitialUrl}";`, |
|
mainActivitiyPath, |
|
) |
|
} |
|
})() |
|
|
|
async function readJSON (source: string) { |
|
const content = await fs.readFile(source, 'utf8') |
|
return JSON.parse(content) |
|
} |
|
|
|
async function writeJSON (target: string, data: any) { |
|
const content = JSON.stringify(data) |
|
await fs.writeFile(target, content, 'utf8') |
|
} |
|
|
|
async function copyFile (source: string, target: string) { |
|
const content = await fs.readFile(source) |
|
await fs.writeFile(target, content) |
|
} |
opened expo/expo#6683 to inquire for possible fix in expo cli