Productsellsreport Documentation

Product Sales Report Controller Documentation

File: /controllers/productsellsreportController.php

Purpose: Generates comprehensive product sales reports with profit analysis, quantity tracking, and category-based filtering

Last Updated: December 20, 2024

Total Functions: 25+

Lines of Code: ~2,020

---

๐Ÿ“‹ Overview

The Product Sales Report Controller is a specialized reporting module that provides detailed product sales analysis and profit tracking capabilities. It handles:

Primary Functions

Related Controllers

---

๐Ÿ—„๏ธ Database Tables

Primary Product Tables

Table NamePurposeKey Columns
**product**Product master dataproductid, productname, productcatid, productbuyprice, productsellprice, productquantity
**productcat**Product categoriesproductcatid, productcatname, productcatparent
**productunit**Product unit measurementsproductunitid, productunitname, productnumber
### Sales Transaction Tables

Table NamePurposeKey Columns
**sellbilldetail**Sales bill line itemssellbilldetailid, sellbillid, sellbilldetailproductid, sellbilldetailquantity, sellbilldetailtotalprice, discountvalue
**sellbill**Sales bills headersellbillid, sellbillclientid, sellbilltotalbill, sellbilldiscount, sellbilldiscounttype, conditions
**returnsellbilldetail**Return bill line itemsreturnsellbilldetailid, returnsellbillid, returnsellbilldetailproductid, returnsellbilldetailquantity
**returnsellbill**Return bills headerreturnsellbillid, returnsellbillclientid, returnsellbilltotalbill
**sellandruternbilldetail**Combined bill detailssellandruternbilldetailid, sellbillid, sellbilldetailproductid, selltype
**sellbillandrutern**Combined sell & returnsellbillid, sellbillprice, returnsellbillprice, sellbilldate
### Service Bills Tables

Table NamePurposeKey Columns
**bills**Service bills headerbillid, clientid, billdate, netbillvalue, discountvalue
**billsproducts**Service bill line itemsbillsproductid, billid, productid, productno, productprice, productBuyPrice
**billsreturnproducts**Service bill returnsbillsreturnproductid, billid, productid, productno
### Reference Tables

Table NamePurposeKey Columns
**programsettings**System configurationprogramsettingsid, profitevaluation, reportsplushhours
**youtubelink**Tutorial linksyoutubelinkid, title, url
**usergroup**User group permissionsusergroupid, usergroupname
---

๐Ÿ”‘ Key Functions

1. show() / Default Action - Main Product Sales Report

Location: Line 154

Purpose: Generate comprehensive product sales report filtered by category and date range

Function Signature:

// Triggered when: do=show or empty $do
$startDate = $_REQUEST['from'];
$endDate = $_REQUEST['to'];
$productCatId = $_REQUEST['productCatId'];

Process Flow:

1. Load product categories for dropdown selection

2. Parse and validate date parameters (defaults to current date)

3. Apply time zone adjustments from program settings

4. Route to appropriate report function based on parameters:

- loadProductByProductcatIdAndDate() - Specific category with date range

- loadProductByAllCategoriesAndDate() - All categories with date range

- loadProductByProductcatId() - Specific category without date filter

- loadProductByAllCategories() - All categories without date filter

5. Display via productsellsreportview/show.html template

Filter Combinations:

---

2. loadProductByProductcatIdAndDate() - Category-Specific Date Report

Location: Line 1446

Purpose: Generate detailed sales report for products in specific category within date range

Function Signature:

function loadProductByProductcatIdAndDate($productcatId, $startDate, $endDate)

Process Flow:

1. Query products by category: queryByProductCatIdEX($productcatId)

2. For each product in category:

- Calculate sales quantities: showSellByProductAndDate()

- Calculate additional sales: showAditionalSellByProductAndDate()

- Calculate return quantities: showReturnSellByProductAndDate()

- Calculate net remaining quantity (sells - returns)

- Get profit/price data: getProductInBillByDateAndProductId()

- Process service bill data if applicable

3. Build category hierarchy path for display

4. Calculate running totals across all products

5. Assign individual product data to template variables

Key Calculations:

---

3. loadProductByAllCategoriesAndDate() - All Categories Date Report

Location: Line 1767

Purpose: Generate sales report for all product categories within date range

Function Signature:

function loadProductByAllCategoriesAndDate($startDate, $endDate)

Process Flow:

1. Query all products: queryByAllCategories()

2. Apply same detailed analysis as category-specific report

3. Process each product through full calculation pipeline

4. Generate comprehensive totals across entire product catalog

5. Group results by category for organized display

Performance Considerations:

---

4. getProductInBillByDateAndProductId() - Comprehensive Product Analysis

Location: Line 1191

Purpose: Calculate detailed profit, pricing, and quantity data for a specific product

Function Signature:

function getProductInBillByDateAndProductId($startDate, $endDate, $productId)

Process Flow:

1. Regular Sales: getTotalSellPriceByDateAndProductId()

2. Additional Sales: getTotalAditionalSellPriceByDateAndProductId()

3. Returns: getTotalReturnSellPriceByDateAndProductId()

4. Additional Returns: getTotalAditionalReturnSellPriceByDateAndProductId()

5. Buy Price Analysis: getTotalBuyPriceByDateAndProductId()

6. Additional Buy Data: getTotalAditionalBuyPriceByDateAndProductId()

7. Return Buy Data: getTotalReturnBuyPriceByDateAndProductId()

Returns Array:

return array(
    $finalProfit,           // [0] Net profit amount
    $finalSellPrice,        // [1] Total sell price after discounts
    $finalBuyPrice,         // [2] Total buy price
    $totalsell_withoutdiscount, // [3] Sell price before discounts
    $finalQuantity,         // [4] Net quantity (sells - returns)
    $finalSellQuantity,     // [5] Total sell quantity
    $finalReturnQuantity,   // [6] Total return quantity
    $finalBuyQuantity       // [7] Total buy quantity
);

---

5. getTotalSellPriceByDateAndProductId() - Regular Sales Analysis

Location: Line 557

Purpose: Calculate sales totals, profit, and quantities for regular sell bills

Function Signature:

function getTotalSellPriceByDateAndProductId($startDate, $endDate, $ProductIdselected)

Process Flow:

1. Query sell bill details: queryWithDateAndConditionsAndProductIdExt()

2. For each line item:

- Apply profit evaluation method from settings

- Calculate quantity in base units using unit conversions

- Process line-level discounts

- Calculate bill-level discount proportion

- Compute final sell price and profit

3. Aggregate totals across all bills

Profit Evaluation Methods:

switch ($Programsetting->Profitevaluation) {
    case "first": $buyprice = $sellbilldetail->buyprice; break;
    case "last": $buyprice = $sellbilldetail->lastbuyprice; break;
    case "mean": $buyprice = $sellbilldetail->meanbuyprice; break;
    case "last_discount": $buyprice = $sellbilldetail->lastbuyprice_withDiscount; break;
    case "mean_discount": $buyprice = $sellbilldetail->meanbuyprice_withDiscount; break;
    case "generalPrice": $buyprice = $sellbilldetail->generalPrice; break;
}

Discount Processing:

// Line-level discount
$discountValue = $sellbilldetail->discountvalue;

// Bill-level discount calculation
if ($sellbillDiscountType == 2) { // Percentage
    $sellbillDiscount = ($sellbillDiscount / 100) * $sellbillTotalBill;
}
// Proportional bill discount for this line
$billDiscountPortion = ($totalPrice / $sellbillTotalBill) * $sellbillDiscount;

// Final sell price after all discounts
$sellPriceForOneProduct = $totalPriceBeforeDiscount - ($discountValue + $billDiscountPortion);

---

6. getTotalAditionalSellPriceByDateAndProductId() - Combined Bill Sales

Location: Line 640

Purpose: Process sales from combined sell/return bills (selltype = 0)

Function Signature:

function getTotalAditionalSellPriceByDateAndProductId($startDate, $endDate, $ProductIdselected, $overAllAveragePrice)

Process Flow:

1. Query combined bill details with sell type 0

2. Apply same calculation logic as regular sales

3. Handle different discount structure for combined bills

4. Use average price override when configured

Key Differences from Regular Sales:

---

7. showSellByProductAndDate() / showReturnSellByProductAndDate() - Quantity Helpers

Location: Lines 1416, 1431

Purpose: Get simple quantity totals for specific product/date combinations

Function Signatures:

function showSellByProductAndDate($productId, $startDate, $endDate)
function showReturnSellByProductAndDate($productId, $startDate, $endDate)

Returns: Simple quantity totals for quick calculations

---

8. loadProductCat() - Category Data Loader

Location: Line 1991

Purpose: Load product categories that contain products for dropdown population

Function Signature:

function loadProductCat()

Returns: Array of product categories with associated products

---

๐Ÿ”„ Workflows

Workflow 1: Product Category Sales Report Generation

โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
START: Select Category & Date Range
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
1Validate Input Parameters
- Check productCatId (-1=all, specific ID, "all")
- Parse and validate date range
- Apply timezone adjustments
- Set defaults if parameters missing
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
2Route to Appropriate Function
IF category + date range:
โ”‚ โ””โ”€โ†’ loadProductByProductcatIdAndDate() โ”‚
IF all categories + date range:
โ”‚ โ””โ”€โ†’ loadProductByAllCategoriesAndDate() โ”‚
IF category only:
โ”‚ โ””โ”€โ†’ loadProductByProductcatId() โ”‚
IF all categories only:
โ”‚ โ””โ”€โ†’ loadProductByAllCategories() โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
3Load Products by Category
- Query product table by category filter
- Load product master data
- Initialize calculation variables
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
4Process Each Product
FOR EACH product in category:
โ”‚
โ†’ Calculate Sales Quantities
โ”‚ โ”œโ”€ Regular sells: showSellByProductAndDate()
โ”‚ โ”‚ โ””โ”€ Additional sells: showAditionalSellBy...() โ”‚
โ”‚
โ†’ Calculate Return Quantities
โ”‚ โ”œโ”€ Regular returns: showReturnSellBy...()
โ”‚ โ”‚ โ””โ”€ Additional returns: showAditionalReturn...() โ”‚
โ”‚
โ†’ Calculate Net Remaining Quantity
โ”‚ โ”‚ โ””โ”€ Net = Total Sells - Total Returns โ”‚
โ”‚
โ†’ Get Comprehensive Analysis
โ”‚ โ”‚ โ””โ”€ getProductInBillByDateAndProductId() โ”‚
โ”‚ โ”œโ”€ Profit calculations
โ”‚ โ”œโ”€ Price analysis
โ”‚ โ”œโ”€ Discount processing
โ”‚ โ”‚ โ””โ”€ Quantity conversions โ”‚
โ”‚
โ†’ Process Service Bills (if applicable)
โ”‚ โ”œโ”€ Query bills table with date filter
โ”‚ โ”œโ”€ Calculate service bill quantities
โ”‚ โ”œโ”€ Apply discount calculations
โ”‚ โ”‚ โ””โ”€ Add to running totals โ”‚
โ”‚
โ”‚ โ””โ”€โ†’ Build Category Hierarchy Display โ”‚
โ”œโ”€ get_parentCat_of_productCat()
โ”‚ โ””โ”€ get_childCat_of_productCat() โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
5Calculate Report Totals
- Sum all product sells across category
- Sum all profit amounts
- Sum all quantities (net, sells, returns)
- Calculate discount totals
- Build grand totals for display
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
6Generate Report Output
- Assign product data to template variables
- Include individual product metrics
- Add category hierarchy information
- Display via productsellsreportview/show.html
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜

---

Workflow 2: Comprehensive Product Analysis Pipeline

โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
START: getProductInBillByDateAndProductId()
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
1Regular Sales Analysis
โ†’ getTotalSellPriceByDateAndProductId()
โ”‚ โ”œโ”€ Query sellbilldetail table
โ”‚ โ”œโ”€ Apply profit evaluation method
โ”‚ โ”œโ”€ Calculate line-level discounts
โ”‚ โ”œโ”€ Calculate bill-level discount portions
โ”‚ โ”œโ”€ Convert quantities to base units
โ”‚ โ”‚ โ””โ”€ Sum: sellPrice, quantity, buyPrice, grossSell โ”‚
โ”‚
โ”‚ โ””โ”€โ†’ Return: [sellPrice, quantity, buyPrice, grossSell] โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
2Additional Sales Analysis (Combined Bills)
โ†’ getTotalAditionalSellPriceByDateAndProductId()
โ”‚ โ”œโ”€ Query sellandruternbilldetail (selltype=0)
โ”‚ โ”œโ”€ Apply same calculation logic
โ”‚ โ”œโ”€ Handle combined bill discount structure
โ”‚ โ”‚ โ””โ”€ Use average price when configured โ”‚
โ”‚
โ”‚ โ””โ”€โ†’ Return: [addSellPrice, addQuantity, addBuy, ...] โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
3Returns Analysis
โ†’ getTotalReturnSellPriceByDateAndProductId()
โ”‚ โ”œโ”€ Query returnsellbilldetail table
โ”‚ โ”œโ”€ Calculate return quantities and values
โ”‚ โ”‚ โ””โ”€ Apply same discount/profit logic โ”‚
โ”‚
โ†’ getTotalAditionalReturnSellPriceByDateAnd...()
โ”‚ โ”œโ”€ Query sellandruternbilldetail (selltype=1)
โ”‚ โ”‚ โ””โ”€ Process return portions of combined bills โ”‚
โ”‚
โ”‚ โ””โ”€โ†’ Return: [returnPrice, returnQty, returnBuy, ...] โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
4Buy Price Analysis (for profit calculation)
โ†’ getTotalBuyPriceByDateAndProductId()
โ†’ getTotalAditionalBuyPriceByDateAndProductId()
โ†’ getTotalReturnBuyPriceByDateAndProductId()
โ”‚ โ””โ”€โ†’ getTotalAditionalReturnBuyPriceByDateAnd...() โ”‚
โ”‚ โ””โ”€โ†’ Return: Buy price totals for profit calculations โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
โ–ผ
โ–ผ
โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
5Aggregate Final Results
- finalSellPrice = sellPrice + additionalSell
- finalReturnPrice = returnPrice + additionalReturn
- finalBuyPrice = buyPrice + additionalBuy
- finalProfit = (finalSell - finalReturn) - finalBuy
- finalQuantity = (sellQty + addSellQty) -
(returnQty + addReturnQty)
โ”‚ โ””โ”€โ†’ Return comprehensive analysis array โ”‚
โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜

---

๐ŸŒ URL Routes & Actions

URL ParameterFunction CalledDescription
`do=` (empty) or `do=show`Default actionProduct sales report by category/date
`do=showmain`Alternative report viewMain category-based view
### Required Parameters by Action

Product Sales Report (do=show):

Main Category View (do=showmain):

Parameter Processing Logic

// Date defaulting
if (empty($startDate) && empty($endDate)) {
    $startDate = date('Y-m-d');
    $endDate = date('Y-m-d');
}

// Time adjustment from settings
if (isset($Programsetting->reportsPlusHours)) {
    $reportsPlusHours = $Programsetting->reportsPlusHours + 24;
    $endDate = date('Y-m-d H:i:s', strtotime('+' . $reportsPlusHours . ' hour', strtotime($endDate)));
    $startDate = date('Y-m-d H:i:s', strtotime('+' . $Programsetting->reportsPlusHours . ' hour', strtotime($startDate)));
}

---

๐Ÿงฎ Calculation Methods

Profit Evaluation Methods

// Configurable via programsettings.profitevaluation
switch ($Programsetting->Profitevaluation) {
    case "first":         // First purchase price
    case "last":          // Last purchase price  
    case "mean":          // Average purchase price
    case "last_discount": // Last price with discount
    case "mean_discount": // Average price with discount
    case "generalPrice":  // General/override price
}

Discount Processing

// Line-level product discount
$lineDiscount = $sellbilldetail->discountvalue;

// Bill-level discount calculation
if ($sellbillDiscountType == 2) {
    $billDiscount = ($sellbillDiscount / 100) * $sellbillTotalBill; // Percentage
} else {
    $billDiscount = $sellbillDiscount; // Fixed amount
}

// Proportional bill discount for this line item
$proportionalDiscount = ($lineTotal / $billTotal) * $billDiscount;

// Final price after all discounts
$finalPrice = $lineTotalBeforeDiscount - ($lineDiscount + $proportionalDiscount);

Unit Conversion

// Convert sold quantity to base units
$productnumber = $myProductunitEx->getProductNumber($productunitId);
$quantityInBaseUnits = $quantity * $productnumber;

Net Quantity Calculation

// Calculate remaining stock movement
$totalSellQuantity = $regularSells + $additionalSells;
$totalReturnQuantity = $regularReturns + $additionalReturns;
$remainingQuantity = $totalSellQuantity - $totalReturnQuantity;

Service Bills Integration

// Service bill discount calculation
$productTotal = $detail->productprice * $detail->productno;
$billDiscountAmount = $productTotal - $detail->netbillvalue;
$finalSellPrice = $productTotal - $billDiscountAmount;

// Service bill profit
$profit = $finalSellPrice - ($detail->productBuyPrice * $detail->productno);

---

๐Ÿ”’ Security & Permissions

User Authentication

// Required authentication check
include_once("../public/authentication.php");

// Category visibility control
$smarty->assign("hidecat", $_SESSION['hidecat']);

Input Sanitization

Session Management

---

๐Ÿ“Š Performance Considerations

Database Optimization

1. Required Indexes:

- sellbilldetail(sellbilldetailproductid, sellbilldate)

- product(productcatid)

- sellbill(sellbilldate, conditions)

- returnsellbilldetail(returnsellbilldetailproductid, returnsellbilldate)

- bills(billdate)

2. Query Performance:

- Date range filtering applied at database level

- Category filtering reduces result sets

- Conditions filtering excludes cancelled bills

- Unit conversion queries optimized

3. Memory Management:

- Large product catalogs can consume significant memory

- Template variable assignment for thousands of products

- Consider pagination for very large datasets

- Cleanup of intermediate calculation variables

Known Performance Bottlenecks

-- This can be slow for large date ranges with many products
SELECT * FROM sellbilldetail sbd
JOIN sellbill sb ON sbd.sellbillid = sb.sellbillid
WHERE sbd.sellbilldetailproductid = ? 
AND sb.sellbilldate BETWEEN ? AND ?
AND sb.conditions = 0;

-- Solution: Composite index
CREATE INDEX idx_product_date_conditions ON sellbilldetail(sellbilldetailproductid, sellbilldate);

---

๐Ÿ› Common Issues & Troubleshooting

1. Incorrect Profit Calculations

Issue: Profit amounts don't match expected values

Cause: Wrong profit evaluation method or missing buy price data

Debug:

-- Check profit evaluation setting
SELECT settingvalue FROM programsettings WHERE settingkey = 'Profitevaluation';

-- Verify buy price data exists
SELECT productid, buyprice, lastbuyprice, meanbuyprice 
FROM sellbilldetail WHERE sellbilldetailproductid = [ID];

2. Missing Product Data

Issue: Products not appearing in reports despite having sales

Cause: Category associations or date range issues

Fix:

-- Check product category assignment
SELECT p.productname, p.productcatid, pc.productcatname
FROM product p 
LEFT JOIN productcat pc ON p.productcatid = pc.productcatid
WHERE p.productid = [ID];

-- Verify sales exist in date range
SELECT COUNT(*) FROM sellbilldetail sbd
JOIN sellbill sb ON sbd.sellbillid = sb.sellbillid
WHERE sbd.sellbilldetailproductid = [ID]
AND sb.sellbilldate BETWEEN '[START]' AND '[END]';

3. Discount Calculation Issues

Issue: Discount amounts don't match manual calculations

Cause: Mixed discount types or bill-level discount distribution

Debug:

// Enable discount debugging
echo "Line Discount: " . $discountValue . "<br>";
echo "Bill Total: " . $sellbillTotalBill . "<br>";
echo "Bill Discount: " . $sellbillDiscount . " (Type: " . $sellbillDiscountType . ")<br>";
echo "Line Proportion: " . ($totalPrice / $sellbillTotalBill) . "<br>";
echo "Proportional Discount: " . (($totalPrice / $sellbillTotalBill) * $sellbillDiscount) . "<br>";

4. Unit Conversion Problems

Issue: Quantities don't match between reports and actual sales

Cause: Unit conversion factors not properly applied

Fix:

-- Verify unit conversion factors
SELECT pu.productunitname, pu.productnumber
FROM productunit pu
JOIN sellbilldetail sbd ON pu.productunitid = sbd.productunitid
WHERE sbd.sellbilldetailproductid = [ID];

---

๐Ÿงช Testing Scenarios

Test Case 1: Category Report Accuracy

1. Select category with known product sales
2. Set date range covering test transactions
3. Verify quantities match database queries
4. Check profit calculations against manual computation
5. Confirm discount applications are correct

Test Case 2: All Categories Performance

1. Run report for all categories with large date range
2. Monitor memory usage and execution time
3. Verify totals match sum of individual category reports
4. Test with different profit evaluation methods

Test Case 3: Service Bills Integration

1. Create test service bills with products
2. Run product report covering service bill dates
3. Verify service bill amounts included in totals
4. Check profit calculations include service data

Debug Mode Enable

// Add at top of controller for debugging
error_reporting(E_ALL);
ini_set('display_errors', 1);

// Debug product analysis
echo "<pre>";
$debugData = getProductInBillByDateAndProductId($startDate, $endDate, $productId);
print_r($debugData);
echo "</pre>";

// Debug category queries
echo "Product Count: " . count($productData) . "<br>";
foreach($productData as $product) {
    echo "Product: " . $product->productname . " (ID: " . $product->productId . ")<br>";
}

---

๐Ÿ“š Related Documentation

---

Documented By: AI Assistant

Review Status: โœ… Complete

Next Review: When major changes occur