Update: 2026-06-29 00:07:33
This commit is contained in:
@@ -72,7 +72,7 @@ $result['path'] = $simplePath;
|
||||
|
||||
// --------- بناء الرابط العام ---------
|
||||
$protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off') ? 'https' : 'http';
|
||||
$host = getenv('APP_DOMAIN') ?: ($_SERVER['HTTP_HOST'] ?? 'api.siromove.com');
|
||||
$host = $_SERVER['HTTP_HOST'] ?? (getenv('APP_DOMAIN') ?: 'api.siromove.com');
|
||||
|
||||
$basePath = rtrim(dirname(dirname(dirname($_SERVER['SCRIPT_NAME']))), '/');
|
||||
$url = "$protocol://$host{$basePath}/auth/uploads/{$country}/{$result['filename']}";
|
||||
|
||||
@@ -5,6 +5,21 @@
|
||||
// ============================================================
|
||||
|
||||
require_once __DIR__ . '/core/bootstrap.php';
|
||||
|
||||
// --------- تحقق من تطابق المنطقة (Region Mismatch Guard) ---------
|
||||
$requestHost = $_SERVER['HTTP_HOST'] ?? '';
|
||||
$appDomain = getenv('APP_DOMAIN') ?: '';
|
||||
if (!empty($appDomain) && !empty($requestHost) && strtolower($requestHost) !== strtolower($appDomain)) {
|
||||
if ($requestHost !== 'localhost' && !preg_match('/^127\.0\.0\./', $requestHost)) {
|
||||
http_response_code(400);
|
||||
exit(json_encode([
|
||||
'status' => 'failure',
|
||||
'error_code' => 'REGION_MISMATCH',
|
||||
'message' => "Region mismatch: Request host '$requestHost' does not match server domain '$appDomain'."
|
||||
]));
|
||||
}
|
||||
}
|
||||
|
||||
require_once __DIR__ . '/functions.php';
|
||||
|
||||
// 1. Rate Limiting and JWT Authentication
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
<?php
|
||||
require_once __DIR__ . '/core/bootstrap.php';
|
||||
try {
|
||||
$db = Database::get('main');
|
||||
$stmt = $db->prepare("UPDATE drivers SET status = 'pending_review' WHERE driverID = 'TEST202606252141546122'");
|
||||
$stmt->execute();
|
||||
echo "Driver status updated to pending_review successfully!";
|
||||
} catch (Exception $e) {
|
||||
echo "Error: " . $e->getMessage();
|
||||
}
|
||||
@@ -460,14 +460,17 @@ class AppLink {
|
||||
static String addNotesPassenger = "$serviceApp/addNotesPassenger.php";
|
||||
static String getPackages = "$serviceApp/getPackages.php";
|
||||
static String updatePackages = "$serviceApp/updatePackages.php";
|
||||
//////
|
||||
static String sendSms = "https://sms.kazumi.me/api/sms/send-sms";
|
||||
static String senddlr = "https://sms.kazumi.me/api/sms/send-dlr";
|
||||
static String sendvalidity = "https://sms.kazumi.me/api/sms/send-validity";
|
||||
static String sendmany = "https://sms.kazumi.me/api/sms/send-many";
|
||||
static String checkCredit = "https://sms.kazumi.me/api/sms/check-credit";
|
||||
static String getSender = "$server/auth/sms/getSender.php";
|
||||
static String checkStatus = "https://sms.kazumi.me/api/sms/check-status";
|
||||
static String updatePhoneInvalidSMSPassenger =
|
||||
"$server/auth/sms/updatePhoneInvalidSMSPassenger.php";
|
||||
|
||||
static String detectCountryFromPhone(String phone) {
|
||||
final clean = phone.replaceAll(RegExp(r'[^0-9]'), '');
|
||||
if (clean.startsWith('962')) return 'Jordan';
|
||||
if (clean.startsWith('963')) return 'Syria';
|
||||
if (clean.startsWith('20')) return 'Egypt';
|
||||
if (clean.startsWith('07') || clean.startsWith('7')) return 'Jordan';
|
||||
if (clean.startsWith('09') || clean.startsWith('9')) return 'Syria';
|
||||
if (clean.startsWith('01') || clean.startsWith('1')) return 'Egypt';
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -86,21 +86,21 @@ class DashboardController extends GetxController {
|
||||
update();
|
||||
}
|
||||
|
||||
sendSMSMethod() async {
|
||||
if (formKey.currentState!.validate()) {
|
||||
for (var phoneNumber in box.read(BoxName.tokensDrivers)['message']) {
|
||||
// for (var i = 0; i < 2; i++) {
|
||||
await CRUD().sendSmsEgypt(
|
||||
phoneNumber['phone'].toString(),
|
||||
// box.read(BoxName.tokensDrivers)['message'][i]['phone'].toString(),
|
||||
smsText.text,
|
||||
);
|
||||
// print('CRUD().phoneDriversTest.: ${phoneNumber['phone']}');
|
||||
Future.delayed(const Duration(microseconds: 20));
|
||||
}
|
||||
Get.back();
|
||||
}
|
||||
}
|
||||
// sendSMSMethod() async {
|
||||
// if (formKey.currentState!.validate()) {
|
||||
// for (var phoneNumber in box.read(BoxName.tokensDrivers)['message']) {
|
||||
// // for (var i = 0; i < 2; i++) {
|
||||
// await CRUD().sendSmsEgypt(
|
||||
// phoneNumber['phone'].toString(),
|
||||
// // box.read(BoxName.tokensDrivers)['message'][i]['phone'].toString(),
|
||||
// smsText.text,
|
||||
// );
|
||||
// // print('CRUD().phoneDriversTest.: ${phoneNumber['phone']}');
|
||||
// Future.delayed(const Duration(microseconds: 20));
|
||||
// }
|
||||
// Get.back();
|
||||
// }
|
||||
// }
|
||||
|
||||
@override
|
||||
void onInit() async {
|
||||
|
||||
@@ -26,7 +26,10 @@ class OtpHelper extends GetxController {
|
||||
/// إرسال OTP
|
||||
static Future<bool> sendOtp(String phoneNumber) async {
|
||||
try {
|
||||
// await CRUD().getJWT();
|
||||
final detectedCountry = AppLink.detectCountryFromPhone(phoneNumber);
|
||||
if (detectedCountry.isNotEmpty) {
|
||||
await box.write(BoxName.countryCode, detectedCountry);
|
||||
}
|
||||
final response = await CRUD().post(
|
||||
link: _sendOtpUrl,
|
||||
payload: {'receiver': phoneNumber, 'user_type': 'admin'},
|
||||
|
||||
@@ -48,7 +48,8 @@ class CRUD {
|
||||
final jwt = decodedResponse1['jwt'];
|
||||
Log.print('jwt: $jwt');
|
||||
await box.write(BoxName.jwt, X.c(X.c(X.c(jwt, cn), cC), cs));
|
||||
await storage.write(key: BoxName.jwt, value: X.c(X.c(X.c(jwt, cn), cC), cs));
|
||||
await storage.write(
|
||||
key: BoxName.jwt, value: X.c(X.c(X.c(jwt, cn), cC), cs));
|
||||
// await AppInitializer().getKey();
|
||||
}
|
||||
}
|
||||
@@ -448,8 +449,7 @@ class CRUD {
|
||||
return response.statusCode;
|
||||
}
|
||||
|
||||
Future allMethodForAI(String prompt, driverID, imagePath) async {
|
||||
}
|
||||
Future allMethodForAI(String prompt, driverID, imagePath) async {}
|
||||
|
||||
Map<String, List<Map<String, String>>> getAllTextValuesWithLineNumbers(
|
||||
Map json) {
|
||||
@@ -569,7 +569,6 @@ class CRUD {
|
||||
return response.statusCode;
|
||||
}
|
||||
|
||||
|
||||
Future<dynamic> kazumiSMS({
|
||||
required String link,
|
||||
Map<String, dynamic>? payload,
|
||||
@@ -594,25 +593,6 @@ class CRUD {
|
||||
} else {}
|
||||
}
|
||||
|
||||
Future<dynamic> sendSmsEgypt(String phone, otp) async {
|
||||
// String sender = await getSender();
|
||||
var headers = {'Content-Type': 'application/json'};
|
||||
var body = jsonEncode({
|
||||
"username": "Sefer",
|
||||
"password": "E)Pu=an/@Z",
|
||||
"message": otp,
|
||||
"language": "e",
|
||||
"sender": "Sefer Egy",
|
||||
"receiver": phone
|
||||
});
|
||||
|
||||
await _client.post(
|
||||
Uri.parse(AppLink.sendSms),
|
||||
body: body,
|
||||
headers: headers,
|
||||
);
|
||||
}
|
||||
|
||||
Future<dynamic> postPayMob({
|
||||
required String link,
|
||||
Map<String, dynamic>? payload,
|
||||
|
||||
@@ -622,4 +622,15 @@ class AppLink {
|
||||
"$serviceApp/getComplaintAllData.php";
|
||||
static String get getComplaintAllDataForDriver =>
|
||||
"$serviceApp/getComplaintAllDataForDriver.php";
|
||||
|
||||
static String detectCountryFromPhone(String phone) {
|
||||
final clean = phone.replaceAll(RegExp(r'[^0-9]'), '');
|
||||
if (clean.startsWith('962')) return 'Jordan';
|
||||
if (clean.startsWith('963')) return 'Syria';
|
||||
if (clean.startsWith('20')) return 'Egypt';
|
||||
if (clean.startsWith('07') || clean.startsWith('7')) return 'Jordan';
|
||||
if (clean.startsWith('09') || clean.startsWith('9')) return 'Syria';
|
||||
if (clean.startsWith('01') || clean.startsWith('1')) return 'Egypt';
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -24,6 +24,10 @@ class PhoneAuthHelper {
|
||||
/// Sends an OTP to the provided phone number.
|
||||
static Future<bool> sendOtp(String phoneNumber) async {
|
||||
try {
|
||||
final detectedCountry = AppLink.detectCountryFromPhone(phoneNumber);
|
||||
if (detectedCountry.isNotEmpty) {
|
||||
await box.write(BoxName.countryCode, detectedCountry);
|
||||
}
|
||||
final fixedPhone = CountryLogic.formatCurrentCountryPhone(phoneNumber);
|
||||
Log.print('fixedPhone: $fixedPhone');
|
||||
|
||||
|
||||
@@ -526,4 +526,15 @@ class AppLink {
|
||||
static String get checkStatus => "https://sms.kazumi.me/api/sms/check-status";
|
||||
static String get updatePhoneInvalidSMSPassenger =>
|
||||
"$server/auth/sms/updatePhoneInvalidSMSPassenger.php";
|
||||
|
||||
static String detectCountryFromPhone(String phone) {
|
||||
final clean = phone.replaceAll(RegExp(r'[^0-9]'), '');
|
||||
if (clean.startsWith('962')) return 'Jordan';
|
||||
if (clean.startsWith('963')) return 'Syria';
|
||||
if (clean.startsWith('20')) return 'Egypt';
|
||||
if (clean.startsWith('07') || clean.startsWith('7')) return 'Jordan';
|
||||
if (clean.startsWith('09') || clean.startsWith('9')) return 'Syria';
|
||||
if (clean.startsWith('01') || clean.startsWith('1')) return 'Egypt';
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,6 +23,10 @@ class PhoneAuthHelper {
|
||||
/// Sends an OTP to the provided phone number.
|
||||
static Future<bool> sendOtp(String phoneNumber) async {
|
||||
try {
|
||||
final detectedCountry = AppLink.detectCountryFromPhone(phoneNumber);
|
||||
if (detectedCountry.isNotEmpty) {
|
||||
await box.write(BoxName.countryCode, detectedCountry);
|
||||
}
|
||||
// إصلاح الرقم قبل الإرسال
|
||||
final fixedPhone = CountryLogic.formatCurrentCountryPhone(phoneNumber);
|
||||
|
||||
|
||||
@@ -188,4 +188,15 @@ class AppLink {
|
||||
static String addCartoDriver = "$serviceApp/addCartoDriver.php";
|
||||
static String getRegisrationCar = "$ride/RegisrationCar/get.php";
|
||||
static String updateRegisrationCar = "$ride/RegisrationCar/update.php";
|
||||
|
||||
static String detectCountryFromPhone(String phone) {
|
||||
final clean = phone.replaceAll(RegExp(r'[^0-9]'), '');
|
||||
if (clean.startsWith('962')) return 'Jordan';
|
||||
if (clean.startsWith('963')) return 'Syria';
|
||||
if (clean.startsWith('20')) return 'Egypt';
|
||||
if (clean.startsWith('07') || clean.startsWith('7')) return 'Jordan';
|
||||
if (clean.startsWith('09') || clean.startsWith('9')) return 'Syria';
|
||||
if (clean.startsWith('01') || clean.startsWith('1')) return 'Egypt';
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,6 +22,12 @@ class LoginController extends GetxController {
|
||||
final FlutterSecureStorage storage = const FlutterSecureStorage();
|
||||
|
||||
void login() async {
|
||||
final emailStr = email.text.trim();
|
||||
final detectedCountry = AppLink.detectCountryFromPhone(emailStr);
|
||||
if (detectedCountry.isNotEmpty) {
|
||||
await box.write(BoxName.countryCode, detectedCountry);
|
||||
}
|
||||
|
||||
// Ensure fingerprint is ready
|
||||
String fingerprint = box.read(BoxName.fingerPrint) ?? '';
|
||||
if (fingerprint.isEmpty) {
|
||||
|
||||
@@ -50,7 +50,8 @@ class MainController extends GetxController {
|
||||
@override
|
||||
void onInit() {
|
||||
super.onInit();
|
||||
// refreshDashboardStats(); // Removed to save data consumption at start
|
||||
final country = box.read('countryCode')?.toString() ?? 'Jordan';
|
||||
Log.print('🌍 [SIRO-SERVICE-STARTUP] Current countryCode stored in box: $country');
|
||||
}
|
||||
|
||||
Future<void> refreshDashboardStats() async {
|
||||
|
||||
@@ -123,6 +123,42 @@ class ReviewDriverController extends GetxController {
|
||||
};
|
||||
|
||||
List<List<dynamic>> getFieldsForTab(String tabKey) {
|
||||
final countryCode = country;
|
||||
if (countryCode == 'Syria') {
|
||||
if (tabKey == 'driver_license_front') {
|
||||
return [
|
||||
['licenseTypeController', 'License Type', false, false, false, false],
|
||||
[
|
||||
'licenseIssueDateController',
|
||||
'License Issue Date',
|
||||
true,
|
||||
false,
|
||||
false,
|
||||
false
|
||||
],
|
||||
[
|
||||
'expiryDateController',
|
||||
'License Expiry Date',
|
||||
true,
|
||||
false,
|
||||
false,
|
||||
false
|
||||
],
|
||||
];
|
||||
}
|
||||
if (tabKey == 'driver_license_back') {
|
||||
return [
|
||||
[
|
||||
'licenseCategoriesController',
|
||||
'License Categories',
|
||||
false,
|
||||
false,
|
||||
false,
|
||||
false
|
||||
],
|
||||
];
|
||||
}
|
||||
}
|
||||
return fieldConfig[tabKey] ?? [];
|
||||
}
|
||||
|
||||
@@ -161,6 +197,10 @@ class ReviewDriverController extends GetxController {
|
||||
driverId.value = args['driverId'] ?? '';
|
||||
phone.value = args['phone'] ?? '';
|
||||
}
|
||||
if (country == 'Jordan' || country == 'Egypt') {
|
||||
docUrls.remove('driver_license_back');
|
||||
}
|
||||
_initializeDocUrls();
|
||||
fetchData();
|
||||
}
|
||||
|
||||
@@ -210,13 +250,64 @@ class ReviewDriverController extends GetxController {
|
||||
}
|
||||
}
|
||||
|
||||
String reconstructDocumentUrl(String originalLink, String docType) {
|
||||
if (originalLink.isEmpty) {
|
||||
return "${AppLink.server}/auth/syria/driversDocs/syria.intaleq.xyz-${driverId.value}-$docType.jpg";
|
||||
}
|
||||
|
||||
try {
|
||||
final origUri = Uri.parse(originalLink);
|
||||
final query = origUri.query;
|
||||
final path = origUri.path;
|
||||
|
||||
if (path.contains('secure_image.php')) {
|
||||
return "${AppLink.server}/secure_image.php?$query";
|
||||
}
|
||||
|
||||
if (path.contains('auth/syria/driversDocs/')) {
|
||||
final parts = path.split('auth/syria/driversDocs/');
|
||||
final filename = parts.last;
|
||||
return "${AppLink.server}/auth/syria/driversDocs/$filename";
|
||||
}
|
||||
|
||||
if (originalLink.startsWith('http://') ||
|
||||
originalLink.startsWith('https://')) {
|
||||
final serverUri = Uri.parse(AppLink.server);
|
||||
final host = serverUri.host;
|
||||
|
||||
final newUri = Uri(
|
||||
scheme: 'https',
|
||||
host: host,
|
||||
path: path,
|
||||
query: query.isNotEmpty ? query : null,
|
||||
);
|
||||
return newUri.toString();
|
||||
}
|
||||
|
||||
final cleanPath = path.startsWith('/') ? path : '/$path';
|
||||
return "${AppLink.server}$cleanPath${query.isNotEmpty ? '?$query' : ''}";
|
||||
} catch (e) {
|
||||
if (originalLink.startsWith('http://')) {
|
||||
return originalLink.replaceFirst('http://', 'https://');
|
||||
}
|
||||
return originalLink;
|
||||
}
|
||||
}
|
||||
|
||||
void _initializeDocUrls() {
|
||||
for (var key in docUrls.keys) {
|
||||
docUrls[key]!.value = reconstructDocumentUrl('', key);
|
||||
}
|
||||
}
|
||||
|
||||
void _populateDocUrls(dynamic docs) {
|
||||
if (docs is List) {
|
||||
for (var doc in docs) {
|
||||
if (doc is Map && doc['doc_type'] != null && doc['link'] != null) {
|
||||
String type = doc['doc_type'].toString();
|
||||
if (docUrls.containsKey(type)) {
|
||||
docUrls[type]!.value = doc['link'].toString();
|
||||
docUrls[type]!.value =
|
||||
reconstructDocumentUrl(doc['link'].toString(), type);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user