How to avoid query inside loop in laravel - php

I have created a simple profit and loss calculation based on FIFO entry in my database of buy and sell order,
and get the buy orders first then I see the sell orders against them and i get the price difference between them and that my profit but now the problem is I have to get the fresh sell orders for every loop of buy order and my code get stuck when the data is large.
can anyone give me the solution for this?
Code:
//get all buy tx orders
$pnl_logs = BuyOrder::where('status', 0)->OrderBy('created_at', 'asc')->get()->take(50);
if ($pnl_logs->isEmpty())
return Response::json(['code' => 0, 'message' => 'No Record found in buy Order to update']);
foreach ($pnl_logs as $logs) {
//get current buy rate and sell rate from price automation table
$system_buy_rate = PriceAutomation::where('type', 0)->orderBy('updated_at', 'desc')->first();
$system_sell_rate = PriceAutomation::where('type', 1)->orderBy('updated_at', 'desc')->first();
//subtract percentage fees from buy orders
$sell_rate = $this->updateSellRate($logs->vendor_id, $logs->sell_rate, $system_buy_rate->base_rate);
//get all sell tx orders
$sell_orders = SellOrders::where('status', 0)->OrderBy('created_at', 'asc')->get()->take(50);
if ($sell_orders->isEmpty())
return Response::json(['code' => 0, 'message' => 'No Record found in Sell Order to update']);
$sum = 0;
$data = [];
foreach ($sell_orders as $key => $orders) {
$sum += $orders->remaining_amount;
$data[$key]['id'] = $orders->id;
$data[$key]['remaining_amount'] = $orders->remaining_amount;
$data[$key]['sell_rate'] = $orders->sell_rate * $orders->remaining_amount;
$data[$key]['system_sell_rate'] = $system_sell_rate->base_rate * $orders->remaining_amount;
$data[$key]['source'] = $orders->gold_source;
if ($sum >= $logs->gold_amount) {
$status = 0;
$rm_balance = 0;
$avg = 0;
$system_avg = 0;
$buy_rm_amount = $logs->gold_amount;
foreach ($data as $k => $v) {
$buy_rm_amount -= $v['remaining_amount'];
if ($buy_rm_amount > 0) {
//a sell tx order is completely consumed for buy tx order
$avg += $v['sell_rate'];
$system_avg += $v['system_sell_rate'];
$status = 1;
} else {
//if buy order is completely satisfied sell tx order
$rm_balance = $sum - $logs->gold_amount;
$avg += ($v['remaining_amount'] - $rm_balance) * $orders->sell_rate;
$system_avg += ($v['remaining_amount'] - $rm_balance) * $system_sell_rate->base_rate;
if ($rm_balance == 0) {
$status = 1;
} else {
$status = 0;
}
}
//update sell order status
SellOrders::where('id', $v['id'])->update(['status' => $status, 'remaining_amount' => $rm_balance, 'system_sell_rate' => $system_sell_rate->base_rate]);
//entry in pnl log
$pnlLogData = [
'tx_id' => $logs->tx_id,
'buy_order_amount' => $logs->gold_amount,
'sell_order_amount' => $v['remaining_amount'] - $rm_balance,
'gold_source' => $v['source']
];
PnlLog::create($pnlLogData);
}
$logs->system_sell_rate = ($logs->system_sell_rate == 0) ? $sell_rate['system_rate'] : $logs->system_sell_rate;
$logs->system_buy_rate = $system_avg;
$logs->buy_rate = $avg;
$logs->sell_rate = $sell_rate['rate'];
$logs->status = 1;
$logs->save();
break;
}

Related

PHP fake average rating generator

Let's imagine that the material has a rating of 2.7 with 7 votes.
I want to create a script that would generate my desired rating that would look real and not fake.
For example, I want the rating to change from 2.7 to 4.6, but the number of votes should also change proportionally.
I can't figure out how to implement it correctly.
My script will make the rating 6.0 as I want, but as a result the number of votes will be as high as 500+. I want to refine the script so that it is more realistic and changes the rating with minimal votes
My code:
My script will make the rating 6.0 as I want for example, but the number of votes will be as high as 500+. I want to generate the average values of the rating based on the previous values, while the deviation in the votes should not look fake.
<?php
class RatingFaker
{
private $totalRating = 10; // Maximum rating threshold (5 or 10)
private $maxRatingGenerate = 10; // We generate maximum rating values during the passage
private $minRatingGenerarate = 5; // Minimally generates a rating value during a pass
private $minRatingCheck = 3.5; // The minimum acceptable threshold from which we start to act
public function __construct($minRatingCheck)
{
$this->minRatingCheck = $minRatingCheck;
}
private function calcAverageRating($ratings = [])
{
$totalWeight = 0;
$totalReviews = 0;
foreach ($ratings as $weight => $numberofReviews) {
$WeightMultipliedByNumber = $weight * $numberofReviews;
$totalWeight += $WeightMultipliedByNumber;
$totalReviews += $numberofReviews;
}
//divide the total weight by total number of reviews
$averageRating = $totalWeight / $totalReviews;
return [
'rating' => $averageRating,
'vote_num' => $totalReviews
];
}
private function getRandVoters()
{
$randRating = rand($this->minRatingGenerarate, $this->maxRatingGenerate);
$randVoters = rand(1, 99);
return [
$randRating => $randVoters
];
}
private function ratingLoop($valueList)
{
$valueList = array_merge($valueList, $this->getRandVoters());
$newRating = $this->calcAverageRating($valueList);
if($newRating['rating'] < $this->minRatingCheck) {
$valueList = array_merge($valueList, $this->getRandVoters());
return $this->ratingLoop($valueList);
}
if($newRating['rating'] > 10) {
$newRating['rating'] = 10;
}
return [
'rating' => round($newRating['rating'], 1),
'sum' => round($newRating['vote_num'] * round($newRating['rating'], 1)),
'voters' => $newRating['vote_num']
];
}
public function check($currentRate, $currentVoteNum)
{
if($currentRate < $this->minRatingCheck) {
$rating = $this->ratingLoop([
$currentRate => $currentVoteNum,
]);
}
return $rating ?? [];
}
}
$currentRate = 2.4;
$voteNum = 88;
$oldRating = [
'rating' => $currentRate,
'sum' => round($voteNum * $currentRate),
'voters' => $voteNum
];
$rating = [];
$ratingFaker = new RatingFaker(6.0);
$rating = $ratingFaker->check($currentRate, $voteNum);
echo '<pre>';
echo 'Was:';
print_r($oldRating);
echo "<br>";
echo "<br>";
echo "<br>";
echo 'Now:';
print_r($rating);
echo '</pre>';
When the current rating is 2.5 based on 9 votes, and you want to get a rating of 6.0 with a minimal number of votes, you need to make sure the total value of 10 votes is 60 ( 60/10 = 6.0 ).
The current rating is : ( 2.5*9 / 9 ) = 2.5
With you extra vote it is: ( (2.5*9+x) / 10 ) = 6.0
Now you only have to find the correct value for x, which is 37.5

Woocommerce - Implementation of query args in the reviews counting graph only for the currently selected language

I have a code that displays reviews graph of the entire website and divides them into sections according to ratings. The problem is that this code calculates the total reviews of the whole website. I would need to filter the total reviews count according to the currently chosen language. I use WPML. Any advice?
Code:
function display_all_product_review_histogram($minimum_rating, $maximum_rating){
$all_product_review_average_rating = get_all_product_review_average_rating($minimum_rating, $maximum_rating);
$total_ratings = $all_product_review_average_rating[0]["total_ratings"];
$get_all_product_review_counts_by_ratings = get_all_product_review_counts_by_ratings($minimum_rating, $maximum_rating);
if($get_all_product_review_counts_by_ratings){
$output = '';
$sum = 0;
$total = 0;
$raw_percentages_array = array();
$percentages_array = array();
//When working with rounded percentages, we must make sure the total percentages add up to 100%.
//Creating array of rating values and its percentage
foreach ($get_all_product_review_counts_by_ratings as $key => $rating) {
$percentage = round($rating["amount"] / $total_ratings, 2) * 100;
$raw_percentages_array[] = array("value" => $rating["value"], "percent_of_total" => $percentage, 'amount'=> $rating["amount"]);
}
//Counting the total of our percents
foreach($raw_percentages_array as $key => $percent) {
$total += $percent[ "percent_of_total" ];
}
//Creating an array that will have the actual percentages after the rounding has been applied to it.
//This will help to see if we have 100% or we are not aligned
foreach($raw_percentages_array as $key => $percent){
$percentages_array[$percent["value"]] = round(($percent["percent_of_total"]/$total) * 100, 0);
}
$sum = array_sum($percentages_array); //Again counting the total of our new percents to see if it adds up to 100%
if($sum != 100){ //If we do not have 100%, then we will alter the highest percentage value so that we get a total of 100%
$highest_percentage_key = array_keys($percentages_array, max($percentages_array)); //Getting key of the highest percentage value
$percentages_array[$highest_percentage_key[0]] = 100 - ($sum - max($percentages_array)); //Alterning the percentage
}
//Now we are ready to create the output that will give us 100% in total
$r_count = 0;
$output .= "<div class='product-review-histogram'>";
foreach ($percentages_array as $key => $percentage) {
$output .= "<div class='histogram-row star-rating-". $key ."'>";
$output .= "<div class='histogram-col-1'>". $key ." star</div>";
$output .= "<div class='histogram-col-2'><div class='histogram-meter-bar'><div class='histogram-bar-temperature' style='width: ". $percentage ."%'></div></div></div>";
$output .= "<div class='histogram-col-3'>". $raw_percentages_array[$r_count]['amount'] ."</div>";
$output .= "</div>";
$r_count++;
}
$output .= "</div>";
return $output;
}else{
return;
}
}
UPDATE - sharing code of get_all_product_review_average_rating function:
function get_all_product_review_average_rating($minimum_rating, $maximum_rating){
$get_all_product_review_counts_by_ratings = get_all_product_review_counts_by_ratings($minimum_rating, $maximum_rating);
if($get_all_product_review_counts_by_ratings){ //If we have reviews
$average_rating_results = array();
$total_ratings = 0;
$total_rating_value = 0;
foreach ($get_all_product_review_counts_by_ratings as $key => $rating) {
$total_ratings = $total_ratings + $rating["amount"];
$current_rating_value = $rating["amount"] * $rating["value"];
$total_rating_value = $total_rating_value + $current_rating_value;
}
$average_rating = number_format($total_rating_value / $total_ratings, 1); //Rounding value to one decimal place
$average_rating_results[] = array(
"total_ratings" => $total_ratings,
"average_rating" => $average_rating
);
return $average_rating_results;
}else{
return;
}
}
UPDATE2 - sharing more of the functions related to the graph
function get_all_product_review_ratings(){
global $wpdb;
if ( false === ( $review_ratings = get_transient( 'all_product_review_ratings' ))){ //Checking if we have previously cached query results in order to save resources and increase speed
$review_ratings = $wpdb->get_results("
SELECT meta_value
FROM {$wpdb->prefix}commentmeta as commentmeta
JOIN {$wpdb->prefix}comments as comments ON comments.comment_id = commentmeta.comment_id
WHERE commentmeta.meta_key = 'rating' AND comments.comment_approved = 1
ORDER BY commentmeta.meta_value
", ARRAY_A);
$expiration = 60 * 5; //Expiring query results after 5 minutes
set_transient( 'all_product_review_ratings', $review_ratings, $expiration ); //Temporarily storing cached data in the database by giving it a custom name and a timeframe after which it will expire and be deleted
return $review_ratings;
}else{
return $review_ratings;
}
}
WHAT DO WE NEED TO CHANGE TO GET THIS IS PROBABLY THIS PART OF THE CODE:
$review_ratings = $wpdb->get_results("
SELECT meta_value
FROM {$wpdb->prefix}commentmeta as commentmeta
JOIN {$wpdb->prefix}comments as comments ON comments.comment_id = commentmeta.comment_id
WHERE commentmeta.meta_key = 'rating' AND comments.comment_approved = 1
ORDER BY commentmeta.meta_value
", ARRAY_A);
UPDATE 3:
function get_all_product_review_counts_by_ratings($minimum_rating, $maximum_rating){
$all_product_review_ratings = get_all_product_review_ratings();
if($all_product_review_ratings){ //If we have reviews
$all_product_review_ratings_one_dimensional_array = array_map("current", $all_product_review_ratings); //Converting two dimensional array to one dimensional array
$rating_counts = array_count_values($all_product_review_ratings_one_dimensional_array); //Creating array that consists of rating counts
$ratings = array();
while($maximum_rating >= $minimum_rating){
if(array_key_exists($maximum_rating, $rating_counts)){
$star_count = $rating_counts[$maximum_rating];
}else{
$star_count = 0;
}
//Creating array that contains information about
$ratings[] = array(
"value" => $maximum_rating,
"amount" => $star_count
);
$maximum_rating--;
}
return $ratings;
}else{
return;
}
}
function get_all_product_review_ratings() {
global $wpdb;
if (false === ( $review_ratings = get_transient('all_product_review_ratings'))) { //Checking if we have previously cached query results in order to save resources and increase speed
$review_ratings = array();
$args = array(
'status' => 'approve',
'type' => 'review',
'paged' => 0,
'meta_query' => array(
array(
'key' => 'verified',
'value' => 1
)
));
// The Query for getting reviews - WPML respected
$comments_query = new WP_Comment_Query;
$comments = $comments_query->query($args);
foreach ($comments as $comment) {
$review_ratings[] = get_comment_meta($comment->comment_ID, 'rating', 1);
}
$expiration = 60 * 5; //Expiring query results after 5 minutes
set_transient('all_product_review_ratings', $review_ratings, $expiration); //Temporarily storing cached data in the database by giving it a custom name and a timeframe after which it will expire and be deleted
return $review_ratings;
} else {
return $review_ratings;
}
}

How to save multiple products details in one row in the database?(laravel)

I'm new to the laravel community but have to make a quick fix for my eCommerce website,
Currently, I have an OrderController that saves information to the database after Checking out,
The problem is, The Current Controller saves multiple products purchase at one time in multiple
new Order Columns in the Database I have been trying to fix on my own for a couple of days now without fully learning laravel as my website is live and I can't spend time learning Laravel.
This is The Code Block That fetches & saves Order details in the Controller:
public function store(Request $request)
{
$carts = Cart::where('user_id', Auth::user()->id)
->get();
if ($carts->isEmpty()) {
flash(translate('Your cart is empty'))->warning();
return redirect()->route('home');
}
$shipping_info = Address::where('id', $carts[0]['address_id'])->first();
$shipping_info->name = Auth::user()->name;
$shipping_info->email = Auth::user()->email;
if ($shipping_info->latitude || $shipping_info->longitude) {
$shipping_info->lat_lang = $shipping_info->latitude . ',' . $shipping_info->longitude;
}
$seller_products = array();
foreach ($carts as $cartItem){
$product_ids = array();
$product = Product::find($cartItem['product_id']);
if(isset($seller_products[$product->user_id])){
$product_ids = $seller_products[$product->user_id];
}
array_push($product_ids, $cartItem);
$seller_products[$product->user_id] = $product_ids;
}
//Order Details Storing
foreach ($seller_products as $cartItem) {
$product = Product::find($cartItem['product_id']);
$subtotal += $cartItem['price'] * $cartItem['quantity'];
$tax += $cartItem['tax'] * $cartItem['quantity'];
$coupon_discount += $cartItem['discount'];
$product_variation = $cartItem['variation'];
$product_stock = $product->stocks->where('variant', $product_variation)->first();
if ($product->digital != 1 && $cartItem['quantity'] > $product_stock->qty) {
flash(translate('The requested quantity is not available for ') . $product->getTranslation('name'))->warning();
$order->delete();
return redirect()->route('cart')->send();
} elseif ($product->digital != 1) {
$product_stock->qty -= $cartItem['quantity'];
$product_stock->save();
}
}
$order_detail = new OrderDetail;
$order_detail->order_id = $order->id;
$order_detail->seller_id = "$seller_products";
$order_detail->product_id = $product->id;
$order_detail->variation = $product_variation;
$order_detail->price = $cartItem['price'] * $cartItem['quantity'];
$order_detail->tax = $cartItem['tax'] * $cartItem['quantity'];
$order_detail->shipping_type = $cartItem['shipping_type'];
$order_detail->product_referral_code = $cartItem['product_referral_code'];
$order_detail->shipping_cost = $cartItem['shipping_cost'];
$shipping += $order_detail->shipping_cost;
if ($cartItem['shipping_type'] == 'pickup_point') {
$order_detail->pickup_point_id = $cartItem['pickup_point'];
}
//End of storing shipping cost
$order_detail->quantity = $cartItem['quantity'];
$order_detail->save();

How to Update in existing quantity in amazon seller using amazon marketplace web service

How to Update in existing quantity in amazon seller using amazon marketplace web service.when update product then old quantity remove and new quantity add.but I want existing quantity Update. For ex. old Quantity 5 then update 10 more Quantity then total quantity 5+10 = 15.
My Code.
require_once 'vendor/autoload.php';
if ($client->validateCredentials()) {
$product = new MCS\MWSProduct();
$product->sku = $request['ItemSKU'];
$product->price = $request['SalePrice'];
$product->quantity = $request['Qty'];
$product->product_id = $request['ASINNo'];;
$product->product_id_type = $request['ProductType'];;
$product->condition_type = $request['ConditionType'];;
$product->title = $request['Title'];;
$product->sale_price = $request['SalePrice'];
//print_r($product);
if ($product->validate()) {
$result = $client->postProduct($product);
if($result){
$arr['status'] = TRUE;
$arr['submitid'] = $result['FeedSubmissionId'];
$info = $client->GetFeedSubmissionResult($result['FeedSubmissionId']);
}
}
2 . One another code :
$client = new MCS\MWSClient([
'Marketplace_Id' => $Amazon_MarketPlaceId,
'Seller_Id' => $Amazon_SellerId,
'Access_Key_ID' => $Amazon_AWSAccessKeyId,
'Secret_Access_Key' => $Amazon_SecretKey,
'MWSAuthToken' => $Amazon_MWSAuthToken
]);
if ($client->validateCredentials()) {
foreach($request as $key => $value){
$SKU_Prices[$key] = $value;
}
if(!empty($SKU_Prices)){
$result = $client->updatePrice($SKU_Prices);
if($result){
$arr['status'] = TRUE;
$arr['submitid'] = $result['FeedSubmissionId'];
}else{
$arr['status'] = FALSE;
$arr['submitid'] = 0;
}
}
}
Please let me know how to Update.

Adjust Array Value in Shopping Cart based on User login state

How would I adjust individual values within the $_SESSION array depending on whether the user is logged_in or not logged_in. So basically the array values equate to the individual item prices within the shopping cart and will be adjusted if the user logs in or logs out of the SESSION.
Here's my current code:
PHP
if(!empty($_SESSION)){
foreach($_SESSION['basket'] as $b){
if ($session->logged_in) { $b['itemprice'] = ""; }
$sub_total = $b['itemprice'] * $b['itemqty'];
$total = $total + $sub_total;
// display contents of shopping cart
}
}
elseif (empty($_SESSION)) { ?>
// display message informing the user that their cart is empty
MYSQL
$itemids = array();
foreach ($_SESSION['basket'] as $item) {
$itemids[] = "'" . $item['itemid'] . "'";
}
$itemids_str = implode(',', $itemids);
$query = mysql_query("SELECT product_id, price, price_100 FROM product WHERE product_id IN ($itemids_str)");
while ($result=mysql_fetch_array($query)) { }
The closest I've come to getting this to work is each product in the cart is given the same price which changes if the user logs in or out. However, I need each item to change to the new price specific to that items product ID.
Some of our members receive a discount on certain items, so once the user logs in from being a GUEST to the registered USER the price needs to be changed on page refresh.
An example being :
**Logged in == FALSE**
Item 1 Price: 100.00
Item 2 Price: 100.00
**User logs in (Logged in == TRUE)**
Item 1 Price: 85.00
Item 2 Price: 94.00
I hope I've been clear - any advice would be appreciated.
Thanks
OPTION A:
function updateCartPrices()
{
$itemids = array();
foreach ($_SESSION['basket'] as $item) {
$itemids[] = "'" . $item['itemid'] . "'";
}
$itemids_str = implode(',', $itemids);
$query = mysql_query("SELECT product_id, price, price_100 FROM product WHERE product_id IN ($itemids_str)");
while ($result=mysql_fetch_array($query)) {
foreach ($_SESSION['basket'] as $key => $item)
{
if($result['product_id'] == $item['itemid'])
{
$_SESSION['basket'][$key]['itemprice'] = ($_SESSION['logged_in']) ? $result['price'] : $result['price_100'];
}
}
}
}
if(!empty($_SESSION)){
updateCartPrices();
foreach($_SESSION['basket'] as $b){
$sub_total = $b['itemprice'] * $b['itemqty'];
$total = $total + $sub_total;
// display contents of shopping cart
}
}
elseif (empty($_SESSION)) { ?>
// display message informing the user that their cart is empty
OPTION B (performance better):
function getLoggedInPrices()
{
$itemids = array();
foreach ($_SESSION['basket'] as $item) {
$itemids[] = "'" . $item['itemid'] . "'";
}
$itemids_str = implode(',', $itemids);
$query = mysql_query("SELECT product_id, price, price_100 FROM product WHERE product_id IN ($itemids_str)");
$prices = array();
while ($result=mysql_fetch_array($query)) {
$prices[$result['product_id']] = $result['price'];
}
return $prices;
}
if(!empty($_SESSION)){
$loggedInPrices = getLoggedInPrices();
foreach($_SESSION['basket'] as $b){
if($_SESSION['logged_in'])
{
$b['itemprice'] = $loggedInPrices[$b['itemid']];
}
$sub_total = $b['itemprice'] * $b['itemqty'];
$total = $total + $sub_total;
// display contents of shopping cart
}
}
elseif (empty($_SESSION)) {

Categories