From c1ab0cf81615e036c3e55f152108aafc197043c9 Mon Sep 17 00:00:00 2001 From: Jonathan Ruddell Date: Mon, 26 Aug 2019 14:38:43 -0700 Subject: [PATCH] replace patchInFile with a wrapped method so failing doesn't exit --- src/boilerplate/files.js | 15 ++++++----- src/entity/files.js | 43 +++++++++++++++--------------- src/lib/patch-needle.js | 13 +++++++++ src/lib/react-native-navigation.js | 24 ++++++++--------- 4 files changed, 55 insertions(+), 40 deletions(-) create mode 100644 src/lib/patch-needle.js diff --git a/src/boilerplate/files.js b/src/boilerplate/files.js index 8917ab5ca..278c6bcd1 100644 --- a/src/boilerplate/files.js +++ b/src/boilerplate/files.js @@ -8,6 +8,7 @@ module.exports = async function (context, props, jhipsterConfig) { const { filesystem, ignite, print, strings } = context const { camelCase, upperFirst } = strings const spinner = print.spin(`using the ${print.colors.blue('JHipster')} boilerplate`).succeed() + const { patchNeedle } = require('../lib/patch-needle') // this is needed because the "upgrade "command is run from within an app, while the "new" command is run from one level deeper // if the ignite/ignite.json file exists (created below), it's an upgrade, otherwise it's a new app @@ -183,7 +184,7 @@ module.exports = async function (context, props, jhipsterConfig) { }) const keycloakConfigFile = 'src/main/docker/realm-config/jhipster-realm.json' if (fs.existsSync(`${jhipsterPathPrefix}${props.jhipsterDirectory}/${keycloakConfigFile}`)) { - await ignite.patchInFile(`${jhipsterPathPrefix}${props.jhipsterDirectory}/${keycloakConfigFile}`, + await patchNeedle(context, `${jhipsterPathPrefix}${props.jhipsterDirectory}/${keycloakConfigFile}`, { replace: `"dev.localhost.ionic:*"`, insert: `"dev.localhost.ionic:*", "${props.name.toLowerCase()}://*"` @@ -192,7 +193,7 @@ module.exports = async function (context, props, jhipsterConfig) { } const securityConfigFile = 'SecurityConfiguration' if (isMonolith && fs.existsSync(`${jhipsterPathPrefix}${props.jhipsterDirectory}/src/main/java/${props.packageFolder}/config/${securityConfigFile}.java`)) { - await ignite.patchInFile(`${jhipsterPathPrefix}${props.jhipsterDirectory}/src/main/java/${props.packageFolder}/config/${securityConfigFile}.java`, + await patchNeedle(context, `${jhipsterPathPrefix}${props.jhipsterDirectory}/src/main/java/${props.packageFolder}/config/${securityConfigFile}.java`, { replace: '.antMatchers("/api/**").authenticated()', insert: '.antMatchers("/api/auth-info").permitAll()\n .antMatchers("/api/**").authenticated()' @@ -203,7 +204,7 @@ module.exports = async function (context, props, jhipsterConfig) { const androidAuthRedirectContent = ` manifestPlaceholders = [ appAuthRedirectScheme: '${props.name.toLowerCase()}' ]` - await ignite.patchInFile('android/app/build.gradle', { + await patchNeedle(context, 'android/app/build.gradle', { before: 'applicationId', insert: androidAuthRedirectContent, match: androidAuthRedirectContent @@ -264,7 +265,7 @@ end spinner.text = '▸ setting up websocket code' spinner.start() // import ChatRedux in redux/index.js - await ignite.patchInFile('app/shared/reducers/index.js', { + await patchNeedle(context, 'app/shared/reducers/index.js', { before: 'ignite-jhipster-redux-store-import-needle', insert: ` chat: require('../../modules/chat/chat.reducer').reducer,`, match: ` chat: require('../../modules/chat/chat.reducer').reducer,` @@ -274,7 +275,7 @@ end // wire ChatScreen in NavigationRouter // const navigationRouterFilePath = `${process.cwd()}/app/navigation/navigation-router.js` // const navigationImportEdit = `import ChatScreen from '../modules/chat/chat-screen'` - // await ignite.patchInFile(navigationRouterFilePath, { + // await patchNeedle(context, navigationRouterFilePath, { // before: 'ignite-jhipster-navigation-import-needle', // insert: navigationImportEdit, // match: navigationImportEdit @@ -282,7 +283,7 @@ end // // // add chat screen to navigation // const navigationScreen = ` ` - // await ignite.patchInFile(navigationRouterFilePath, { + // await patchNeedle(context, navigationRouterFilePath, { // before: 'ignite-jhipster-navigation-needle', // insert: navigationScreen, // match: navigationScreen @@ -290,7 +291,7 @@ end // copy the WebsocketConfiguration.java to the jhipsterDirectory if (fs.existsSync(`${jhipsterPathPrefix}${props.jhipsterDirectory}/src/main/java/${props.packageFolder}/config/WebsocketConfiguration.java`)) { - await ignite.patchInFile(`${jhipsterPathPrefix}${props.jhipsterDirectory}/src/main/java/${props.packageFolder}/config/WebsocketConfiguration.java`, { replace: '"/websocket/tracker"', insert: '"/websocket/tracker", "/websocket/chat"' }) + await patchNeedle(context, `${jhipsterPathPrefix}${props.jhipsterDirectory}/src/main/java/${props.packageFolder}/config/WebsocketConfiguration.java`, { replace: '"/websocket/tracker"', insert: '"/websocket/tracker", "/websocket/chat"' }) } spinner.stop() } else { diff --git a/src/entity/files.js b/src/entity/files.js index d3207af52..a2bceef42 100644 --- a/src/entity/files.js +++ b/src/entity/files.js @@ -5,6 +5,7 @@ module.exports = async function (generator, igniteContext) { const semver = require('semver') const pluralize = require('pluralize') const fs = require('fs-extra') + const { patchNeedle } = require('../lib/patch-needle') const { getEntityFormField, getRelationshipFormField } = require('../lib/entity-helpers') const { ignite, strings, parameters, print } = igniteContext const { kebabCase, pascalCase, snakeCase, upperCase, camelCase, isBlank, upperFirst } = strings // eslint-disable-line @@ -163,42 +164,42 @@ module.exports = async function (generator, igniteContext) { } // add methods to api - ignite.patchInFile(apiFilePath, { + await patchNeedle(igniteContext, apiFilePath, { before: 'ignite-jhipster-api-method-needle', insert: apiMethods, match: apiMethods }) - ignite.patchInFile(apiFilePath, { + await patchNeedle(igniteContext, apiFilePath, { before: 'ignite-jhipster-api-export-needle', insert: apiMethodsExport, match: apiMethodsExport }) - ignite.patchInFile(fixtureApiFilePath, { + await patchNeedle(igniteContext, fixtureApiFilePath, { before: 'ignite-jhipster-api-fixture-needle', insert: fixtureApiMethods, match: fixtureApiMethods }) // import redux in redux/index.js - ignite.patchInFile(reduxIndexFilePath, { + await patchNeedle(igniteContext, reduxIndexFilePath, { before: 'ignite-jhipster-redux-store-import-needle', insert: ` ${camelCase(props.pluralName)}: require('../../modules/entities/${props.kebabName}/${props.kebabName}.reducer').reducer,`, match: ` ${camelCase(props.pluralName)}: require('../../modules/entities/${props.kebabName}/${props.kebabName}.reducer').reducer,` }) // import saga/redux in sagas/index.js - ignite.patchInFile(sagaIndexFilePath, { + await patchNeedle(igniteContext, sagaIndexFilePath, { before: 'ignite-jhipster-saga-redux-import-needle', insert: `import { ${props.name}Types } from '../../modules/entities/${props.kebabName}/${props.kebabName}.reducer'`, match: `import { ${props.name}Types } from '../../modules/entities/${props.kebabName}/${props.kebabName}.reducer'` }) - ignite.patchInFile(sagaIndexFilePath, { + await patchNeedle(igniteContext, sagaIndexFilePath, { before: 'ignite-jhipster-saga-method-import-needle', insert: `import { get${props.name}, get${props.pluralName}, update${props.name}, delete${props.name}${props.searchEngine ? `, search${props.pluralName}` : ''} } from '../../modules/entities/${props.kebabName}/${props.kebabName}.sagas'`, match: `import { get${props.name}, get${props.pluralName}, update${props.name}, delete${props.name}${props.searchEngine ? `, search${props.pluralName}` : ''} } from '../../modules/entities/${props.kebabName}/${props.kebabName}.sagas'` }) - ignite.patchInFile(sagaIndexFilePath, { + await patchNeedle(igniteContext, sagaIndexFilePath, { before: 'ignite-jhipster-saga-redux-connect-needle', insert: sagaConnections, match: sagaConnections @@ -282,19 +283,19 @@ module.exports = async function (generator, igniteContext) { // import entity screens to navigation const navigationImport = `import ${props.name}EntityScreen from '../modules/entities/${props.kebabName}/${props.kebabName}-entity-screen'` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-import-needle', insert: navigationImport, match: navigationImport }) const navigationImportDetail = `import ${props.name}EntityDetailScreen from '../modules/entities/${props.kebabName}/${props.kebabName}-entity-detail-screen'` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-import-needle', insert: navigationImportDetail, match: navigationImportDetail }) const navigationImportEdit = `import ${props.name}EntityEditScreen from '../modules/entities/${props.kebabName}/${props.kebabName}-entity-edit-screen'` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-import-needle', insert: navigationImportEdit, match: navigationImportEdit @@ -305,19 +306,19 @@ module.exports = async function (generator, igniteContext) { // import entity screens to navigation const navigationDeclaration = `export const ${upperSnakeCaseName} = 'nav.${props.name}EntityScreen'` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-declaration-needle', insert: navigationDeclaration, match: navigationDeclaration }) const navigationDeclarationDetail = `export const ${upperSnakeCaseNameDetail} = 'nav.${props.name}EntityDetailScreen'` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-declaration-needle', insert: navigationDeclarationDetail, match: navigationDeclarationDetail }) const navigationDeclarationEdit = `export const ${upperSnakeCaseNameEdit} = 'nav.${props.name}EntityEditScreen'` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-declaration-needle', insert: navigationDeclarationEdit, match: navigationDeclarationEdit @@ -325,19 +326,19 @@ module.exports = async function (generator, igniteContext) { // add entity screens to navigation const navigationScreen = ` Navigation.registerComponentWithRedux(${upperSnakeCaseName}, () => ${props.name}EntityScreen, Provider, store)` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-registration-needle', insert: navigationScreen, match: navigationScreen }) const navigationScreenDetail = ` Navigation.registerComponentWithRedux(${upperSnakeCaseNameDetail}, () => ${props.name}EntityDetailScreen, Provider, store)` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-registration-needle', insert: navigationScreenDetail, match: navigationScreenDetail }) const navigationScreenEdit = ` Navigation.registerComponentWithRedux(${upperSnakeCaseNameEdit}, () => ${props.name}EntityEditScreen, Provider, store)` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-registration-needle', insert: navigationScreenEdit, match: navigationScreenEdit @@ -399,30 +400,30 @@ export const ${camelCase(props.name)}EntityEditScreen = (data) => Navigation.pus } } })` - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-method-needle', insert: navigationMethodMain, match: navigationMethodMain }) - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-method-needle', insert: navigationMethodEdit, match: navigationMethodEdit }) - ignite.patchInFile(navigationRouterFilePath, { + await patchNeedle(igniteContext, navigationRouterFilePath, { before: 'ignite-jhipster-navigation-method-needle', insert: navigationMethodDetail, match: navigationMethodDetail }) // add entity to entities screen const entityScreenButton = ` ` - ignite.patchInFile(entityScreenFilePath, { + await patchNeedle(igniteContext, entityScreenFilePath, { before: 'ignite-jhipster-entity-screen-needle', insert: entityScreenButton, match: entityScreenButton }) const entityScreenImport = ` ${camelCase(props.name)}EntityScreen,` - ignite.patchInFile(entityScreenFilePath, { + await patchNeedle(igniteContext, entityScreenFilePath, { before: 'ignite-jhipster-entity-screen-import-needle', insert: entityScreenImport, match: entityScreenImport diff --git a/src/lib/patch-needle.js b/src/lib/patch-needle.js new file mode 100644 index 000000000..5df6de3f3 --- /dev/null +++ b/src/lib/patch-needle.js @@ -0,0 +1,13 @@ + +const patchNeedle = async (context, filePath, params) => { + const { ignite, print } = context + try { + await ignite.patchInFile(filePath, params) + } catch (e) { + print.warning(`Could not find insertion point in ${filePath}:\n${params.before}`) + } +} + +module.exports = { + patchNeedle +} diff --git a/src/lib/react-native-navigation.js b/src/lib/react-native-navigation.js index 641d79fdf..d06635976 100644 --- a/src/lib/react-native-navigation.js +++ b/src/lib/react-native-navigation.js @@ -1,3 +1,5 @@ +const { patchNeedle } = require('../lib/patch-needle') + const patchReactNativeNavigation = async (context = {}, props) => { // REACT_NATIVE_NAVIGATION_VERSION const { @@ -39,9 +41,8 @@ const patchReactNativeNavigation = async (context = {}, props) => { await updateAndroidFiles(context, props) } const updateIosFiles = async (context, props) => { - const { ignite } = context /*eslint-disable */ - await ignite.patchInFile(`${process.cwd()}/ios/${props.name}/Info.plist`, { + await patchNeedle(context, `${process.cwd()}/ios/${props.name}/Info.plist`, { before: `CFBundleDisplayName`, insert: ` CFBundleURLTypes @@ -62,22 +63,21 @@ const updateIosFiles = async (context, props) => { } const updateAndroidFiles = async (context, props) => { - const { ignite } = context // settings.gradle - await ignite.patchInFile(`${process.cwd()}/android/settings.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/settings.gradle`, { after: `include ':app'`, insert: `include ':react-native-navigation'\nproject(':react-native-navigation').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-navigation/lib/android/app/')` }) // build.gradle - await ignite.patchInFile(`${process.cwd()}/android/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/build.gradle`, { before: `mavenLocal()`, insert: ` google() mavenCentral() maven { url 'https://jitpack.io' }` }) - await ignite.patchInFile(`${process.cwd()}/android/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/build.gradle`, { after: `repositories {`, insert: ` google() mavenLocal() @@ -85,23 +85,23 @@ const updateAndroidFiles = async (context, props) => { }) // react-native-init uses a later version so this is not currently needed - // await ignite.patchInFile(`${process.cwd()}/android/build.gradle`, { + // await patchNeedle(context, `${process.cwd()}/android/build.gradle`, { // replace: `buildToolsVersion = "26.0.3"`, // insert: `buildToolsVersion = "28.0.3"` // }) - await ignite.patchInFile(`${process.cwd()}/android/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/build.gradle`, { replace: `minSdkVersion = 16`, insert: `minSdkVersion = 19` }) // app/build.gradle - await ignite.patchInFile(`${process.cwd()}/android/app/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/app/build.gradle`, { after: `versionCode 1`, insert: ` missingDimensionStrategy "RNN.reactNativeVersion", "reactNative57_5"` }) - await ignite.patchInFile(`${process.cwd()}/android/app/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/app/build.gradle`, { before: `buildTypes {`, insert: ` compileOptions { sourceCompatibility JavaVersion.VERSION_1_8 @@ -109,7 +109,7 @@ const updateAndroidFiles = async (context, props) => { }` }) - await ignite.patchInFile(`${process.cwd()}/android/app/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/app/build.gradle`, { before: `dependencies {`, insert: `configurations.all { resolutionStrategy.eachDependency { DependencyResolveDetails details -> @@ -120,7 +120,7 @@ const updateAndroidFiles = async (context, props) => { } }` }) - await ignite.patchInFile(`${process.cwd()}/android/app/build.gradle`, { + await patchNeedle(context, `${process.cwd()}/android/app/build.gradle`, { after: `dependencies {`, insert: ` implementation "com.facebook.react:react-native:+" // From node_modules