@wavemaker-ai/wm-reactnative-cli 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. package/README.md +236 -0
  2. package/assets/CLI-EnvironmentVariable.png +0 -0
  3. package/assets/EnvironmentVariable.png +0 -0
  4. package/assets/EnvironmentVariable1.png +0 -0
  5. package/files/ui-build.js +331 -0
  6. package/index.js +381 -0
  7. package/package.json +39 -0
  8. package/src/android.js +479 -0
  9. package/src/command.js +552 -0
  10. package/src/config.js +11 -0
  11. package/src/custom-logger/progress-bar.js +97 -0
  12. package/src/custom-logger/steps.js +117 -0
  13. package/src/custom-logger/task-logger.js +147 -0
  14. package/src/exec.js +73 -0
  15. package/src/expo-launcher.js +596 -0
  16. package/src/ios.js +517 -0
  17. package/src/logger.js +104 -0
  18. package/src/mobileprovision-parse/index.js +72 -0
  19. package/src/project-sync.service.js +390 -0
  20. package/src/requirements.js +250 -0
  21. package/src/utils.js +100 -0
  22. package/src/web-preview-launcher.js +548 -0
  23. package/src/zip.js +19 -0
  24. package/templates/embed/android/ReactNativeAppFragment.java +78 -0
  25. package/templates/embed/android/SplashScreenReactActivityLifecycleListener.kt +41 -0
  26. package/templates/embed/android/fragment_react_native_app.xml +14 -0
  27. package/templates/embed/ios/ReactNativeView.h +12 -0
  28. package/templates/embed/ios/ReactNativeView.m +59 -0
  29. package/templates/embed/ios/ReactNativeView.swift +53 -0
  30. package/templates/expo-camera-patch/useWebQRScanner.js +100 -0
  31. package/templates/ios-build-patch/podFIlePostInstall.js +72 -0
  32. package/templates/package/packageLock.json +14334 -0
  33. package/templates/wm-rn-runtime/App.js +479 -0
  34. package/templates/wm-rn-runtime/App.navigator.js +109 -0
  35. package/test.js +0 -0
  36. package/tools-site/index.html.template +17 -0
  37. package/tools-site/page_background.svg +99 -0
  38. package/tools-site/qrcode.js +614 -0
  39. package/tools-site/styles.css +39 -0
@@ -0,0 +1,78 @@
1
+ package com.wavemaker.reactnative;
2
+
3
+ import android.os.Bundle;
4
+
5
+ import androidx.fragment.app.Fragment;
6
+
7
+ import android.view.LayoutInflater;
8
+ import android.view.View;
9
+ import android.view.ViewGroup;
10
+
11
+ import com.facebook.react.ReactFragment;
12
+ import ${packageName}.R;
13
+
14
+ /**
15
+ * A simple {@link Fragment} subclass.
16
+ * Use the {@link ReactNativeAppFragment#newInstance} factory method to
17
+ * create an instance of this fragment.
18
+ */
19
+ public class ReactNativeAppFragment extends Fragment {
20
+
21
+ // TODO: Rename parameter arguments, choose names that match
22
+ // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
23
+ private static final String PAGE_NAME = "pageName";
24
+
25
+ // TODO: Rename and change types of parameters
26
+ private String pageName;
27
+
28
+ public ReactNativeAppFragment() {
29
+ // Required empty public constructor
30
+ }
31
+
32
+ /**
33
+ * Use this factory method to create a new instance of
34
+ * this fragment using the provided parameters.
35
+ *
36
+ * @param pageName Parameter 2.
37
+ * @return A new instance of fragment ReactNativeAppFragment.
38
+ */
39
+ // TODO: Rename and change types and number of parameters
40
+ public static ReactNativeAppFragment newInstance(String pageName) {
41
+ ReactNativeAppFragment fragment = new ReactNativeAppFragment();
42
+ Bundle args = new Bundle();
43
+ args.putString(PAGE_NAME, pageName);
44
+ fragment.setArguments(args);
45
+ return fragment;
46
+ }
47
+
48
+ @Override
49
+ public void onCreate(Bundle savedInstanceState) {
50
+ super.onCreate(null);
51
+ if (getArguments() != null) {
52
+ pageName = getArguments().getString(PAGE_NAME);
53
+ }
54
+ Fragment reactNativeFragment = new ReactFragment.Builder()
55
+ .setComponentName("main")
56
+ .setLaunchOptions(getLaunchOptions(pageName))
57
+ .setFabricEnabled(false)
58
+ .build();
59
+
60
+ this.getChildFragmentManager().beginTransaction()
61
+ .add(R.id.reactNativeFragment, reactNativeFragment)
62
+ .commit();
63
+ }
64
+
65
+ @Override
66
+ public View onCreateView(LayoutInflater inflater, ViewGroup container,
67
+ Bundle savedInstanceState) {
68
+ setHasOptionsMenu(true);
69
+ // Inflate the layout for this fragment
70
+ return inflater.inflate(R.layout.fragment_react_native_app, container, false);
71
+ }
72
+
73
+ private Bundle getLaunchOptions(String pageName) {
74
+ Bundle initialProperties = new Bundle();
75
+ initialProperties.putString("pageName", pageName);
76
+ return initialProperties;
77
+ }
78
+ }
@@ -0,0 +1,41 @@
1
+ package expo.modules.splashscreen
2
+
3
+ import android.app.Activity
4
+ import android.content.Context
5
+ import android.os.Bundle
6
+ import android.os.Handler
7
+ import com.facebook.react.ReactRootView
8
+ import expo.modules.core.interfaces.ReactActivityLifecycleListener
9
+ import expo.modules.splashscreen.singletons.SplashScreen
10
+
11
+ // this needs to stay for versioning to work
12
+ /* ktlint-disable no-unused-imports */
13
+ import expo.modules.splashscreen.SplashScreenImageResizeMode
14
+ // EXPO_VERSIONING_NEEDS_EXPOVIEW_R
15
+ /* ktlint-enable no-unused-imports */
16
+
17
+ class SplashScreenReactActivityLifecycleListener(activityContext: Context) : ReactActivityLifecycleListener {
18
+ override fun onCreate(activity: Activity, savedInstanceState: Bundle?) {
19
+ // To support backward compatible or SplashScreenImageResizeMode customization
20
+ // that calling `SplashScreen.show()` in MainActivity,
21
+ // we postpone the in-module call to the end of main loop.
22
+ // If MainActivity.onCreate has `SplashScreen.show()`, it will override the call here.
23
+ Handler(activity.mainLooper).post {
24
+ /*SplashScreen.show(
25
+ activity,
26
+ getResizeMode(activity),
27
+ ReactRootView::class.java,
28
+ getStatusBarTranslucent(activity)
29
+ )*/
30
+ }
31
+ }
32
+
33
+ private fun getResizeMode(context: Context): SplashScreenImageResizeMode =
34
+ SplashScreenImageResizeMode.fromString(
35
+ context.getString(R.string.expo_splash_screen_resize_mode).toLowerCase()
36
+ )
37
+ ?: SplashScreenImageResizeMode.CONTAIN
38
+
39
+ private fun getStatusBarTranslucent(context: Context): Boolean =
40
+ context.getString(R.string.expo_splash_screen_status_bar_translucent).toBoolean()
41
+ }
@@ -0,0 +1,14 @@
1
+ <?xml version="1.0" encoding="utf-8"?>
2
+ <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
3
+ xmlns:tools="http://schemas.android.com/tools"
4
+ android:layout_width="match_parent"
5
+ android:layout_height="match_parent"
6
+ tools:context=".ui.ReactNativeAppFragment">
7
+
8
+ <!-- TODO: Update blank fragment layout -->
9
+ <FrameLayout
10
+ android:id="@+id/reactNativeFragment"
11
+ android:layout_width="match_parent"
12
+ android:layout_height="match_parent" />
13
+
14
+ </FrameLayout>
@@ -0,0 +1,12 @@
1
+ #import <Foundation/Foundation.h>
2
+ #import <React/RCTBridgeDelegate.h>
3
+ #import <UIKit/UIKit.h>
4
+
5
+ #import <Expo/Expo.h>
6
+
7
+ @interface ReactNativeView : EXAppDelegateWrapper <RCTBridgeDelegate>
8
+ @property (nonatomic, strong) UIView *view;
9
+
10
+ - (ReactNativeView*) initWithPageName:(NSString *)aPageName;
11
+
12
+ @end
@@ -0,0 +1,59 @@
1
+ #import "ReactNativeView.h"
2
+
3
+ #import <React/RCTBridge.h>
4
+ #import <React/RCTBundleURLProvider.h>
5
+ #import <React/RCTRootView.h>
6
+ #import <React/RCTLinkingManager.h>
7
+ #import <React/RCTConvert.h>
8
+
9
+ #import <RCTAppSetupUtils.h>
10
+
11
+ #if RCT_NEW_ARCH_ENABLED
12
+ #import <React/CoreModulesPlugins.h>
13
+ #import <React/RCTCxxBridgeDelegate.h>
14
+ #import <React/RCTFabricSurfaceHostingProxyRootView.h>
15
+ #import <React/RCTSurfacePresenter.h>
16
+ #import <React/RCTSurfacePresenterBridgeAdapter.h>
17
+ #import <ReactCommon/RCTTurboModuleManager.h>
18
+
19
+ #import <react/config/ReactNativeConfig.h>
20
+
21
+ #endif
22
+
23
+ @implementation ReactNativeView
24
+
25
+ static RCTBridge *bridge;
26
+
27
+ UIView *_view;
28
+
29
+ NSString* pageName = nil;
30
+
31
+ - (ReactNativeView*) initWithPageName:(NSString *)aPageName {
32
+ if (self = [super init]) {
33
+ pageName = aPageName;
34
+ }
35
+ if (!bridge) {
36
+ bridge = [self.reactDelegate createBridgeWithDelegate:self launchOptions: nil];
37
+ }
38
+ _view = [self.reactDelegate createRootViewWithBridge:bridge moduleName:@"main" initialProperties:@{@"pageName": pageName}];
39
+ return self;
40
+ }
41
+
42
+ - (UIView *)view {
43
+ return _view;
44
+ }
45
+
46
+ - (NSArray<id<RCTBridgeModule>> *)extraModulesForBridge:(RCTBridge *)bridge
47
+ {
48
+ // If you'd like to export some custom RCTBridgeModules, add them here!
49
+ return @[];
50
+ }
51
+
52
+ - (NSURL *)sourceURLForBridge:(RCTBridge *)bridge
53
+ {
54
+ return [[NSBundle mainBundle] URLForResource:@"main" withExtension:@"jsbundle"];
55
+ }
56
+
57
+
58
+
59
+ @end
@@ -0,0 +1,53 @@
1
+ import SwiftUI
2
+ import UIKit
3
+ import EmbedCommModule
4
+
5
+ struct ReactNativeSwiftView: UIViewRepresentable {
6
+ var pageName = ""
7
+
8
+ init(pageName: String) {
9
+ self.pageName = pageName;
10
+ }
11
+
12
+ typealias UIViewType = UIView
13
+
14
+ typealias UIViewControllerType = UIViewController
15
+
16
+ func makeUIView(context: Context) -> UIView {
17
+ return ReactNativeView(pageName: self.pageName).view;
18
+ }
19
+ func updateUIView(_ uiView: UIView, context: Context) {
20
+ //
21
+ }
22
+ }
23
+
24
+ @available(iOS 13.0, *)
25
+ struct ReactNativePageView: View {
26
+ var pageName = ""
27
+
28
+ @available(iOS 13.0, *)
29
+ var body: some View {
30
+ ReactNativeSwiftView(pageName: self.pageName)
31
+ }
32
+ }
33
+
34
+ @available(iOS 13.0, *)
35
+ class ReactNativeHostingController: UIHostingController<ReactNativePageView> {
36
+ required init?(coder aDecoder: NSCoder) {
37
+ super.init(coder: aDecoder, rootView: ReactNativePageView(pageName: ""))
38
+ CommunicationService.INSTANCE.process(
39
+ messageType: "close",
40
+ processor: {(message: NSDictionary?, promise: Promise?) in
41
+ DispatchQueue.main.async(execute: {
42
+ self.navigationController?.popViewController(animated: true);
43
+ self.dismiss(animated: true);
44
+ });
45
+ });
46
+ }
47
+
48
+ override func viewWillDisappear(_ animated: Bool) {
49
+ super.viewDidDisappear(animated);
50
+ CommunicationService.INSTANCE.removeProcessor(messageType: "close");
51
+ }
52
+
53
+ }
@@ -0,0 +1,100 @@
1
+ // import { useWorker } from '@koale/useworker';
2
+ import * as React from 'react';
3
+ import { captureImageData } from './WebCameraUtils';
4
+ const qrWorkerMethod = ({ data, width, height }) => {
5
+ // eslint-disable-next-line no-undef
6
+ const decoded = self.jsQR(data, width, height, {
7
+ inversionAttempts: 'attemptBoth',
8
+ });
9
+ let parsed;
10
+ try {
11
+ parsed = JSON.parse(decoded);
12
+ }
13
+ catch {
14
+ parsed = decoded;
15
+ }
16
+ if (parsed?.data) {
17
+ const nativeEvent = {
18
+ type: 'qr',
19
+ data: parsed.data,
20
+ cornerPoints: [],
21
+ bounds: { origin: { x: 0, y: 0 }, size: { width: 0, height: 0 } },
22
+ };
23
+ if (parsed.location) {
24
+ nativeEvent.cornerPoints = [
25
+ parsed.location.topLeftCorner,
26
+ parsed.location.bottomLeftCorner,
27
+ parsed.location.topRightCorner,
28
+ parsed.location.bottomRightCorner,
29
+ ];
30
+ }
31
+ return nativeEvent;
32
+ }
33
+ return parsed;
34
+ };
35
+ function useRemoteJsQR() {
36
+ /*return useWorker(qrWorkerMethod, {
37
+ remoteDependencies: ['https://cdn.jsdelivr.net/npm/jsqr@1.2.0/dist/jsQR.min.js'],
38
+ autoTerminate: false,
39
+ });*/
40
+ }
41
+ export function useWebQRScanner(video, { isEnabled, captureOptions, interval, onScanned, onError, }) {
42
+ const isRunning = React.useRef(false);
43
+ const timeout = React.useRef(undefined);
44
+ const [decode, clearWorker] = useRemoteJsQR();
45
+ async function scanAsync() {
46
+ // If interval is 0 then only scan once.
47
+ if (!isRunning.current || !onScanned) {
48
+ stop();
49
+ return;
50
+ }
51
+ try {
52
+ const data = captureImageData(video.current, captureOptions);
53
+ if (data) {
54
+ const nativeEvent = await decode(data);
55
+ if (nativeEvent?.data) {
56
+ onScanned({
57
+ nativeEvent,
58
+ });
59
+ }
60
+ }
61
+ }
62
+ catch (error) {
63
+ if (onError) {
64
+ onError({ nativeEvent: error });
65
+ }
66
+ }
67
+ finally {
68
+ // If interval is 0 then only scan once.
69
+ if (interval === 0) {
70
+ stop();
71
+ return;
72
+ }
73
+ const intervalToUse = !interval || interval < 0 ? 16 : interval;
74
+ // @ts-ignore: Type 'Timeout' is not assignable to type 'number'
75
+ timeout.current = setTimeout(() => {
76
+ scanAsync();
77
+ }, intervalToUse);
78
+ }
79
+ }
80
+ function stop() {
81
+ isRunning.current = false;
82
+ clearTimeout(timeout.current);
83
+ }
84
+ React.useEffect(() => {
85
+ if (isEnabled) {
86
+ isRunning.current = true;
87
+ scanAsync();
88
+ }
89
+ else {
90
+ stop();
91
+ }
92
+ }, [isEnabled]);
93
+ React.useEffect(() => {
94
+ return () => {
95
+ stop();
96
+ clearWorker.kill();
97
+ };
98
+ }, []);
99
+ }
100
+ //# sourceMappingURL=useWebQRScanner.js.map
@@ -0,0 +1,72 @@
1
+ const newPostInstallBlock =
2
+ `post_install do |installer|
3
+ react_native_post_install(
4
+ installer,
5
+ config[:reactNativePath],
6
+ :mac_catalyst_enabled => false
7
+ )
8
+
9
+ # Set provisioning profile to "None" for all pod targets
10
+ installer.pods_project.targets.each do |target|
11
+ target.build_configurations.each do |config|
12
+ config.build_settings['PROVISIONING_PROFILE'] = 'None'
13
+ config.build_settings['CODE_SIGN_IDENTITY'] = ''
14
+ config.build_settings['CODE_SIGNING_ALLOWED'] = 'NO'
15
+ end
16
+ end
17
+
18
+ # Disable code signing for resource bundle targets
19
+ installer.target_installation_results.pod_target_installation_results
20
+ .each do |pod_name, target_installation_result|
21
+ target_installation_result.resource_bundle_targets.each do |resource_bundle_target|
22
+ resource_bundle_target.build_configurations.each do |config|
23
+ config.build_settings['CODE_SIGNING_ALLOWED'] = 'NO'
24
+ config.build_settings['PROVISIONING_PROFILE'] = 'None'
25
+ config.build_settings['CODE_SIGN_IDENTITY'] = ''
26
+ end
27
+ end
28
+ end
29
+
30
+ # Fix for React Native Firebase when using static frameworks
31
+ # ROOT CAUSE: Static frameworks with modules enabled create strict module boundaries.
32
+ # When RNFBMessaging imports <RNFBApp/...>, the module system expects ALL types to be
33
+ # visible through RNFBApp's module exports. But RCTPromiseRejectBlock is in React-Core,
34
+ # and RNFBApp doesn't re-export it. The module system blocks access even if headers exist.
35
+ #
36
+ # SOLUTION: Disable modules for RNFB targets entirely. This makes the compiler use
37
+ # traditional #import header inclusion instead of strict module boundaries.
38
+ installer.pods_project.targets.each do |target|
39
+ if target.name.start_with?('RNFB')
40
+ target.build_configurations.each do |config|
41
+ # DISABLE modules - this is the key fix
42
+ # Without modules, the compiler uses traditional header inclusion and can find
43
+ # React-Core types through the header search paths
44
+ config.build_settings['CLANG_ENABLE_MODULES'] = 'NO'
45
+
46
+ # Ensure header maps are enabled so headers can be found
47
+ config.build_settings['USE_HEADERMAP'] = 'YES'
48
+
49
+ # Add React-Core headers to search paths so they can be found via #import
50
+ header_search_paths = config.build_settings['HEADER_SEARCH_PATHS'] || '$(inherited)'
51
+ react_core_path = File.join(installer.sandbox.root, 'Headers', 'Public', 'React-Core')
52
+ react_core_path_quoted = '"' + react_core_path + '"'
53
+ if header_search_paths.is_a?(Array)
54
+ unless header_search_paths.any? { |path| path.include?('React-Core') }
55
+ header_search_paths << react_core_path_quoted
56
+ end
57
+ elsif header_search_paths.is_a?(String)
58
+ unless header_search_paths.include?('React-Core')
59
+ config.build_settings['HEADER_SEARCH_PATHS'] = [header_search_paths, react_core_path_quoted]
60
+ end
61
+ else
62
+ config.build_settings['HEADER_SEARCH_PATHS'] = ['$(inherited)', react_core_path_quoted]
63
+ end
64
+ end
65
+ end
66
+ end
67
+
68
+ end`;
69
+
70
+ module.exports = {
71
+ newPostInstallBlock
72
+ }