with encrypted data on envolope submit
This commit is contained in:
@@ -11,13 +11,27 @@ import {
|
||||
} from 'react-native';
|
||||
import RNFS from 'react-native-fs';
|
||||
import * as XLSX from 'xlsx';
|
||||
import axios from 'axios';
|
||||
import axios, { AxiosError } from 'axios';
|
||||
import { useSelector } from 'react-redux';
|
||||
import colors from '../../../Constant/Color';
|
||||
import { GET_ENVELOPE_C, SUBMIT_ENVELOPE_C_UPLOAD } from '../../../Services/BBPS/ApiUrls';
|
||||
import { GET_ENVELOPE_C, SUBMIT_ENVELOPE_C_UPLOAD } from '../../../Services/ApiCall/ApiUrls';
|
||||
import { useNavigation } from '@react-navigation/native';
|
||||
import { encrypt, encryptWithRSA } from '../../../Services/Encryption/encrypt';
|
||||
|
||||
|
||||
/* -------------------- UTILS -------------------- */
|
||||
interface OfficerKey {
|
||||
officersId: number;
|
||||
officerPublicKey: string;
|
||||
officerType: string;
|
||||
}
|
||||
|
||||
|
||||
interface SaveEnvelopeOfficerDetail {
|
||||
officerId: number;
|
||||
officerEncryptedKey: string;
|
||||
officerType: string;
|
||||
}
|
||||
|
||||
// Convert ArrayBuffer → Base64
|
||||
const arrayBufferToBase64 = (buffer: ArrayBuffer) => {
|
||||
@@ -29,37 +43,54 @@ const arrayBufferToBase64 = (buffer: ArrayBuffer) => {
|
||||
return global.btoa(binary);
|
||||
};
|
||||
|
||||
|
||||
// Find column dynamically by keywords
|
||||
const findColumnKey = (columns: string[], keywords: string[]) =>
|
||||
columns.find(col =>
|
||||
keywords.some(k => col.toLowerCase().includes(k.toLowerCase()))
|
||||
);
|
||||
|
||||
|
||||
// Detect TOTAL row (any column contains TOTAL)
|
||||
const isTotalRow = (row: any) =>
|
||||
Object.values(row).some(v => String(v).toUpperCase() === 'TOTAL');
|
||||
|
||||
|
||||
/* -------------------- COMPONENT -------------------- */
|
||||
|
||||
|
||||
const EnvelopeCExcelPreview = (props: any) => {
|
||||
const tenderData = props;
|
||||
console.log("Tender Data",tenderData)
|
||||
const token = useSelector((state: any) => state.token.token);
|
||||
const navigation = useNavigation() as any;
|
||||
|
||||
|
||||
const [data, setData] = useState<any[]>([]);
|
||||
const [columns, setColumns] = useState<string[]>([]);
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
loadExcelFromApi();
|
||||
}, []);
|
||||
|
||||
|
||||
/* -------------------- LOAD EXCEL -------------------- */
|
||||
|
||||
|
||||
const loadExcelFromApi = async () => {
|
||||
try {
|
||||
setLoading(true);
|
||||
|
||||
|
||||
console.log('\n📊 LOADING EXCEL FROM API');
|
||||
console.log('═══════════════════════════════════════════════════════');
|
||||
console.log('🔗 API URL:', `${GET_ENVELOPE_C}${tenderData?.tenderId?.tenderId}`);
|
||||
console.log('🆔 Tender ID:', tenderData?.tenderId?.tenderId);
|
||||
console.log('🔑 Token:', token.token ? 'Present' : 'Missing');
|
||||
|
||||
|
||||
const response = await axios.get(
|
||||
`${GET_ENVELOPE_C}${tenderData?.tenderId?.tenderId}`,
|
||||
{
|
||||
@@ -70,45 +101,71 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
}
|
||||
);
|
||||
|
||||
|
||||
console.log('\n✅ API RESPONSE RECEIVED');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
console.log('📡 Status:', response.status);
|
||||
console.log('📡 Status Text:', response.statusText);
|
||||
console.log('📦 Response Data Size (KB):', (response.data.byteLength / 1024).toFixed(2));
|
||||
|
||||
|
||||
const base64 = arrayBufferToBase64(response.data);
|
||||
const workbook = XLSX.read(base64, { type: 'base64' });
|
||||
const sheet = workbook.Sheets[workbook.SheetNames[0]];
|
||||
const rows: any[] = XLSX.utils.sheet_to_json(sheet, { defval: '' });
|
||||
|
||||
|
||||
console.log('📊 PARSED DATA - Total Rows:', rows.length);
|
||||
|
||||
|
||||
setColumns(Object.keys(rows[0] || {}));
|
||||
setData(rows);
|
||||
|
||||
} catch (e) {
|
||||
Alert.alert('Error', 'Failed to load Excel');
|
||||
|
||||
console.log('✅ EXCEL LOADED SUCCESSFULLY\n');
|
||||
|
||||
|
||||
} catch (e: any) {
|
||||
console.log('\n❌ ERROR LOADING EXCEL');
|
||||
console.error('Error:', e.message);
|
||||
Alert.alert('Error', 'Failed to load Excel: ' + e.message);
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/* -------------------- UPDATE CELL -------------------- */
|
||||
|
||||
|
||||
const updateCell = (rowIndex: number, key: string, value: string) => {
|
||||
const updated = [...data];
|
||||
const row = updated[rowIndex];
|
||||
|
||||
|
||||
if (isTotalRow(row)) return;
|
||||
|
||||
|
||||
const qtyKey:any = findColumnKey(columns, ['qty', 'quantity']);
|
||||
const rateKey:any = findColumnKey(columns, ['rate', 'price']);
|
||||
const valueKey = findColumnKey(columns, ['value', 'amount', 'total']);
|
||||
|
||||
|
||||
if (key === qtyKey || key === rateKey) {
|
||||
row[key] = value;
|
||||
|
||||
|
||||
const qty = Number(row[qtyKey]);
|
||||
const rate = Number(row[rateKey]);
|
||||
|
||||
|
||||
if (valueKey) {
|
||||
row[valueKey] =
|
||||
!isNaN(qty) && !isNaN(rate) ? qty * rate : 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Recalculate TOTAL
|
||||
const totalRowIndex = updated.findIndex(isTotalRow);
|
||||
if (totalRowIndex !== -1 && valueKey) {
|
||||
@@ -119,67 +176,248 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
}, 0);
|
||||
}
|
||||
|
||||
|
||||
setData(updated);
|
||||
};
|
||||
|
||||
|
||||
/* -------------------- SAVE & UPLOAD EXCEL -------------------- */
|
||||
|
||||
|
||||
const buildOfficerEncryptedKeys = (envelopeKey: string): SaveEnvelopeOfficerDetail[] => {
|
||||
const officerKeys: OfficerKey[] = tenderData?.tenderId?.envelopeKeyDetailsResDTO?.departmentOfficerPublicKeys || [];
|
||||
|
||||
|
||||
console.log('\n🔐 ENCRYPTING ENVELOPE KEY FOR OFFICERS');
|
||||
console.log('═══════════════════════════════════════════════════════');
|
||||
console.log('📌 Envelope Key to encrypt:', envelopeKey);
|
||||
console.log('👥 Number of officers:', officerKeys.length);
|
||||
|
||||
|
||||
const encryptedKeys: SaveEnvelopeOfficerDetail[] = [];
|
||||
|
||||
|
||||
for (let i = 0; i < officerKeys.length; i++) {
|
||||
const officer = officerKeys[i];
|
||||
console.log(`\n🔄 Officer ${i + 1}/${officerKeys.length}`);
|
||||
console.log(' ID:', officer.officersId);
|
||||
console.log(' Type:', officer.officerType);
|
||||
|
||||
|
||||
try {
|
||||
const encryptedKey = encryptWithRSA(envelopeKey, officer.officerPublicKey);
|
||||
|
||||
|
||||
if (!encryptedKey) {
|
||||
console.error(` ❌ FAILED to encrypt key for officer ${officer.officersId}`);
|
||||
} else {
|
||||
console.log(` ✅ SUCCESS - Encrypted key length: ${encryptedKey.length}`);
|
||||
}
|
||||
|
||||
|
||||
encryptedKeys.push({
|
||||
officerId: officer.officersId,
|
||||
officerEncryptedKey: encryptedKey || '',
|
||||
officerType: officer.officerType,
|
||||
});
|
||||
} catch (error) {
|
||||
console.error(` ❌ ERROR encrypting for officer ${officer.officersId}:`, error);
|
||||
encryptedKeys.push({
|
||||
officerId: officer.officersId,
|
||||
officerEncryptedKey: '',
|
||||
officerType: officer.officerType,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
console.log('\n✅ ALL OFFICER KEYS ENCRYPTED');
|
||||
console.log('═══════════════════════════════════════════════════════\n');
|
||||
return encryptedKeys;
|
||||
};
|
||||
|
||||
|
||||
// ✅ NEW: Encrypt Excel file content (binary) after creation
|
||||
const encryptExcelFile = async (filePath: string, encryptionKey: string): Promise<string> => {
|
||||
console.log('\n🔐 ENCRYPTING EXCEL FILE CONTENT');
|
||||
console.log('═══════════════════════════════════════════════════════');
|
||||
console.log('📁 File Path:', filePath);
|
||||
console.log('🔑 Encryption Key:', encryptionKey);
|
||||
|
||||
|
||||
try {
|
||||
// Read the Excel file as Base64
|
||||
const fileContent = await RNFS.readFile(filePath, 'base64');
|
||||
console.log('📖 File read successfully, Base64 length:', fileContent.length);
|
||||
|
||||
|
||||
// Encrypt the entire file content
|
||||
console.log('🔒 Encrypting file content...');
|
||||
const encryptedContent:any = encrypt(fileContent, encryptionKey);
|
||||
console.log('✅ File content encrypted, Encrypted length:', encryptedContent?.length);
|
||||
|
||||
|
||||
// Save encrypted content to a new file
|
||||
const encryptedFilePath = `${RNFS.DocumentDirectoryPath}/envelopeC_encrypted.xlsx`;
|
||||
await RNFS.writeFile(encryptedFilePath, encryptedContent, 'utf8');
|
||||
console.log('💾 Encrypted file saved at:', encryptedFilePath);
|
||||
|
||||
|
||||
console.log('✅ EXCEL FILE ENCRYPTION COMPLETED');
|
||||
console.log('═══════════════════════════════════════════════════════\n');
|
||||
|
||||
|
||||
return encryptedFilePath;
|
||||
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ ERROR ENCRYPTING EXCEL FILE:', error);
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
const saveUpdatedExcel = async () => {
|
||||
try {
|
||||
setLoading(true);
|
||||
|
||||
|
||||
console.log('\n💾 SAVING UPDATED EXCEL');
|
||||
console.log('═══════════════════════════════════════════════════════');
|
||||
|
||||
|
||||
const ENCRYPTION_KEY = tenderData?.tenderId?.envelopeKeyDetailsResDTO?.envelopeCGenerateKey || '';
|
||||
|
||||
if (!ENCRYPTION_KEY) {
|
||||
console.error('❌ ENCRYPTION KEY NOT FOUND');
|
||||
Alert.alert('Error', 'Encryption key not available');
|
||||
setLoading(false);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
console.log('🔑 Encryption Key:', ENCRYPTION_KEY);
|
||||
|
||||
|
||||
// Step 1: Create normal Excel workbook with user data (NOT ENCRYPTED YET)
|
||||
console.log('\n📝 STEP 1: Creating Excel workbook with user data');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
const worksheet = XLSX.utils.json_to_sheet(data);
|
||||
const workbook = XLSX.utils.book_new();
|
||||
XLSX.utils.book_append_sheet(workbook, worksheet, 'Sheet1');
|
||||
|
||||
|
||||
const binary = XLSX.write(workbook, {
|
||||
bookType: 'xlsx',
|
||||
type: 'binary',
|
||||
});
|
||||
|
||||
|
||||
const buffer = new Uint8Array(binary.length);
|
||||
for (let i = 0; i < binary.length; i++) {
|
||||
buffer[i] = binary.charCodeAt(i) & 0xff;
|
||||
}
|
||||
|
||||
const filePath = `${RNFS.DocumentDirectoryPath}/envelopeC_updated.xlsx`;
|
||||
await RNFS.writeFile(filePath, buffer.toString(), 'ascii');
|
||||
|
||||
// Step 2: Save the plain Excel file
|
||||
console.log('\n📝 STEP 2: Saving plain Excel file');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
const plainFilePath = `${RNFS.DocumentDirectoryPath}/envelopeC_plain.xlsx`;
|
||||
await RNFS.writeFile(plainFilePath, buffer.toString(), 'ascii');
|
||||
console.log('✅ Plain Excel saved at:', plainFilePath);
|
||||
|
||||
|
||||
// Step 3: Encrypt the entire Excel file
|
||||
console.log('\n📝 STEP 3: Encrypting the Excel file');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
const encryptedFilePath = await encryptExcelFile(plainFilePath, ENCRYPTION_KEY);
|
||||
console.log('✅ Encrypted Excel file ready');
|
||||
|
||||
|
||||
// Step 4: Build officer encrypted keys
|
||||
console.log('\n📝 STEP 4: Building officer encrypted keys');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
const officerEncryptedKeys = buildOfficerEncryptedKeys(ENCRYPTION_KEY);
|
||||
|
||||
|
||||
// Step 5: Prepare FormData for upload
|
||||
console.log('\n📝 STEP 5: Building FormData');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
const formData = new FormData();
|
||||
formData.append(
|
||||
'requestDto',
|
||||
JSON.stringify({
|
||||
tenderId: tenderData?.tenderId?.tenderId,
|
||||
deptId: tenderData?.tenderId?.deptId,
|
||||
typesOfTender: tenderData?.tenderId?.typesOfTender,
|
||||
fieldValue: '',
|
||||
fieldValueInWord: 'zero',
|
||||
})
|
||||
);
|
||||
const requestDto = {
|
||||
tenderId: tenderData?.tenderId?.tenderId,
|
||||
deptId: tenderData?.tenderId?.deptId,
|
||||
typesOfTender: tenderData?.tenderId?.typesOfTender,
|
||||
fieldValue: '',
|
||||
fieldValueInWord: 'zero',
|
||||
deviceType: 'MOBILE',
|
||||
fileName: 'envelopeC_encrypted.xlsx',
|
||||
saveEnvelopesOfficersDetailsResDTO: officerEncryptedKeys,
|
||||
};
|
||||
|
||||
|
||||
formData.append('requestDto', JSON.stringify(requestDto));
|
||||
|
||||
|
||||
// Use the ENCRYPTED file for upload
|
||||
formData.append('file', {
|
||||
uri: `file://${filePath}`,
|
||||
name: 'envelopeC_updated.xlsx',
|
||||
uri: `file://${encryptedFilePath}`,
|
||||
name: 'envelopeC_encrypted.xlsx',
|
||||
type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
|
||||
});
|
||||
} as any);
|
||||
|
||||
await axios.post(SUBMIT_ENVELOPE_C_UPLOAD, formData, {
|
||||
|
||||
console.log('📋 Request DTO:', JSON.stringify(requestDto, null, 2));
|
||||
console.log('📎 Encrypted File Path:', encryptedFilePath);
|
||||
|
||||
|
||||
// Step 6: Upload to server
|
||||
console.log('\n📝 STEP 6: Uploading encrypted file to server');
|
||||
console.log('───────────────────────────────────────────────────────');
|
||||
console.log('FormData prepared:', formData);
|
||||
|
||||
|
||||
const response = await axios.post(SUBMIT_ENVELOPE_C_UPLOAD, formData, {
|
||||
headers: {
|
||||
'Content-Type': 'multipart/form-data',
|
||||
Authentication: `Bearer ${token.token}`,
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
console.log('✅ UPLOAD SUCCESSFUL');
|
||||
console.log('Response:', response.data);
|
||||
console.log('═══════════════════════════════════════════════════════\n');
|
||||
|
||||
|
||||
// Clean up temporary files
|
||||
await RNFS.unlink(plainFilePath).catch(e => console.log('Plain file cleanup:', e.message));
|
||||
await RNFS.unlink(encryptedFilePath).catch(e => console.log('Encrypted file cleanup:', e.message));
|
||||
|
||||
|
||||
Alert.alert('Success', 'Excel uploaded successfully');
|
||||
navigation.goBack();
|
||||
} catch (e) {
|
||||
Alert.alert('Error', 'Save failed');
|
||||
|
||||
|
||||
} catch (e: any) {
|
||||
console.error('❌ Error saving/uploading Excel:', {
|
||||
message: e?.message,
|
||||
response: e?.response?.data,
|
||||
status: e?.response?.status,
|
||||
statusText: e?.response?.statusText,
|
||||
});
|
||||
|
||||
|
||||
Alert.alert('Error', e?.response?.data?.message || 'Save failed');
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/* -------------------- UI -------------------- */
|
||||
|
||||
|
||||
if (loading) {
|
||||
return (
|
||||
<View style={styles.loader}>
|
||||
@@ -188,10 +426,12 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
const qtyKey = findColumnKey(columns, ['qty', 'quantity']);
|
||||
const rateKey = findColumnKey(columns, ['rate', 'price']);
|
||||
const valueKey = findColumnKey(columns, ['value', 'amount', 'total']);
|
||||
|
||||
|
||||
return (
|
||||
<View style={styles.container}>
|
||||
<ScrollView horizontal contentContainerStyle={{ padding: 10 }}>
|
||||
@@ -203,6 +443,7 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
))}
|
||||
</View>
|
||||
|
||||
|
||||
{/* DATA */}
|
||||
<ScrollView style={{ maxHeight: 420 }}>
|
||||
{data.map((row, rowIndex) => (
|
||||
@@ -211,6 +452,7 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
const editable =
|
||||
!isTotalRow(row) && (key === qtyKey || key === rateKey);
|
||||
|
||||
|
||||
return (
|
||||
<TextInput
|
||||
key={key}
|
||||
@@ -234,6 +476,7 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
</View>
|
||||
</ScrollView>
|
||||
|
||||
|
||||
{tenderData?.buttonEnable && (
|
||||
<TouchableOpacity style={styles.button} onPress={saveUpdatedExcel}>
|
||||
<Text style={styles.buttonText}>Save Updated Excel</Text>
|
||||
@@ -243,10 +486,13 @@ const EnvelopeCExcelPreview = (props: any) => {
|
||||
);
|
||||
};
|
||||
|
||||
|
||||
export default EnvelopeCExcelPreview;
|
||||
|
||||
|
||||
/* -------------------- STYLES -------------------- */
|
||||
|
||||
|
||||
const styles = StyleSheet.create({
|
||||
container: { flex: 1, backgroundColor: '#fff' },
|
||||
loader: { flex: 1, justifyContent: 'center', alignItems: 'center' },
|
||||
@@ -282,4 +528,4 @@ const styles = StyleSheet.create({
|
||||
textAlign: 'center',
|
||||
fontWeight: '600',
|
||||
},
|
||||
});
|
||||
});
|
||||
@@ -2,7 +2,7 @@ import React, { useCallback, useState, useEffect } from 'react';
|
||||
import { View, FlatList, ActivityIndicator, RefreshControl, Text } from 'react-native';
|
||||
import Animated, { FadeInDown, FadeOutUp } from 'react-native-reanimated';
|
||||
import { useNavigation } from '@react-navigation/native';
|
||||
import { useFetchLiveAuction, useFetchLiveTender } from '../../Services/BBPS/Hooks';
|
||||
import { useFetchLiveAuction, useFetchLiveTender } from '../../Services/ApiCall/Hooks';
|
||||
import { SearchInput } from '../../Component/Serach/SeacrhInput';
|
||||
import { Skelton } from '../../Component/Index';
|
||||
import colors from '../../Constant/Color';
|
||||
@@ -14,10 +14,8 @@ const LiveTender = () => {
|
||||
const navigation: any = useNavigation();
|
||||
const Dispatch = useDispatch()
|
||||
const user = useSelector((state: any) => state?.token.token);
|
||||
console.log("userdata",user)
|
||||
const SelectedPurchaseList = useSelector((state: any) => state.selectPurchaseTender);
|
||||
const { data, fetchNextPage, hasNextPage, isFetchingNextPage, isLoading, isRefetching, refetch }: any = useFetchLiveTender();
|
||||
console.log("to show ",data)
|
||||
const [showRefreshBanner, setShowRefreshBanner] = useState(false);
|
||||
|
||||
useEffect(() => {
|
||||
@@ -49,7 +47,6 @@ const LiveTender = () => {
|
||||
|
||||
const renderItem = useCallback(
|
||||
({ item, index }: any) => {
|
||||
console.log("opopopopoopopopop",item.tenderNumber,item)
|
||||
if(item.tenderStatus==="Cancelled") return null;
|
||||
const isPurchase = SelectedPurchaseList.findIndex((prev: any) => prev.tenderId === item.tenderId)
|
||||
return <LiveTenderTile
|
||||
|
||||
@@ -12,11 +12,11 @@ import {
|
||||
import { useRoute, useNavigation } from '@react-navigation/native';
|
||||
import {
|
||||
useFetchLiveTenderById,
|
||||
} from '../../Services/BBPS/Hooks';
|
||||
} from '../../Services/ApiCall/Hooks';
|
||||
import { InsideHeader } from '../../Component/Index';
|
||||
import colors from '../../Constant/Color';
|
||||
import ReactNativeBlobUtil from 'react-native-blob-util';
|
||||
import { GET_DOCID } from '../../Services/BBPS/ApiUrls';
|
||||
import { GET_DOCID } from '../../Services/ApiCall/ApiUrls';
|
||||
import {
|
||||
Layers,
|
||||
Briefcase,
|
||||
@@ -50,9 +50,7 @@ const LiveTenderDetail = () => {
|
||||
const route = useRoute<any>();
|
||||
const navigation = useNavigation<any>();
|
||||
const tender = route?.params;
|
||||
console.log("object---",tender)
|
||||
const { data } = useFetchLiveTenderById(tender?.tenderId);
|
||||
console.log("huh",data)
|
||||
const [downloadingId, setDownloadingId] = useState<string | number | null>(null);
|
||||
const insets = useSafeAreaInsets()
|
||||
if (!data?.data?.[0]) return null;
|
||||
|
||||
@@ -30,7 +30,6 @@ const LiveTenderTile: React.FC<LiveTenderTileProps> = ({
|
||||
: [];
|
||||
|
||||
const purchased = contractorIds.includes(String(contractorId));
|
||||
console.log("item is ",data)
|
||||
if(data.tenderStatus==="Amended"){
|
||||
|
||||
}
|
||||
|
||||
@@ -23,7 +23,7 @@ import {
|
||||
} from 'lucide-react-native';
|
||||
import colors from '../../../Constant/Color';
|
||||
import { useSafeAreaInsets } from 'react-native-safe-area-context';
|
||||
import { useFetchTenderById } from '../../../Services/BBPS/Hooks';
|
||||
import { useFetchTenderById } from '../../../Services/ApiCall/Hooks';
|
||||
|
||||
interface Props {
|
||||
visible: boolean;
|
||||
|
||||
@@ -3,7 +3,7 @@ import React, { useCallback, useEffect } from 'react'
|
||||
import { InsideHeader } from '../../Component/Index'
|
||||
import colors from '../../Constant/Color'
|
||||
import { useFocusEffect, useNavigation, useRoute } from '@react-navigation/native'
|
||||
import { useFetchTenderById, useProceedToBid } from '../../Services/BBPS/Hooks'
|
||||
import { useFetchTenderById, useProceedToBid } from '../../Services/ApiCall/Hooks'
|
||||
|
||||
const ProceedToBidDetail = () => {
|
||||
// Sample data based on your JSON
|
||||
@@ -12,13 +12,10 @@ const ProceedToBidDetail = () => {
|
||||
const { data, refetch, isRefetching } = useProceedToBid(tenderDataId?.tenderId);
|
||||
const { data: tenderResponse, refetch: tenderRefetch }: any = useFetchTenderById(tenderDataId?.tenderId);
|
||||
const tenderData = tenderResponse?.data;
|
||||
console.log("dataopop",tenderData)
|
||||
const [refreshing, setRefreshing] = React.useState(false);
|
||||
const [loading, setLoading] = React.useState(false);
|
||||
|
||||
// console.log("proceed to bid tender detail : ", tenderDataId)
|
||||
// console.log("proceed to data detail : ", data)
|
||||
// console.log("tender data for updated : ", tenderData)
|
||||
|
||||
const navigation = useNavigation<any>()
|
||||
// Format date from array
|
||||
|
||||
@@ -176,7 +173,11 @@ const ProceedToBidDetail = () => {
|
||||
<View style={styles.statusGrid}>
|
||||
<StatusIndicator status={tenderData?.envelopeASubmittStatus} label="Envelope A" />
|
||||
{tenderData?.showEB &&<StatusIndicator status={tenderData?.envelopeBSubmittStatus} label="Envelope B" />}
|
||||
{tenderData?.showLCS &&<StatusIndicator status={tenderData?.envelopeBSubmittStatus} label="Envelope LCS" />}
|
||||
{tenderData?.showQCBS &&<StatusIndicator status={tenderData?.envelopeBSubmittStatus} label="Envelope QCBS" />}
|
||||
{tenderData?.showEC &&<StatusIndicator status={tenderData?.envelopeCSubmittStatus} label="Envelope C" />}
|
||||
|
||||
|
||||
</View>
|
||||
</View>
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ import { InsideHeader, Loader } from '../../Component/Index';
|
||||
import colors from '../../Constant/Color';
|
||||
import { CreditCard, Calendar, User, DollarSign, ArrowRight } from 'lucide-react-native';
|
||||
import { useDispatch, useSelector } from 'react-redux';
|
||||
import { useOfflineTenderPurchase } from '../../Services/BBPS/Hooks';
|
||||
import { useOfflineTenderPurchase } from '../../Services/ApiCall/Hooks';
|
||||
import { StackActions, useNavigation } from '@react-navigation/native';
|
||||
import NavigationString from '../../Constant/NavigationString';
|
||||
import { showErrorAlert, showToast } from '../../Constant/ShowDailog';
|
||||
@@ -50,11 +50,9 @@ const ProceedToPurTender = () => {
|
||||
orderNo: orderNo,
|
||||
};
|
||||
|
||||
console.log("tender offline body : ", body)
|
||||
try {
|
||||
mutate(body, {
|
||||
onSuccess: (res) => {
|
||||
console.log(res, '---------------------purchsase response');
|
||||
if (res.statusCode === 200) {
|
||||
showToast(res.message);
|
||||
navigation.dispatch(StackActions.pop(2));
|
||||
|
||||
@@ -2,7 +2,7 @@ import React, { useState, useCallback, memo, useEffect } from 'react';
|
||||
import { View, Text, StyleSheet, FlatList, RefreshControl, ActivityIndicator } from 'react-native';
|
||||
import { useNavigation } from '@react-navigation/native';
|
||||
import moment from 'moment';
|
||||
import { useFetchPurchaseTender } from '../../Services/BBPS/Hooks';
|
||||
import { useFetchPurchaseTender } from '../../Services/ApiCall/Hooks';
|
||||
import PurchaseTenderTile from './PurchaseTenderTile';
|
||||
import { useDispatch } from 'react-redux';
|
||||
import { setTender } from '../../Redux/Slices/SelectedTender';
|
||||
|
||||
@@ -19,7 +19,6 @@ const PurchaseTenderList = () => {
|
||||
};
|
||||
|
||||
useEffect(()=>{
|
||||
console.log("dcj",SelectedPurchaseList)
|
||||
if(SelectedPurchaseList.length === 0){
|
||||
Navigation.goBack()
|
||||
}
|
||||
@@ -36,7 +35,6 @@ const PurchaseTenderList = () => {
|
||||
{/* Cards */}
|
||||
{SelectedPurchaseList.map((item: any, index: any) => {
|
||||
const expanded = expandedIndex === index;
|
||||
console.log("item gvsdvgfsv h ca : ", item)
|
||||
return (
|
||||
<Animated.View
|
||||
key={item.auctionId}
|
||||
|
||||
@@ -4,7 +4,7 @@ import Animated, { FadeInUp, useAnimatedStyle, useSharedValue, withTiming } from
|
||||
import moment from 'moment';
|
||||
import CountdownTimer from '../../Component/Counter/CountdownTimer';
|
||||
import colors from '../../Constant/Color';
|
||||
import { useFetchTenderById } from '../../Services/BBPS/Hooks';
|
||||
import { useFetchTenderById } from '../../Services/ApiCall/Hooks';
|
||||
import { useNavigation } from '@react-navigation/native';
|
||||
import TenderFullDetail from './Modal/TenderFullDetail';
|
||||
|
||||
@@ -12,7 +12,6 @@ const PurchaseTenderTile = ({ item, onPressDetails }: any) => {
|
||||
const scale = useSharedValue(1);
|
||||
const elevation = useSharedValue(8);
|
||||
const navigation = useNavigation<any>();
|
||||
console.log("obj000ect",item)
|
||||
const animatedStyle = useAnimatedStyle(() => ({
|
||||
transform: [{ scale: scale.value }],
|
||||
elevation: elevation.value,
|
||||
|
||||
@@ -11,7 +11,7 @@ import { InsideHeader } from '../../Component/Index';
|
||||
import {
|
||||
useFetchLiveTender,
|
||||
useFetchPurchaseTender,
|
||||
} from '../../Services/BBPS/Hooks';
|
||||
} from '../../Services/ApiCall/Hooks';
|
||||
import colors from '../../Constant/Color';
|
||||
import { ShoppingCart, Lock } from 'lucide-react-native';
|
||||
import { useNavigation } from '@react-navigation/native';
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user