update mobile no and wellmess

This commit is contained in:
Surendiran 2025-11-06 18:15:30 +05:30
parent 9a771db590
commit 58b32005e9
20 changed files with 2457 additions and 2123 deletions

View File

@ -19,12 +19,12 @@ if (project.hasProperty('google-services.json')) {
def flutterVersionCode = localProperties.getProperty('flutter.versionCode')
if (flutterVersionCode == null) {
flutterVersionCode = '39'
flutterVersionCode = '41'
}
def flutterVersionName = localProperties.getProperty('flutter.versionName')
if (flutterVersionName == null) {
flutterVersionName = '2.0.1'
flutterVersionName = '2.0.3'
}
def keystoreProperties = new Properties()

View File

@ -1,5 +1,5 @@
# Uncomment this line to define a global platform for your project
platform :ios, '13.0'
platform :ios, '14.0'
# CocoaPods analytics sends network stats synchronously affecting flutter build latency.
ENV['COCOAPODS_DISABLE_STATS'] = 'true'

View File

@ -0,0 +1,13 @@
import UIKit
import Flutter
@main
@objc class AppDelegate: FlutterAppDelegate {
override func application(
_ application: UIApplication,
didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
) -> Bool {
GeneratedPluginRegistrant.register(with: self)
return super.application(application, didFinishLaunchingWithOptions: launchOptions)
}
}

View File

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="19162" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" launchScreen="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="01J-lp-oVM">
<device id="retina6_1" orientation="portrait" appearance="light"/>
<dependencies>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="19144"/>
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
<scenes>
<!--View Controller-->
<scene sceneID="EHf-IW-A2E">
<objects>
<viewController id="01J-lp-oVM" sceneMemberID="viewController">
<view key="view" contentMode="scaleToFill" id="Ze5-6b-2t3">
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
<color key="backgroundColor" systemColor="systemBackgroundColor"/>
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
</view>
</viewController>
<placeholder placeholderIdentifier="IBFirstResponder" id="iYj-Kq-Ea1" userLabel="First Responder" sceneMemberID="firstResponder"/>
</objects>
<point key="canvasLocation" x="53" y="375"/>
</scene>
</scenes>
</document>

View File

@ -0,0 +1 @@
#import "GeneratedPluginRegistrant.h"

View File

@ -1,6 +1,6 @@
import 'package:firebase_app_check/firebase_app_check.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:firebase_messaging/firebase_messaging.dart';
// import 'package:firebase_app_check/firebase_app_check.dart';
// import 'package:firebase_core/firebase_core.dart';
// import 'package:firebase_messaging/firebase_messaging.dart';
import 'package:flutter/material.dart';
import 'package:flutter_dotenv/flutter_dotenv.dart';
import 'package:nhance_app_pwa/customAppBar/toastHelper.dart';
@ -130,55 +130,55 @@ Future<String?> tokenRedirectLogic(
return null; // no redirect
}
Future<void> _firebaseMessagingBackgroundHandler(RemoteMessage message) async {
await Firebase.initializeApp();
print("Handling background message: ${message.messageId}");
}
// Future<void> _firebaseMessagingBackgroundHandler(RemoteMessage message) async {
// await Firebase.initializeApp();
// print("Handling background message: ${message.messageId}");
// }
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
// final SharedPreferences prefs = await SharedPreferences.getInstance();
// prefs.clear();
if (kIsWeb) {
await Firebase.initializeApp(
options: const FirebaseOptions(
// apiKey: 'AIzaSyC4yHbCX4mQu0jO81pJrDwxKLQlTQWofrc',
// appId: '1:1084115316849:android:68b14c4ff37f4bbc6c6bd0',
// messagingSenderId: '1084115316849',
// projectId: 'nhance-ee8d1'
apiKey: "AIzaSyC4yHbCX4mQu0jO81pJrDwxKLQlTQWofrc",
authDomain: "nhance-ee8d1.firebaseapp.com",
projectId: "nhance-ee8d1",
storageBucket: "nhance-ee8d1.firebasestorage.app",
messagingSenderId: "1084115316849",
appId: "1:1084115316849:web:8fc3b1c886349ae86c6bd0"));
} else {
await Firebase.initializeApp();
await FirebaseAppCheck.instance.activate(
// webProvider: ReCaptchaV3Provider('recaptcha-v3-site-key'),
androidProvider: AndroidProvider.playIntegrity,
appleProvider: AppleProvider.appAttest,
);
FirebaseMessaging.onBackgroundMessage(_firebaseMessagingBackgroundHandler);
FirebaseMessaging messaging = FirebaseMessaging.instance;
// NotificationSettings settings = await messaging.requestPermission();
NotificationSettings settings =
await FirebaseMessaging.instance.requestPermission(
alert: true,
badge: true,
sound: true,
);
print('User granted permission: ${settings.authorizationStatus}');
FirebaseMessaging.onMessage.listen((RemoteMessage message) {
print('Foreground Message: ${message.notification?.title}');
});
FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {
print('User tapped on notification');
});
}
// if (kIsWeb) {
// await Firebase.initializeApp(
// options: const FirebaseOptions(
// // apiKey: 'AIzaSyC4yHbCX4mQu0jO81pJrDwxKLQlTQWofrc',
// // appId: '1:1084115316849:android:68b14c4ff37f4bbc6c6bd0',
// // messagingSenderId: '1084115316849',
// // projectId: 'nhance-ee8d1'
// apiKey: "AIzaSyC4yHbCX4mQu0jO81pJrDwxKLQlTQWofrc",
// authDomain: "nhance-ee8d1.firebaseapp.com",
// projectId: "nhance-ee8d1",
// storageBucket: "nhance-ee8d1.firebasestorage.app",
// messagingSenderId: "1084115316849",
// appId: "1:1084115316849:web:8fc3b1c886349ae86c6bd0"));
// } else {
// await Firebase.initializeApp();
// await FirebaseAppCheck.instance.activate(
// // webProvider: ReCaptchaV3Provider('recaptcha-v3-site-key'),
// androidProvider: AndroidProvider.playIntegrity,
// appleProvider: AppleProvider.appAttest,
// );
// FirebaseMessaging.onBackgroundMessage(_firebaseMessagingBackgroundHandler);
//
// FirebaseMessaging messaging = FirebaseMessaging.instance;
// // NotificationSettings settings = await messaging.requestPermission();
// NotificationSettings settings =
// await FirebaseMessaging.instance.requestPermission(
// alert: true,
// badge: true,
// sound: true,
// );
// print('User granted permission: ${settings.authorizationStatus}');
//
// FirebaseMessaging.onMessage.listen((RemoteMessage message) {
// print('Foreground Message: ${message.notification?.title}');
// });
//
// FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {
// print('User tapped on notification');
// });
// }
await dotenv.load(fileName: Environment.fileName);
@ -194,19 +194,19 @@ Future<void> main() async {
routes: [
GoRoute(path: '/splash', builder: (context, state) => const SplashScreen()),
GoRoute(path: '/login', builder: (context, state) => login()),
GoRoute(
path: '/verify',
builder: (context, state) {
final extras = state.extra as Map<String, dynamic>?;
return MyVerify(
verificationId: extras?['verificationId'] ?? '',
mobileNumber: extras?['mobileNumber'] ?? '',
resendToken: extras?['resendToken'],
onResendCode: extras?['onResendCode'],
);
},
),
// GoRoute(
// path: '/verify',
// builder: (context, state) {
// final extras = state.extra as Map<String, dynamic>?;
//
// return MyVerify(
// verificationId: extras?['verificationId'] ?? '',
// mobileNumber: extras?['mobileNumber'] ?? '',
// resendToken: extras?['resendToken'],
// onResendCode: extras?['onResendCode'],
// );
// },
// ),
// GoRoute(
// path: '/chatbot',
// builder: (context, state) {

View File

@ -1,5 +1,5 @@
import 'package:firebase_auth/firebase_auth.dart';
import 'package:firebase_messaging/firebase_messaging.dart';
// import 'package:firebase_auth/firebase_auth.dart';
// import 'package:firebase_messaging/firebase_messaging.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:go_router/go_router.dart';
@ -66,8 +66,8 @@ class _MyEmailVerifyState extends State<MyEmailVerify> {
String? fcmToken;
String? apnsToken;
late String verificationId;
final FirebaseMessaging _firebaseMessaging = FirebaseMessaging.instance;
final FirebaseAuth _auth = FirebaseAuth.instance;
// final FirebaseMessaging _firebaseMessaging = FirebaseMessaging.instance;
// final FirebaseAuth _auth = FirebaseAuth.instance;
bool _isLoading = false;
late String _verificationId;
@ -88,56 +88,56 @@ class _MyEmailVerifyState extends State<MyEmailVerify> {
super.dispose();
}
Future<void> initNotification() async {
try {
// Request permission
NotificationSettings settings =
await _firebaseMessaging.requestPermission(
alert: true,
badge: true,
sound: true,
);
print('🔔 Permission: ${settings.authorizationStatus}');
if (Platform.isIOS || Platform.isMacOS) {
// Get APNS token
apnsToken = await _firebaseMessaging.getAPNSToken();
print('📱 APNS Token (iOS): $apnsToken');
// Retry if null
if (apnsToken == null) {
await Future.delayed(const Duration(seconds: 3));
apnsToken = await _firebaseMessaging.getAPNSToken();
print('🔁 Retried APNS Token: $apnsToken');
}
if (apnsToken != null) {
await sendDeviceToken(apnsToken!);
}
} else if (Platform.isAndroid) {
// Get FCM token
fcmToken = await _firebaseMessaging.getToken();
print('🔥 FCM Token (Android): $fcmToken');
if (fcmToken != null) {
await sendDeviceToken(fcmToken!);
}
}
// Background handler
FirebaseMessaging.onBackgroundMessage(firebaseMessagingBackgroundHandler);
// Foreground listener
FirebaseMessaging.onMessage.listen((RemoteMessage message) {
print('💬 Message: ${message.notification?.title}');
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text(message.notification?.title ?? 'New Notification')),
);
});
} catch (e) {
print('❌ Notification init error: $e');
}
}
// Future<void> initNotification() async {
// try {
// // Request permission
// NotificationSettings settings =
// await _firebaseMessaging.requestPermission(
// alert: true,
// badge: true,
// sound: true,
// );
// print('🔔 Permission: ${settings.authorizationStatus}');
//
// if (Platform.isIOS || Platform.isMacOS) {
// // Get APNS token
// apnsToken = await _firebaseMessaging.getAPNSToken();
// print('📱 APNS Token (iOS): $apnsToken');
//
// // Retry if null
// if (apnsToken == null) {
// await Future.delayed(const Duration(seconds: 3));
// apnsToken = await _firebaseMessaging.getAPNSToken();
// print('🔁 Retried APNS Token: $apnsToken');
// }
//
// if (apnsToken != null) {
// await sendDeviceToken(apnsToken!);
// }
// } else if (Platform.isAndroid) {
// // Get FCM token
// fcmToken = await _firebaseMessaging.getToken();
// print('🔥 FCM Token (Android): $fcmToken');
//
// if (fcmToken != null) {
// await sendDeviceToken(fcmToken!);
// }
// }
//
// // Background handler
// FirebaseMessaging.onBackgroundMessage(firebaseMessagingBackgroundHandler);
//
// // Foreground listener
// FirebaseMessaging.onMessage.listen((RemoteMessage message) {
// print('💬 Message: ${message.notification?.title}');
// ScaffoldMessenger.of(context).showSnackBar(
// SnackBar(content: Text(message.notification?.title ?? 'New Notification')),
// );
// });
// } catch (e) {
// print('❌ Notification init error: $e');
// }
// }
// Future<void> initNotification() async {
// await _firebaseMessaging.requestPermission();
@ -346,13 +346,13 @@ class _MyEmailVerifyState extends State<MyEmailVerify> {
print('Successfully Login');
loginUser(
gpaEmpName: session.gpaEmpName,
empPrimaryId: session.empPrimaryId,
empCodeString: session.empCodeString,
client_id: session.client_id,
empClientBranchId: session.empClientBranchId,
);
// loginUser(
// gpaEmpName: session.gpaEmpName,
// empPrimaryId: session.empPrimaryId,
// empCodeString: session.empCodeString,
// client_id: session.client_id,
// empClientBranchId: session.empClientBranchId,
// );
// if (kIsWeb) {
// html.window.localStorage['gpaEmpName'] = gpaEmpName;
@ -432,7 +432,7 @@ class _MyEmailVerifyState extends State<MyEmailVerify> {
} else {
prefs.setString('empEmailid', widget.value);
}
await initNotification();
// await initNotification();
checkLoginPin(context);
}
// }
@ -490,7 +490,7 @@ class _MyEmailVerifyState extends State<MyEmailVerify> {
} else {
prefs.setString('empEmailid', widget.value);
}
await initNotification();
// await initNotification();
checkLoginPin(context);
}
// }
@ -1241,10 +1241,10 @@ class _MyEmailVerifyState extends State<MyEmailVerify> {
}
// Must be outside any class this fixes your error
@pragma('vm:entry-point')
Future<void> firebaseMessagingBackgroundHandler(RemoteMessage message) async {
print('📨 Handling background message: ${message.messageId}');
print('Title: ${message.notification?.title}');
print('Body: ${message.notification?.body}');
print('Data: ${message.data}');
}
// @pragma('vm:entry-point')
// Future<void> firebaseMessagingBackgroundHandler(RemoteMessage message) async {
// print('📨 Handling background message: ${message.messageId}');
// print('Title: ${message.notification?.title}');
// print('Body: ${message.notification?.body}');
// print('Data: ${message.data}');
// }

View File

@ -1,4 +1,4 @@
import 'package:firebase_auth/firebase_auth.dart';
// import 'package:firebase_auth/firebase_auth.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
@ -33,7 +33,7 @@ class _loginState extends State<login> {
dynamic empMobileNo;
dynamic empEmailid;
final FirebaseAuth _auth = FirebaseAuth.instance;
// final FirebaseAuth _auth = FirebaseAuth.instance;
late String _verificationId;
int? _resendToken;

View File

@ -123,31 +123,10 @@ class _HomeState extends State<Home> {
if (kIsWeb) {
openBotmanChat();
// setupBackButtonHandler(() {
// if (!_dialogShown) _showBackConfirmationDialog();
// });
// Push a dummy state so back button triggers popstate instead of navigating
// html.window.history.pushState(null, 'home', html.window.location.href);
// html.window.onPopState.listen((event) {
// if (!_dialogShown) {
// _showBackConfirmationDialog();
// }
// // Re-push to prevent leaving
// html.window.history.pushState(null, 'home', html.window.location.href);
// });
}
// if (Platform.isAndroid) {
// WebViewPlatform.instance = AndroidWebViewPlatform();
// if (kIsWeb) {
// openBotmanChat();
// }
// _controller = WebViewController()
// ..setJavaScriptMode(JavaScriptMode.unrestricted)
// ..loadFlutterAsset('assets/botman_chat.html'); // or loadHtmlString
}
@override
@ -974,44 +953,44 @@ class _HomeState extends State<Home> {
),
),
]),
floatingActionButton: Responsive.isDesktop(context)
? null
: FloatingActionButton(
// onPressed: () => push(chatbot()),
onPressed: () => {
// Navigator.push(
// context,
// MaterialPageRoute(
// builder: (context) => MyWebViewPage(
// url: 'https://venbait.in/nhance/dev/chatbot?employee_id=${empPrimaryId}&emp_code=${empCodeString}&origin=mob&name=${empName}&client_id=${client_id}&client_branch_id=${client_branch_id}',
// ),
// ),
// )
// context.go(
// '/chatbot',
// extra: {
// 'client_branch_id': client_branch_id,
// 'empCodeString': empCodeString,
// 'empName': empName,
// 'empPrimaryId': empPrimaryId,
// 'client_id': client_id,
// },
// )
Navigator.push(
context,
// MaterialPageRoute(builder: (context) => const BotmanChatPage()),
MaterialPageRoute(
builder: (context) => ChatbotWebViewPage(
client_branch_id: client_branch_id,
empCodeString: empCodeString,
empName: empName,
empPrimaryId: empPrimaryId,
client_id: client_id,
)),
)
},
child: Icon(Icons.chat),
),
// floatingActionButton: Responsive.isDesktop(context)
// ? null
// : FloatingActionButton(
// // onPressed: () => push(chatbot()),
// onPressed: () => {
// // Navigator.push(
// // context,
// // MaterialPageRoute(
// // builder: (context) => MyWebViewPage(
// // url: 'https://venbait.in/nhance/dev/chatbot?employee_id=${empPrimaryId}&emp_code=${empCodeString}&origin=mob&name=${empName}&client_id=${client_id}&client_branch_id=${client_branch_id}',
// // ),
// // ),
// // )
// // context.go(
// // '/chatbot',
// // extra: {
// // 'client_branch_id': client_branch_id,
// // 'empCodeString': empCodeString,
// // 'empName': empName,
// // 'empPrimaryId': empPrimaryId,
// // 'client_id': client_id,
// // },
// // )
// Navigator.push(
// context,
// // MaterialPageRoute(builder: (context) => const BotmanChatPage()),
// MaterialPageRoute(
// builder: (context) => ChatbotWebViewPage(
// client_branch_id: client_branch_id,
// empCodeString: empCodeString,
// empName: empName,
// empPrimaryId: empPrimaryId,
// client_id: client_id,
// )),
// )
// },
// child: Icon(Icons.chat),
// ),
floatingActionButtonLocation: Responsive.isDesktop(context)
? null
: FloatingActionButtonLocation.miniEndFloat,

View File

@ -37,6 +37,9 @@ class _policiesState extends State<policies> {
dynamic _token;
dynamic empCodeString;
dynamic empPrimaryId;
dynamic empName;
dynamic mobileNo;
dynamic client_branch_id;
dynamic client_id;
dynamic policyList;
dynamic policyDataIsEmpty = 1;
@ -77,16 +80,49 @@ class _policiesState extends State<policies> {
final SharedPreferences prefs = await SharedPreferences.getInstance();
if (token != null && token.isNotEmpty) {
// Decode the JWT token received from the API response
Map<String, dynamic>? decodedToken = Jwt.parseJwt(token);
print(decodedToken);
empCodeString = prefs.getString('empCode');
print(empCodeString); // Check if emp_code is correct
empPrimaryId = prefs.getString('empPrimaryId');
client_id = prefs.getString('client_id');
print(client_id);
mobileNo = session.mobileNo;
client_branch_id = session.empClientBranchId;
empCodeString = session.empCodeString;
empName = session.gpaEmpName;
print(empCodeString); // Check if emp_code is correct
empPrimaryId = session.empPrimaryId;
client_id = session.client_id;
}
}
Future<void> getEcardDownload() async {
final clientPolicyID = widget.arguments?['client_policy_id'];
final policyNo = widget.arguments?['policy_no'];
final eCarDParams = {
'id': empPrimaryId,
'emp_code': empCodeString,
'client_policy_id': clientPolicyID,
'policy_no': policyNo
};
final response = await apiService.getEcardRequest(eCarDParams);
print('check 1');
final ecardDownloadUrl = response['data']['eCardDownload'];
final message = response['data']['message'];
if (ecardDownloadUrl != null) {
print('✅ Link: $ecardDownloadUrl');
await _launchURL(ecardDownloadUrl,context); // Only launch if status is success
// ToastHelper.showSuccessToast(context, message);
} else {
print('❌ Error: $message');
ToastHelper.showErrorToast(context, message);
}
}
Future<void> _launchURL(String url, BuildContext context) async {
print('url $url');
try {
final Uri uri = Uri.parse(url);
await launchUrl(uri, mode: LaunchMode.externalApplication);
} catch (e) {
print('Could not launch URL: $e');
}
}
String convertDateFormat(String date) {
// Define input and output date formats
@ -111,19 +147,6 @@ class _policiesState extends State<policies> {
}
}
// Function to open URL in the default browser
Future<void> _launchURL(String url) async {
final Uri uri = Uri.parse(url); // Parse the URL properly
print('_launchURL $uri');
if (uri != null) {
print('If $uri');
await launchUrl(uri, mode: LaunchMode.externalApplication);
} else {
print('else $uri');
throw 'Could not launch $url';
}
}
void _openUrl(String url) async {
if (url.isNotEmpty && await canLaunch(url)) {
await launch(url,
@ -270,14 +293,15 @@ class _policiesState extends State<policies> {
: 180,
child: TextButton(
onPressed: () {
if (argumentsData['eCardDownload'] !=
null) {
_launchURL(
argumentsData['eCardDownload']);
} else {
ToastHelper.showInfoToast(
context, 'Not Generated');
}
getEcardDownload();
// if (argumentsData['eCardDownload'] !=
// null) {
// _launchURL(
// argumentsData['eCardDownload']);
// } else {
// ToastHelper.showInfoToast(
// context, 'Not Generated');
// }
},
style: TextButton.styleFrom(
padding: EdgeInsets.only(

File diff suppressed because it is too large Load Diff

View File

@ -153,6 +153,46 @@ class ApiService {
return response;
}
Future<Map<String, dynamic>> getEcardRequest(eCardParam) async {
print(_postToken);
if (_postToken == null) {
await _initializeToken();
}
final url = Uri.parse('${Environment.apiUrl}ecardRequest');
final headers = {
'Authorization': 'Bearer $_postToken' ?? '',
'Content-Type': 'application/json', // Ensure content type is JSON
};
final jsonBody = jsonEncode(eCardParam);
// Send formDataJson as the body
final response = await _makePostRequestWithoutFormData(url,jsonBody, headers);
return response;
}
Future<bool> updateMobileNumber(Map<String, dynamic> updateParam) async {
if (_postToken == null) {
await _initializeToken();
}
final url = Uri.parse('${Environment.apiUrl}updateMobileNumber');
final headers = {
'Authorization': 'Bearer $_postToken',
'Content-Type': 'application/json',
};
final jsonBody = jsonEncode(updateParam);
final response = await _makePostRequestWithoutFormData(
url,
jsonBody,
headers,
);
return response['status'] == 'success';
}
Future<Map<String, dynamic>> fetchDepartmentList(String clientId, String empCode) async {
print(_postToken);
if (_postToken == null) {
@ -282,6 +322,14 @@ class ApiService {
return _handleResponse(response);
}
Future<Map<String, dynamic>> _makePostRequestWithoutFormData(
Uri url, String body, Map<String, String> headers) async {
final response = await http.post(url, headers: headers, body: body);
return _handleResponse(response);
}
Future<Map<String, dynamic>> _handleResponse(http.Response response) async {
if (response.statusCode == 200) {
return jsonDecode(response.body);

View File

@ -0,0 +1,84 @@
import 'dart:convert';
import 'dart:io';
import 'package:flutter/foundation.dart';
import 'package:package_info_plus/package_info_plus.dart';
import 'package:http/http.dart' as http;
class AppVersionService {
/// Get installed app version (Android + iOS)
static Future<String> getInstalledVersion() async {
PackageInfo info = await PackageInfo.fromPlatform();
return info.version; // Example: "1.9"
}
/// Get App Store version (iOS)
static Future<String?> getAppStoreVersion(String appId) async {
final url = Uri.parse("https://itunes.apple.com/lookup?id=$appId");
final response = await http.get(url);
if (response.statusCode == 200) {
final data = jsonDecode(response.body);
if (data["resultCount"] > 0) {
return data["results"][0]["version"]; // Example: "1.9"
}
}
return null;
}
/// Get Play Store version (Android)
/// NOTE: Play Store has no official API. This scrapes the HTML page.
static Future<String?> getPlayStoreVersion(String packageName) async {
print(Platform.isAndroid);
try {
print('Platform.isAndroid');
final url = Uri.parse(
"https://play.google.com/store/apps/details?id=$packageName&hl=en&gl=US",
);
print(url);
final response = await http.get(url);
print('Get Version Response $response');
if (response.statusCode == 200) {
final html = response.body;
print('Get Version Response $html');
// Android version usually appears near: "Current Version"
final versionRegEx = RegExp(
r'Current Version.*?<\/span><span[^>]*>(.*?)<\/span>',
caseSensitive: false,
dotAll: true,
);
print('versionRegEx $versionRegEx');
final match = versionRegEx.firstMatch(html);
print('match $match');
if (match != null) {
return match.group(1)?.trim();
}
}
} catch (e) {
debugPrint("Play Store error: $e");
}
return null;
}
/// Unified function to get latest store version based on platform
static Future<String?> getLatestStoreVersion({
required String androidPackage,
required String iosAppId,
}) async {
if (kIsWeb) return null;
if (Platform.isAndroid) {
print('Platform.isAndroid');
return await getPlayStoreVersion(androidPackage);
}
if (Platform.isIOS) {
return await getAppStoreVersion(iosAppId);
}
return null;
}
}

View File

@ -0,0 +1,105 @@
import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:google_fonts/google_fonts.dart';
import 'package:http/http.dart' as http;
import '../../customAppBar/toastHelper.dart';
import '../../models/environment.dart';
import '../postEnrollment/service/api_service.dart';
import 'package:flutter/material.dart';
import 'package:google_fonts/google_fonts.dart';
import 'dart:convert';
import 'package:http/http.dart' as http;
Future<String?> showUpdateMobileDialog(
BuildContext context,
ApiService apiService,
String clientId,
String emailId,
String? currentMobile,
) {
final controller = TextEditingController(text: currentMobile ?? '');
bool isLoading = false;
return showDialog<String>(
context: context,
barrierDismissible: false,
builder: (context) {
return StatefulBuilder(
builder: (context, setState) {
return AlertDialog(
title: Text(
"Update Mobile Number",
style: GoogleFonts.poppins(fontWeight: FontWeight.w600),
),
content: TextField(
controller: controller,
keyboardType: TextInputType.phone,
decoration: const InputDecoration(
labelText: "Enter Mobile Number",
border: OutlineInputBorder(),
),
),
actions: [
// Cancel Button
ElevatedButton(
onPressed: () => Navigator.pop(context, null),
child: Text("Cancel", style: GoogleFonts.poppins(color: Colors.white)),
style: ElevatedButton.styleFrom(backgroundColor: Color(0xFFE26728)),
),
const SizedBox(width: 10),
// Save Button
ElevatedButton(
onPressed: isLoading
? null
: () async {
final newMobile = controller.text.trim();
if (newMobile.isEmpty) {
ToastHelper.showErrorToast(context, "Enter mobile number");
return;
}
setState(() => isLoading = true);
final updateParam = {
"email_id": emailId,
"client_id": clientId,
"new_mobile_number": newMobile,
};
// Call API using apiService
bool success = await apiService.updateMobileNumber(updateParam);
if (success) {
ToastHelper.showSuccessToast(context, "Mobile Number Updated");
Navigator.pop(context, newMobile);
} else {
ToastHelper.showErrorToast(context, "Failed to update number");
}
},
child: isLoading
? const SizedBox(
width: 18,
height: 18,
child: CircularProgressIndicator(
color: Colors.white,
strokeWidth: 2,
),
)
: Text("Save", style: GoogleFonts.poppins(color: Colors.white)),
style: ElevatedButton.styleFrom(backgroundColor: Color(0xFFE26728)),
),
],
);
},
);
},
);
}

View File

@ -30,6 +30,8 @@ class PopupHelper {
// 🔹 Fetch link using API
final response = await apiService.getWellnessLink(empPrimaryId);
print('Wellness response : $response');
if (response['status'] == 'success') {
wellnessURL = response['data'];
} else if (response['status'] == 'failed') {

File diff suppressed because it is too large Load Diff

View File

@ -7,10 +7,6 @@ import Foundation
import file_picker
import file_selector_macos
import firebase_app_check
import firebase_auth
import firebase_core
import firebase_messaging
import flutter_inappwebview_macos
import flutter_secure_storage_macos
import google_sign_in_ios
@ -26,10 +22,6 @@ import webview_flutter_wkwebview
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {
FilePickerPlugin.register(with: registry.registrar(forPlugin: "FilePickerPlugin"))
FileSelectorPlugin.register(with: registry.registrar(forPlugin: "FileSelectorPlugin"))
FLTFirebaseAppCheckPlugin.register(with: registry.registrar(forPlugin: "FLTFirebaseAppCheckPlugin"))
FLTFirebaseAuthPlugin.register(with: registry.registrar(forPlugin: "FLTFirebaseAuthPlugin"))
FLTFirebaseCorePlugin.register(with: registry.registrar(forPlugin: "FLTFirebaseCorePlugin"))
FLTFirebaseMessagingPlugin.register(with: registry.registrar(forPlugin: "FLTFirebaseMessagingPlugin"))
InAppWebViewFlutterPlugin.register(with: registry.registrar(forPlugin: "InAppWebViewFlutterPlugin"))
FlutterSecureStoragePlugin.register(with: registry.registrar(forPlugin: "FlutterSecureStoragePlugin"))
FLTGoogleSignInPlugin.register(with: registry.registrar(forPlugin: "FLTGoogleSignInPlugin"))

View File

@ -17,8 +17,8 @@ publish_to: 'none' # Remove this line if you wish to publish to pub.dev
# In Windows, build-name is used as the major, minor, and patch parts
# of the product and file versions while build-number is used as the build suffix.
#version: 1.0.32+32
#version: 1.0.20+21
version: 2.0.1+39
version: 1.0.20+23
#version: 2.0.3+41
environment:
sdk: '>=3.3.3 <4.0.0'
@ -51,13 +51,13 @@ dependencies:
url_launcher: ^6.2.6
flutter_svg: ^2.0.10+1
dash_chat_2: ^0.0.21
firebase_messaging: ^16.0.3
# firebase_messaging: ^16.0.3
local_auth: ^3.0.0
google_sign_in: ^7.2.0
dio: ^5.7.0
firebase_core: ^4.2.0
firebase_auth: ^6.1.1
firebase_app_check: ^0.4.1+1
# firebase_core: ^4.2.0
# firebase_auth: ^6.1.1
# firebase_app_check: ^0.4.1+2
package_info_plus: ^9.0.0
webview_flutter: ^4.13.0
webview_flutter_android: ^4.7.0

View File

@ -7,8 +7,6 @@
#include "generated_plugin_registrant.h"
#include <file_selector_windows/file_selector_windows.h>
#include <firebase_auth/firebase_auth_plugin_c_api.h>
#include <firebase_core/firebase_core_plugin_c_api.h>
#include <flutter_inappwebview_windows/flutter_inappwebview_windows_plugin_c_api.h>
#include <flutter_secure_storage_windows/flutter_secure_storage_windows_plugin.h>
#include <local_auth_windows/local_auth_plugin.h>
@ -17,10 +15,6 @@
void RegisterPlugins(flutter::PluginRegistry* registry) {
FileSelectorWindowsRegisterWithRegistrar(
registry->GetRegistrarForPlugin("FileSelectorWindows"));
FirebaseAuthPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("FirebaseAuthPluginCApi"));
FirebaseCorePluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("FirebaseCorePluginCApi"));
FlutterInappwebviewWindowsPluginCApiRegisterWithRegistrar(
registry->GetRegistrarForPlugin("FlutterInappwebviewWindowsPluginCApi"));
FlutterSecureStorageWindowsPluginRegisterWithRegistrar(

View File

@ -4,8 +4,6 @@
list(APPEND FLUTTER_PLUGIN_LIST
file_selector_windows
firebase_auth
firebase_core
flutter_inappwebview_windows
flutter_secure_storage_windows
local_auth_windows