Payfast.component.ts - before create payment
Sat Jul 27 2024 18:12:32 GMT+0000 (Coordinated Universal Time)
Saved by @iamkatmakhafola
//ts
import { HttpClient } from '@angular/common/http';
import { Component, OnInit } from '@angular/core';
import { FormBuilder } from '@angular/forms';
import { Router } from '@angular/router';
import { Md5 } from 'ts-md5';
import { environment } from '../../environments/environment';
import { OrderService } from '../Services/order.service';
import { MatSnackBar } from '@angular/material/snack-bar';
import { UserService } from '../Services/userprofile.service';
import { CartItemViewModel, OrderViewModel } from '../shared/order';
declare global {
interface Window {
payfast_do_onsite_payment: (param1: any, callback: any) => any;
}
}
@Component({
selector: 'app-payfast',
standalone: true,
imports: [],
templateUrl: './payfast.component.html',
styleUrl: './payfast.component.css'
})
export class PayfastComponent implements OnInit {
memberId!: number;
constructor(private router : Router, private orderService : OrderService, private userService: UserService, private formBuilder: FormBuilder, private snackBar: MatSnackBar) {
}
ngOnInit(): void {
this.fetchMemberId();
}
getSignature(data : Map<string, string>) : string {
let tmp = new URLSearchParams();
data.forEach((v, k)=> {
tmp.append(k, v)
});
let queryString = tmp.toString();
let sig = Md5.hashStr(queryString);
return sig;
}
async doOnSitePayment() {
await this.fetchMemberId();
let onSiteUserData = new Map<string, string>();
onSiteUserData.set("merchant_id", "10033427")
onSiteUserData.set("merchant_key", "mu83ipbgas9p7")
onSiteUserData.set('return_url', window.location.origin + '/payment-success')
onSiteUserData.set('cancel_url', window.location.origin + '/payment-cancel')
// Gather required user data from orderService or other sources
const userData = this.orderService.getUserData();
onSiteUserData.set("email_address", userData.email);
// Set amount and item_name
this.orderService.getTotalAmount().subscribe(amount => {
onSiteUserData.set('amount', amount.toString());
onSiteUserData.set('item_name', 'Cart Purchase');
// Optional passphrase for added security
onSiteUserData.set('passphrase', 'HelloWorldHello'); // Use if you have a passphrase
let signature = this.getSignature(onSiteUserData);
onSiteUserData.set('signature', signature);
let formData = new FormData();
onSiteUserData.forEach((val, key) => {
formData.append(key, val);
});
fetch(environment.payfastOnsiteEndpoint, {
method: 'POST',
body: formData,
redirect: 'follow'
})
.then(response => response.json())
.then(respJson => {
let uuid = respJson['uuid'];
window.payfast_do_onsite_payment({ 'uuid': uuid }, (res: any) => {
if (res == true) {
this.createOrder();
this.snackBar.open('Payment Successful', 'Close', { duration: 5000 });
} else {
this.snackBar.open('Payment Failed', 'Close', { duration: 5000 });
}
});
})
.catch(error => {
console.error('Error processing payment:', error);
this.router.navigate(['/cancel']);
});
});
}
//order
private fetchMemberId() {
const user = localStorage.getItem('User');
if (user) {
const userData = JSON.parse(user);
this.memberId = userData.userId;
// Optional: Fetch and validate member details if needed
this.userService.getMemberByUserId(this.memberId).subscribe({
next: (member) => {
if (member && member.member_ID) {
this.memberId = member.member_ID;
console.log('Member ID:', this.memberId); // Check if this logs the correct ID
} else {
console.error('Member ID is undefined in the response');
this.snackBar.open('Failed to retrieve member information', 'Close', { duration: 5000 });
}
},
error: (error) => {
console.error('Error fetching member:', error);
this.snackBar.open('Failed to retrieve member information', 'Close', { duration: 5000 });
}
});
} else {
this.snackBar.open('User not logged in', 'Close', { duration: 5000 });
this.router.navigate(['/login']);
}
}
private createOrder() {
if (this.memberId === undefined) {
this.snackBar.open('Member ID is not available', 'Close', { duration: 5000 });
return;
}
this.orderService.getCartItems().subscribe(cartItems => {
const order = this.prepareOrderDetails(cartItems);
this.orderService.createOrder(order ).subscribe({
next: (orderResponse) => {
this.snackBar.open('Order Created Successfully', 'Close', { duration: 5000 });
this.router.navigate(['/orders']);
console.log("Order Creation Successful: ", orderResponse)
},
error: (error) => {
console.error('Error creating order:', error);
this.snackBar.open('Failed to create order', 'Close', { duration: 5000 });
this.router.navigate(['/cart']);
}
});
});
}
private prepareOrderDetails(cartItems: CartItemViewModel[]): OrderViewModel {
const order: OrderViewModel = {
order_ID: 0, // ID will be generated by backend
member_ID: this.memberId,
order_Date: new Date().toISOString(),
total_Price: this.calculateTotalPrice(cartItems),
order_Status_ID: 1, // Ready for Collection
isCollected: false,
orderLines: cartItems.map(item => ({
order_Line_ID: 0, // ID will be generated by backend
product_ID: item.product_ID,
product_Name: item.product_Name,
quantity: item.quantity,
unit_Price: item.unit_Price
}))
};
console.log('Prepared order details:', order);
return order;
}
// Helper method to calculate the total price
private calculateTotalPrice(cartItems: CartItemViewModel[]): number {
return cartItems.reduce((total, item) => total + (item.unit_Price * item.quantity), 0);
}
}



Comments