Merge remote-tracking branch 'origin/master'
This commit is contained in:
@@ -1,27 +0,0 @@
|
|||||||
/* Indexes for order validate performance */
|
|
||||||
|
|
||||||
IF NOT EXISTS (
|
|
||||||
SELECT 1
|
|
||||||
FROM sys.indexes
|
|
||||||
WHERE name = 'IX_trOrderLine_OrderHeader_ItemCode'
|
|
||||||
AND object_id = OBJECT_ID('dbo.trOrderLine')
|
|
||||||
)
|
|
||||||
BEGIN
|
|
||||||
CREATE NONCLUSTERED INDEX IX_trOrderLine_OrderHeader_ItemCode
|
|
||||||
ON dbo.trOrderLine (OrderHeaderID, ItemCode)
|
|
||||||
INCLUDE (ItemTypeCode, ColorCode, ItemDim1Code, ItemDim2Code, ItemDim3Code, LineDescription, SortOrder, OrderLineID);
|
|
||||||
END
|
|
||||||
GO
|
|
||||||
|
|
||||||
IF NOT EXISTS (
|
|
||||||
SELECT 1
|
|
||||||
FROM sys.indexes
|
|
||||||
WHERE name = 'IX_prItemVariant_Combo'
|
|
||||||
AND object_id = OBJECT_ID('dbo.prItemVariant')
|
|
||||||
)
|
|
||||||
BEGIN
|
|
||||||
CREATE NONCLUSTERED INDEX IX_prItemVariant_Combo
|
|
||||||
ON dbo.prItemVariant (ItemTypeCode, ItemCode, ColorCode, ItemDim1Code, ItemDim2Code, ItemDim3Code)
|
|
||||||
INCLUDE (PLU);
|
|
||||||
END
|
|
||||||
GO
|
|
||||||
@@ -1,18 +0,0 @@
|
|||||||
USE [BAGGI_V3]
|
|
||||||
GO
|
|
||||||
|
|
||||||
SET ANSI_NULLS ON
|
|
||||||
GO
|
|
||||||
SET QUOTED_IDENTIFIER ON
|
|
||||||
GO
|
|
||||||
|
|
||||||
CREATE OR ALTER PROCEDURE [dbo].[SP_BUILD_STATEMENT_AGING_PIPELINE]
|
|
||||||
AS
|
|
||||||
BEGIN
|
|
||||||
SET NOCOUNT ON;
|
|
||||||
SET XACT_ABORT ON;
|
|
||||||
|
|
||||||
EXEC dbo.SP_BUILD_CARI_VADE_GUN_STAGING;
|
|
||||||
EXEC dbo.SP_BUILD_CARI_BAKIYE_CACHE;
|
|
||||||
END
|
|
||||||
GO
|
|
||||||
@@ -101,15 +101,19 @@ func GetAccounts(ctx context.Context) ([]models.Account, error) {
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(acc.AccountCode) >= 4 {
|
acc.DisplayCode = formatAccountDisplayCode(acc.AccountCode)
|
||||||
acc.DisplayCode =
|
|
||||||
strings.TrimSpace(acc.AccountCode[:3] + " " + acc.AccountCode[3:])
|
|
||||||
} else {
|
|
||||||
acc.DisplayCode = acc.AccountCode
|
|
||||||
}
|
|
||||||
|
|
||||||
accounts = append(accounts, acc)
|
accounts = append(accounts, acc)
|
||||||
}
|
}
|
||||||
|
|
||||||
return accounts, rows.Err()
|
return accounts, rows.Err()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func formatAccountDisplayCode(code string) string {
|
||||||
|
trimmed := strings.TrimSpace(code)
|
||||||
|
runes := []rune(trimmed)
|
||||||
|
if len(runes) <= 3 {
|
||||||
|
return trimmed
|
||||||
|
}
|
||||||
|
return strings.TrimSpace(string(runes[:3]) + " " + string(runes[3:]))
|
||||||
|
}
|
||||||
|
|||||||
@@ -15,15 +15,16 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type mkCariBakiyeLine struct {
|
type mkCariBakiyeLine struct {
|
||||||
CurrAccTypeCode int
|
CurrAccTypeCode int
|
||||||
CariKodu string
|
CariKodu string
|
||||||
CariDoviz string
|
CariDoviz string
|
||||||
SirketKodu int
|
SirketKodu int
|
||||||
PislemTipi string
|
PislemTipi string
|
||||||
YerelBakiye float64
|
ParasalIslemTipi string
|
||||||
Bakiye float64
|
YerelBakiye float64
|
||||||
VadeGun float64
|
Bakiye float64
|
||||||
VadeBelgeGun float64
|
VadeGun float64
|
||||||
|
VadeBelgeGun float64
|
||||||
}
|
}
|
||||||
|
|
||||||
type cariMeta struct {
|
type cariMeta struct {
|
||||||
@@ -181,13 +182,13 @@ func GetCustomerBalanceList(ctx context.Context, params models.CustomerBalanceLi
|
|||||||
}
|
}
|
||||||
|
|
||||||
usd := toUSD(ln.Bakiye, curr, usdTry, rateMap)
|
usd := toUSD(ln.Bakiye, curr, usdTry, rateMap)
|
||||||
|
add12, add13 := resolveBalanceBuckets(ln)
|
||||||
switch strings.TrimSpace(ln.PislemTipi) {
|
if add12 {
|
||||||
case "1_2":
|
|
||||||
row.Bakiye12 += ln.Bakiye
|
row.Bakiye12 += ln.Bakiye
|
||||||
row.TLBakiye12 += ln.YerelBakiye
|
row.TLBakiye12 += ln.YerelBakiye
|
||||||
row.USDBakiye12 += usd
|
row.USDBakiye12 += usd
|
||||||
case "1_3":
|
}
|
||||||
|
if add13 {
|
||||||
row.Bakiye13 += ln.Bakiye
|
row.Bakiye13 += ln.Bakiye
|
||||||
row.TLBakiye13 += ln.YerelBakiye
|
row.TLBakiye13 += ln.YerelBakiye
|
||||||
row.USDBakiye13 += usd
|
row.USDBakiye13 += usd
|
||||||
@@ -319,13 +320,14 @@ func loadBalanceLines(ctx context.Context, selectedDate, cariSearch string) ([]m
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
query := fmt.Sprintf(`
|
queryTemplate := `
|
||||||
SELECT
|
SELECT
|
||||||
CurrAccTypeCode,
|
CurrAccTypeCode,
|
||||||
CariKodu,
|
CariKodu,
|
||||||
CariDoviz,
|
CariDoviz,
|
||||||
SirketKodu,
|
SirketKodu,
|
||||||
PislemTipi,
|
PislemTipi,
|
||||||
|
%s
|
||||||
YerelBakiye,
|
YerelBakiye,
|
||||||
Bakiye,
|
Bakiye,
|
||||||
CAST(0 AS DECIMAL(18,4)) AS Vade_Gun,
|
CAST(0 AS DECIMAL(18,4)) AS Vade_Gun,
|
||||||
@@ -333,13 +335,33 @@ func loadBalanceLines(ctx context.Context, selectedDate, cariSearch string) ([]m
|
|||||||
FROM dbo.MK_CARI_BAKIYE_LIST(@SonTarih)
|
FROM dbo.MK_CARI_BAKIYE_LIST(@SonTarih)
|
||||||
WHERE (@CariSearch = '' OR CariKodu LIKE '%%' + @CariSearch + '%%')
|
WHERE (@CariSearch = '' OR CariKodu LIKE '%%' + @CariSearch + '%%')
|
||||||
AND %s
|
AND %s
|
||||||
`, piyasaScope)
|
`
|
||||||
|
|
||||||
rows, err := db.MssqlDB.QueryContext(ctx, query,
|
selectParasalCandidates := make([]string, 0, 7)
|
||||||
sql.Named("SonTarih", selectedDate),
|
if expr := strings.TrimSpace(resolveParasalIslemSelectExpr(ctx, "SELECT * FROM dbo.MK_CARI_BAKIYE_LIST('2000-01-01')")); expr != "" {
|
||||||
sql.Named("CariSearch", strings.TrimSpace(cariSearch)),
|
selectParasalCandidates = append(selectParasalCandidates, expr)
|
||||||
|
}
|
||||||
|
selectParasalCandidates = append(selectParasalCandidates,
|
||||||
|
"CAST(ATAtt01 AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST(ParasalIslemTipi AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST(ParislemTipi AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST(ParIslemTipi AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST('' AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
)
|
)
|
||||||
if err != nil {
|
|
||||||
|
var rows *sql.Rows
|
||||||
|
for i, sel := range selectParasalCandidates {
|
||||||
|
query := fmt.Sprintf(queryTemplate, sel, piyasaScope)
|
||||||
|
rows, err = db.MssqlDB.QueryContext(ctx, query,
|
||||||
|
sql.Named("SonTarih", selectedDate),
|
||||||
|
sql.Named("CariSearch", strings.TrimSpace(cariSearch)),
|
||||||
|
)
|
||||||
|
if err == nil {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if i < len(selectParasalCandidates)-1 && isInvalidColumnError(err) {
|
||||||
|
continue
|
||||||
|
}
|
||||||
return nil, fmt.Errorf("MK_CARI_BAKIYE_LIST query error: %w", err)
|
return nil, fmt.Errorf("MK_CARI_BAKIYE_LIST query error: %w", err)
|
||||||
}
|
}
|
||||||
defer rows.Close()
|
defer rows.Close()
|
||||||
@@ -353,6 +375,7 @@ func loadBalanceLines(ctx context.Context, selectedDate, cariSearch string) ([]m
|
|||||||
&r.CariDoviz,
|
&r.CariDoviz,
|
||||||
&r.SirketKodu,
|
&r.SirketKodu,
|
||||||
&r.PislemTipi,
|
&r.PislemTipi,
|
||||||
|
&r.ParasalIslemTipi,
|
||||||
&r.YerelBakiye,
|
&r.YerelBakiye,
|
||||||
&r.Bakiye,
|
&r.Bakiye,
|
||||||
&r.VadeGun,
|
&r.VadeGun,
|
||||||
@@ -648,7 +671,7 @@ func buildFilters(params models.CustomerBalanceListParams) balanceFilters {
|
|||||||
piyasa: parseCSVSet(params.Piyasa),
|
piyasa: parseCSVSet(params.Piyasa),
|
||||||
temsilci: parseCSVSet(params.Temsilci),
|
temsilci: parseCSVSet(params.Temsilci),
|
||||||
riskDurumu: parseCSVSet(params.RiskDurumu),
|
riskDurumu: parseCSVSet(params.RiskDurumu),
|
||||||
islemTipi: parseCSVSet(params.IslemTipi),
|
islemTipi: parseIslemTipiSet(params.IslemTipi),
|
||||||
ulke: parseCSVSet(params.Ulke),
|
ulke: parseCSVSet(params.Ulke),
|
||||||
il: parseCSVSet(params.Il),
|
il: parseCSVSet(params.Il),
|
||||||
ilce: parseCSVSet(params.Ilce),
|
ilce: parseCSVSet(params.Ilce),
|
||||||
@@ -707,6 +730,28 @@ func parseCSVSet(v string) map[string]struct{} {
|
|||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func parseIslemTipiSet(v string) map[string]struct{} {
|
||||||
|
raw := parseCSVSet(v)
|
||||||
|
if len(raw) == 0 {
|
||||||
|
return raw
|
||||||
|
}
|
||||||
|
|
||||||
|
out := make(map[string]struct{}, 2)
|
||||||
|
for token := range raw {
|
||||||
|
switch strings.ToLower(strings.TrimSpace(token)) {
|
||||||
|
case "1_2", "prbr_1_2", "usd_1_2", "try_1_2", "tl_1_2", "usd_bakiye_1_2", "tl_bakiye_1_2":
|
||||||
|
out["1_2"] = struct{}{}
|
||||||
|
case "1_3", "prbr_1_3", "usd_1_3", "try_1_3", "tl_1_3", "usd_bakiye_1_3", "tl_bakiye_1_3":
|
||||||
|
out["1_3"] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(out) == 0 {
|
||||||
|
return raw
|
||||||
|
}
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
func getAuthorizedPiyasaCodes(ctx context.Context) ([]string, error) {
|
func getAuthorizedPiyasaCodes(ctx context.Context) ([]string, error) {
|
||||||
claims, ok := auth.GetClaimsFromContext(ctx)
|
claims, ok := auth.GetClaimsFromContext(ctx)
|
||||||
if !ok || claims == nil {
|
if !ok || claims == nil {
|
||||||
@@ -794,3 +839,181 @@ func firstNonEmpty(v ...string) string {
|
|||||||
}
|
}
|
||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func isInvalidColumnError(err error) bool {
|
||||||
|
if err == nil {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
msg := strings.ToLower(err.Error())
|
||||||
|
return strings.Contains(msg, "invalid column name")
|
||||||
|
}
|
||||||
|
|
||||||
|
func shouldSkipBalanceLine(ln mkCariBakiyeLine) bool {
|
||||||
|
add12, add13 := resolveBalanceBuckets(ln)
|
||||||
|
p := strings.TrimSpace(ln.PislemTipi)
|
||||||
|
if p == "1_2" {
|
||||||
|
return !add12
|
||||||
|
}
|
||||||
|
if p == "1_3" {
|
||||||
|
return !add13
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
func resolveBalanceBuckets(ln mkCariBakiyeLine) (add12 bool, add13 bool) {
|
||||||
|
p := strings.TrimSpace(ln.PislemTipi)
|
||||||
|
t := normalizeParasalIslemTipi(ln.ParasalIslemTipi)
|
||||||
|
switch t {
|
||||||
|
case "1":
|
||||||
|
return true, true
|
||||||
|
case "2", "1_2":
|
||||||
|
return true, false
|
||||||
|
case "3", "1_3":
|
||||||
|
return false, true
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parasal tip yoksa eski davranis: PislemTipi'ne gore ayir.
|
||||||
|
if p == "1_2" {
|
||||||
|
return true, false
|
||||||
|
}
|
||||||
|
if p == "1_3" {
|
||||||
|
return false, true
|
||||||
|
}
|
||||||
|
return false, false
|
||||||
|
}
|
||||||
|
|
||||||
|
func normalizeParasalIslemTipi(v string) string {
|
||||||
|
s := strings.TrimSpace(v)
|
||||||
|
if s == "" {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
lower := strings.ToLower(s)
|
||||||
|
compact := strings.ReplaceAll(strings.ReplaceAll(strings.ReplaceAll(lower, " ", ""), "-", "_"), "/", "_")
|
||||||
|
if strings.Contains(compact, "1_2") {
|
||||||
|
return "1_2"
|
||||||
|
}
|
||||||
|
if strings.Contains(compact, "1_3") {
|
||||||
|
return "1_3"
|
||||||
|
}
|
||||||
|
|
||||||
|
// "1,2" / "1,3" gibi liste formatlarini dogrudan yakala.
|
||||||
|
tokenized := strings.NewReplacer(" ", "", ";", ",", "|", ",", "/", ",", "-", ",", "_", ",").Replace(lower)
|
||||||
|
parts := strings.Split(tokenized, ",")
|
||||||
|
has1 := false
|
||||||
|
has2 := false
|
||||||
|
has3 := false
|
||||||
|
for _, p := range parts {
|
||||||
|
t := strings.TrimSpace(p)
|
||||||
|
switch t {
|
||||||
|
case "1":
|
||||||
|
has1 = true
|
||||||
|
case "2":
|
||||||
|
has2 = true
|
||||||
|
case "3":
|
||||||
|
has3 = true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if has1 && has2 {
|
||||||
|
return "1_2"
|
||||||
|
}
|
||||||
|
if has1 && has3 {
|
||||||
|
return "1_3"
|
||||||
|
}
|
||||||
|
if has2 && !has1 && !has3 {
|
||||||
|
return "2"
|
||||||
|
}
|
||||||
|
if has3 && !has1 && !has2 {
|
||||||
|
return "3"
|
||||||
|
}
|
||||||
|
if has1 && !has2 && !has3 {
|
||||||
|
return "1"
|
||||||
|
}
|
||||||
|
|
||||||
|
// "2.00", "2,00", " 2 " gibi varyasyonlari tek tipe indir.
|
||||||
|
s = strings.ReplaceAll(s, ",", ".")
|
||||||
|
if n, err := strconv.ParseFloat(s, 64); err == nil {
|
||||||
|
return strconv.Itoa(int(n))
|
||||||
|
}
|
||||||
|
|
||||||
|
// Metinsel geldiyse ilk rakam bloğunu al.
|
||||||
|
start := -1
|
||||||
|
end := -1
|
||||||
|
for i, r := range s {
|
||||||
|
if r >= '0' && r <= '9' {
|
||||||
|
if start == -1 {
|
||||||
|
start = i
|
||||||
|
}
|
||||||
|
end = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if start != -1 {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if start == -1 || end < start {
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
return s[start : end+1]
|
||||||
|
}
|
||||||
|
|
||||||
|
func resolveParasalIslemSelectExpr(ctx context.Context, sampleQuery string) string {
|
||||||
|
sampleQuery = strings.TrimSpace(sampleQuery)
|
||||||
|
if sampleQuery == "" {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
metaQuery := `
|
||||||
|
SELECT name
|
||||||
|
FROM sys.dm_exec_describe_first_result_set(@tsql, NULL, 0)
|
||||||
|
WHERE error_number IS NULL
|
||||||
|
AND name IS NOT NULL
|
||||||
|
`
|
||||||
|
rows, err := db.MssqlDB.QueryContext(ctx, metaQuery, sql.Named("tsql", sampleQuery))
|
||||||
|
if err != nil {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
defer rows.Close()
|
||||||
|
|
||||||
|
type candidate struct {
|
||||||
|
key string
|
||||||
|
expr string
|
||||||
|
}
|
||||||
|
priority := []candidate{
|
||||||
|
{key: "ata tt01", expr: "CAST(%s AS varchar(16)) AS ParasalIslemTipi,"},
|
||||||
|
{key: "atatt01", expr: "CAST(%s AS varchar(16)) AS ParasalIslemTipi,"},
|
||||||
|
{key: "parasalislemtipi", expr: "CAST(%s AS varchar(16)) AS ParasalIslemTipi,"},
|
||||||
|
{key: "parislemtipi", expr: "CAST(%s AS varchar(16)) AS ParasalIslemTipi,"},
|
||||||
|
{key: "parislemtur", expr: "CAST(%s AS varchar(16)) AS ParasalIslemTipi,"},
|
||||||
|
}
|
||||||
|
|
||||||
|
available := make(map[string]string)
|
||||||
|
for rows.Next() {
|
||||||
|
var col sql.NullString
|
||||||
|
if err := rows.Scan(&col); err != nil {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
name := strings.TrimSpace(col.String)
|
||||||
|
if name == "" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
normalized := strings.ToLower(strings.ReplaceAll(strings.ReplaceAll(name, "_", ""), " ", ""))
|
||||||
|
available[normalized] = name
|
||||||
|
}
|
||||||
|
if err := rows.Err(); err != nil {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, c := range priority {
|
||||||
|
key := strings.ToLower(strings.ReplaceAll(strings.ReplaceAll(c.key, "_", ""), " ", ""))
|
||||||
|
if col, ok := available[key]; ok {
|
||||||
|
return fmt.Sprintf(c.expr, quoteSQLIdent(col))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func quoteSQLIdent(ident string) string {
|
||||||
|
return "[" + strings.ReplaceAll(strings.TrimSpace(ident), "]", "]]") + "]"
|
||||||
|
}
|
||||||
|
|||||||
@@ -137,13 +137,13 @@ func GetStatementAgingBalanceList(ctx context.Context, params models.CustomerBal
|
|||||||
|
|
||||||
usd := toUSD(ln.Bakiye, curr, usdTry, rateMap)
|
usd := toUSD(ln.Bakiye, curr, usdTry, rateMap)
|
||||||
tl := toTRY(ln.Bakiye, curr, rateMap)
|
tl := toTRY(ln.Bakiye, curr, rateMap)
|
||||||
|
add12, add13 := resolveBalanceBuckets(ln)
|
||||||
switch strings.TrimSpace(ln.PislemTipi) {
|
if add12 {
|
||||||
case "1_2":
|
|
||||||
row.Bakiye12 += ln.Bakiye
|
row.Bakiye12 += ln.Bakiye
|
||||||
row.TLBakiye12 += tl
|
row.TLBakiye12 += tl
|
||||||
row.USDBakiye12 += usd
|
row.USDBakiye12 += usd
|
||||||
case "1_3":
|
}
|
||||||
|
if add13 {
|
||||||
row.Bakiye13 += ln.Bakiye
|
row.Bakiye13 += ln.Bakiye
|
||||||
row.TLBakiye13 += tl
|
row.TLBakiye13 += tl
|
||||||
row.USDBakiye13 += usd
|
row.USDBakiye13 += usd
|
||||||
@@ -187,13 +187,14 @@ func loadAgingBalanceLines(ctx context.Context, cariSearch string) ([]mkCariBaki
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
query := fmt.Sprintf(`
|
queryTemplate := `
|
||||||
SELECT
|
SELECT
|
||||||
CurrAccTypeCode,
|
CurrAccTypeCode,
|
||||||
CariKodu = LTRIM(RTRIM(CariKodu)),
|
CariKodu = LTRIM(RTRIM(CariKodu)),
|
||||||
CariDoviz = LTRIM(RTRIM(CariDoviz)),
|
CariDoviz = LTRIM(RTRIM(CariDoviz)),
|
||||||
SirketKodu,
|
SirketKodu,
|
||||||
PislemTipi,
|
PislemTipi,
|
||||||
|
%s
|
||||||
YerelBakiye = CAST(0 AS DECIMAL(18,2)),
|
YerelBakiye = CAST(0 AS DECIMAL(18,2)),
|
||||||
Bakiye,
|
Bakiye,
|
||||||
Vade_Gun,
|
Vade_Gun,
|
||||||
@@ -202,10 +203,30 @@ func loadAgingBalanceLines(ctx context.Context, cariSearch string) ([]mkCariBaki
|
|||||||
WHERE (@CariSearch = '' OR LTRIM(RTRIM(CariKodu)) LIKE '%%' + @CariSearch + '%%')
|
WHERE (@CariSearch = '' OR LTRIM(RTRIM(CariKodu)) LIKE '%%' + @CariSearch + '%%')
|
||||||
AND %s
|
AND %s
|
||||||
ORDER BY CariKodu, CariDoviz, PislemTipi
|
ORDER BY CariKodu, CariDoviz, PislemTipi
|
||||||
`, piyasaScope)
|
`
|
||||||
|
|
||||||
rows, err := db.MssqlDB.QueryContext(ctx, query, sql.Named("CariSearch", strings.TrimSpace(cariSearch)))
|
selectParasalCandidates := make([]string, 0, 7)
|
||||||
if err != nil {
|
if expr := strings.TrimSpace(resolveParasalIslemSelectExpr(ctx, "SELECT * FROM dbo.CARI_BAKIYE_GUN_CACHE")); expr != "" {
|
||||||
|
selectParasalCandidates = append(selectParasalCandidates, expr)
|
||||||
|
}
|
||||||
|
selectParasalCandidates = append(selectParasalCandidates,
|
||||||
|
"CAST(ATAtt01 AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST(ParasalIslemTipi AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST(ParislemTipi AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST(ParIslemTipi AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
"CAST('' AS varchar(16)) AS ParasalIslemTipi,",
|
||||||
|
)
|
||||||
|
|
||||||
|
var rows *sql.Rows
|
||||||
|
for i, sel := range selectParasalCandidates {
|
||||||
|
query := fmt.Sprintf(queryTemplate, sel, piyasaScope)
|
||||||
|
rows, err = db.MssqlDB.QueryContext(ctx, query, sql.Named("CariSearch", strings.TrimSpace(cariSearch)))
|
||||||
|
if err == nil {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if i < len(selectParasalCandidates)-1 && isInvalidColumnError(err) {
|
||||||
|
continue
|
||||||
|
}
|
||||||
return nil, fmt.Errorf("CARI_BAKIYE_GUN_CACHE query error: %w", err)
|
return nil, fmt.Errorf("CARI_BAKIYE_GUN_CACHE query error: %w", err)
|
||||||
}
|
}
|
||||||
defer rows.Close()
|
defer rows.Close()
|
||||||
@@ -219,6 +240,7 @@ func loadAgingBalanceLines(ctx context.Context, cariSearch string) ([]mkCariBaki
|
|||||||
&r.CariDoviz,
|
&r.CariDoviz,
|
||||||
&r.SirketKodu,
|
&r.SirketKodu,
|
||||||
&r.PislemTipi,
|
&r.PislemTipi,
|
||||||
|
&r.ParasalIslemTipi,
|
||||||
&r.YerelBakiye,
|
&r.YerelBakiye,
|
||||||
&r.Bakiye,
|
&r.Bakiye,
|
||||||
&r.VadeGun,
|
&r.VadeGun,
|
||||||
|
|||||||
@@ -23,7 +23,10 @@ SELECT
|
|||||||
a.ItemCode AS Urun_Kodu,
|
a.ItemCode AS Urun_Kodu,
|
||||||
a.ColorCode AS Urun_Rengi,
|
a.ColorCode AS Urun_Rengi,
|
||||||
SUM(a.Qty1) AS Toplam_Adet,
|
SUM(a.Qty1) AS Toplam_Adet,
|
||||||
SUM(ABS(a.Doc_Price)) AS Toplam_Fiyat,
|
CAST(
|
||||||
|
SUM(a.Qty1 * ABS(a.Doc_Price)) / NULLIF(SUM(a.Qty1), 0)
|
||||||
|
AS numeric(18,2)
|
||||||
|
) AS Toplam_Fiyat,
|
||||||
CAST(SUM(a.Qty1 * ABS(a.Doc_Price)) AS numeric(18,2)) AS Toplam_Tutar
|
CAST(SUM(a.Qty1 * ABS(a.Doc_Price)) AS numeric(18,2)) AS Toplam_Tutar
|
||||||
FROM AllInvoicesWithAttributes a
|
FROM AllInvoicesWithAttributes a
|
||||||
LEFT JOIN prItemAttribute AnaGrup
|
LEFT JOIN prItemAttribute AnaGrup
|
||||||
|
|||||||
@@ -23,25 +23,34 @@ type ProductImageItem struct {
|
|||||||
ContentURL string `json:"content_url"`
|
ContentURL string `json:"content_url"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// LIST PRODUCT IMAGES
|
||||||
|
//
|
||||||
|
|
||||||
// GET /api/product-images?code=...&color=...
|
// GET /api/product-images?code=...&color=...
|
||||||
func GetProductImagesHandler(pg *sql.DB) http.HandlerFunc {
|
func GetProductImagesHandler(pg *sql.DB) http.HandlerFunc {
|
||||||
|
|
||||||
return func(w http.ResponseWriter, r *http.Request) {
|
return func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
|
||||||
reqID := strings.TrimSpace(r.Header.Get("X-Request-ID"))
|
reqID := strings.TrimSpace(r.Header.Get("X-Request-ID"))
|
||||||
if reqID == "" {
|
if reqID == "" {
|
||||||
reqID = uuid.NewString()
|
reqID = uuid.NewString()
|
||||||
}
|
}
|
||||||
|
|
||||||
w.Header().Set("X-Request-ID", reqID)
|
w.Header().Set("X-Request-ID", reqID)
|
||||||
|
|
||||||
code := strings.TrimSpace(r.URL.Query().Get("code"))
|
code := strings.TrimSpace(r.URL.Query().Get("code"))
|
||||||
color := strings.TrimSpace(r.URL.Query().Get("color"))
|
color := strings.TrimSpace(r.URL.Query().Get("color"))
|
||||||
|
|
||||||
if code == "" {
|
if code == "" {
|
||||||
|
|
||||||
slog.Warn("product_images.list.bad_request",
|
slog.Warn("product_images.list.bad_request",
|
||||||
"req_id", reqID,
|
"req_id", reqID,
|
||||||
"path", r.URL.Path,
|
"path", r.URL.Path,
|
||||||
"query", r.URL.RawQuery,
|
"query", r.URL.RawQuery,
|
||||||
"reason", "missing_code",
|
"reason", "missing_code",
|
||||||
)
|
)
|
||||||
|
|
||||||
http.Error(w, "Eksik parametre: code gerekli", http.StatusBadRequest)
|
http.Error(w, "Eksik parametre: code gerekli", http.StatusBadRequest)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@@ -50,38 +59,59 @@ func GetProductImagesHandler(pg *sql.DB) http.HandlerFunc {
|
|||||||
SELECT
|
SELECT
|
||||||
b.id,
|
b.id,
|
||||||
b.file_name,
|
b.file_name,
|
||||||
COALESCE(b.file_size, 0) AS file_size,
|
COALESCE(b.file_size,0) AS file_size,
|
||||||
COALESCE(b.storage_path, '') AS storage_path
|
COALESCE(b.storage_path,'') AS storage_path
|
||||||
FROM dfblob b
|
FROM dfblob b
|
||||||
JOIN mmitem i
|
JOIN mmitem i
|
||||||
ON i.id = b.src_id
|
ON i.id = b.src_id
|
||||||
WHERE b.typ = 'img'
|
WHERE b.typ = 'img'
|
||||||
AND b.src_table = 'mmitem'
|
AND b.src_table = 'mmitem'
|
||||||
AND UPPER(i.code) = UPPER($1)
|
AND UPPER(i.code) = UPPER($1)
|
||||||
AND ($2 = '' OR b.file_name ILIKE '%' || '-' || $2 || '-%')
|
AND (
|
||||||
ORDER BY COALESCE(b.sort_order, 999999), b.zlins_dttm DESC, b.id DESC
|
$2 = ''
|
||||||
|
OR b.file_name ILIKE '%' || '-' || $2 || '-%'
|
||||||
|
OR b.file_name ILIKE '%' || '-' || $2 || '_%'
|
||||||
|
)
|
||||||
|
ORDER BY
|
||||||
|
COALESCE(b.sort_order,999999),
|
||||||
|
b.zlins_dttm DESC,
|
||||||
|
b.id DESC
|
||||||
`
|
`
|
||||||
|
|
||||||
rows, err := pg.Query(query, code, color)
|
rows, err := pg.Query(query, code, color)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
||||||
slog.Error("product_images.list.query_failed",
|
slog.Error("product_images.list.query_failed",
|
||||||
"req_id", reqID,
|
"req_id", reqID,
|
||||||
"code", code,
|
"code", code,
|
||||||
"color", color,
|
"color", color,
|
||||||
"err", err.Error(),
|
"err", err.Error(),
|
||||||
)
|
)
|
||||||
|
|
||||||
http.Error(w, "Gorsel sorgu hatasi: "+err.Error(), http.StatusInternalServerError)
|
http.Error(w, "Gorsel sorgu hatasi: "+err.Error(), http.StatusInternalServerError)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
defer rows.Close()
|
defer rows.Close()
|
||||||
|
|
||||||
items := make([]ProductImageItem, 0, 16)
|
items := make([]ProductImageItem, 0, 16)
|
||||||
|
|
||||||
for rows.Next() {
|
for rows.Next() {
|
||||||
|
|
||||||
var it ProductImageItem
|
var it ProductImageItem
|
||||||
if err := rows.Scan(&it.ID, &it.FileName, &it.FileSize, &it.Storage); err != nil {
|
|
||||||
|
if err := rows.Scan(
|
||||||
|
&it.ID,
|
||||||
|
&it.FileName,
|
||||||
|
&it.FileSize,
|
||||||
|
&it.Storage,
|
||||||
|
); err != nil {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
it.ContentURL = fmt.Sprintf("/api/product-images/%d/content", it.ID)
|
it.ContentURL = fmt.Sprintf("/api/product-images/%d/content", it.ID)
|
||||||
|
|
||||||
items = append(items, it)
|
items = append(items, it)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -97,24 +127,35 @@ ORDER BY COALESCE(b.sort_order, 999999), b.zlins_dttm DESC, b.id DESC
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// GET IMAGE CONTENT
|
||||||
|
//
|
||||||
|
|
||||||
// GET /api/product-images/{id}/content
|
// GET /api/product-images/{id}/content
|
||||||
func GetProductImageContentHandler(pg *sql.DB) http.HandlerFunc {
|
func GetProductImageContentHandler(pg *sql.DB) http.HandlerFunc {
|
||||||
|
|
||||||
return func(w http.ResponseWriter, r *http.Request) {
|
return func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
|
||||||
reqID := strings.TrimSpace(r.Header.Get("X-Request-ID"))
|
reqID := strings.TrimSpace(r.Header.Get("X-Request-ID"))
|
||||||
if reqID == "" {
|
if reqID == "" {
|
||||||
reqID = uuid.NewString()
|
reqID = uuid.NewString()
|
||||||
}
|
}
|
||||||
|
|
||||||
w.Header().Set("X-Request-ID", reqID)
|
w.Header().Set("X-Request-ID", reqID)
|
||||||
|
|
||||||
idStr := mux.Vars(r)["id"]
|
idStr := mux.Vars(r)["id"]
|
||||||
|
|
||||||
id, err := strconv.ParseInt(idStr, 10, 64)
|
id, err := strconv.ParseInt(idStr, 10, 64)
|
||||||
|
|
||||||
if err != nil || id <= 0 {
|
if err != nil || id <= 0 {
|
||||||
|
|
||||||
slog.Warn("product_images.content.bad_request",
|
slog.Warn("product_images.content.bad_request",
|
||||||
"req_id", reqID,
|
"req_id", reqID,
|
||||||
"id_raw", idStr,
|
"id_raw", idStr,
|
||||||
"path", r.URL.Path,
|
"path", r.URL.Path,
|
||||||
"reason", "invalid_id",
|
"reason", "invalid_id",
|
||||||
)
|
)
|
||||||
|
|
||||||
http.Error(w, "Gecersiz gorsel id", http.StatusBadRequest)
|
http.Error(w, "Gecersiz gorsel id", http.StatusBadRequest)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@@ -128,83 +169,89 @@ func GetProductImageContentHandler(pg *sql.DB) http.HandlerFunc {
|
|||||||
|
|
||||||
err = pg.QueryRow(`
|
err = pg.QueryRow(`
|
||||||
SELECT
|
SELECT
|
||||||
COALESCE(file_name, ''),
|
COALESCE(file_name,''),
|
||||||
COALESCE(storage_path, ''),
|
COALESCE(storage_path,''),
|
||||||
COALESCE(stored_in_db, false),
|
COALESCE(stored_in_db,false),
|
||||||
bin
|
bin
|
||||||
FROM dfblob
|
FROM dfblob
|
||||||
WHERE id = $1
|
WHERE id = $1
|
||||||
AND typ = 'img'
|
AND typ = 'img'
|
||||||
`, id).Scan(&fileName, &storagePath, &storedInDB, &binData)
|
`, id).Scan(&fileName, &storagePath, &storedInDB, &binData)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
||||||
if err == sql.ErrNoRows {
|
if err == sql.ErrNoRows {
|
||||||
|
|
||||||
slog.Warn("product_images.content.not_found_row",
|
slog.Warn("product_images.content.not_found_row",
|
||||||
"req_id", reqID,
|
"req_id", reqID,
|
||||||
"id", id,
|
"id", id,
|
||||||
)
|
)
|
||||||
|
|
||||||
http.NotFound(w, r)
|
http.NotFound(w, r)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
slog.Error("product_images.content.query_failed",
|
slog.Error("product_images.content.query_failed",
|
||||||
"req_id", reqID,
|
"req_id", reqID,
|
||||||
"id", id,
|
"id", id,
|
||||||
"err", err.Error(),
|
"err", err.Error(),
|
||||||
)
|
)
|
||||||
|
|
||||||
http.Error(w, "Gorsel okunamadi: "+err.Error(), http.StatusInternalServerError)
|
http.Error(w, "Gorsel okunamadi: "+err.Error(), http.StatusInternalServerError)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DB içinde binary saklıysa
|
||||||
if storedInDB && len(binData) > 0 {
|
if storedInDB && len(binData) > 0 {
|
||||||
slog.Info("product_images.content.served_from_db",
|
|
||||||
"req_id", reqID,
|
|
||||||
"id", id,
|
|
||||||
"file_name", fileName,
|
|
||||||
"bytes", len(binData),
|
|
||||||
)
|
|
||||||
w.Header().Set("Content-Type", http.DetectContentType(binData))
|
w.Header().Set("Content-Type", http.DetectContentType(binData))
|
||||||
w.Header().Set("Cache-Control", "public, max-age=3600")
|
w.Header().Set("Cache-Control", "public, max-age=3600")
|
||||||
|
|
||||||
_, _ = w.Write(binData)
|
_, _ = w.Write(binData)
|
||||||
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
resolved, tried := resolveStoragePath(storagePath)
|
resolved, tried := resolveStoragePath(storagePath)
|
||||||
|
|
||||||
if resolved == "" {
|
if resolved == "" {
|
||||||
|
|
||||||
slog.Warn("product_images.content.file_not_found",
|
slog.Warn("product_images.content.file_not_found",
|
||||||
"req_id", reqID,
|
"req_id", reqID,
|
||||||
"id", id,
|
"id", id,
|
||||||
"stored_in_db", storedInDB,
|
|
||||||
"file_name", fileName,
|
"file_name", fileName,
|
||||||
"storage_path", storagePath,
|
"storage_path", storagePath,
|
||||||
"tried", tried,
|
"tried", tried,
|
||||||
)
|
)
|
||||||
|
|
||||||
http.NotFound(w, r)
|
http.NotFound(w, r)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
slog.Info("product_images.content.served_from_file",
|
|
||||||
"req_id", reqID,
|
|
||||||
"id", id,
|
|
||||||
"file_name", fileName,
|
|
||||||
"storage_path", storagePath,
|
|
||||||
"resolved_path", resolved,
|
|
||||||
)
|
|
||||||
|
|
||||||
w.Header().Set("Cache-Control", "public, max-age=3600")
|
w.Header().Set("Cache-Control", "public, max-age=3600")
|
||||||
|
|
||||||
http.ServeFile(w, r, resolved)
|
http.ServeFile(w, r, resolved)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// FILE PATH RESOLVER
|
||||||
|
//
|
||||||
|
|
||||||
func resolveStoragePath(storagePath string) (string, []string) {
|
func resolveStoragePath(storagePath string) (string, []string) {
|
||||||
|
|
||||||
raw := strings.TrimSpace(storagePath)
|
raw := strings.TrimSpace(storagePath)
|
||||||
|
|
||||||
if raw == "" {
|
if raw == "" {
|
||||||
return "", nil
|
return "", nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// URL/query temizligi ve platforma uygun normalize
|
|
||||||
if i := strings.Index(raw, "?"); i >= 0 {
|
if i := strings.Index(raw, "?"); i >= 0 {
|
||||||
raw = raw[:i]
|
raw = raw[:i]
|
||||||
}
|
}
|
||||||
|
|
||||||
raw = strings.ReplaceAll(raw, "\\", "/")
|
raw = strings.ReplaceAll(raw, "\\", "/")
|
||||||
|
|
||||||
if scheme := strings.Index(raw, "://"); scheme >= 0 {
|
if scheme := strings.Index(raw, "://"); scheme >= 0 {
|
||||||
rest := raw[scheme+3:]
|
rest := raw[scheme+3:]
|
||||||
if i := strings.Index(rest, "/"); i >= 0 {
|
if i := strings.Index(rest, "/"); i >= 0 {
|
||||||
@@ -215,47 +262,36 @@ func resolveStoragePath(storagePath string) (string, []string) {
|
|||||||
raw = strings.TrimPrefix(raw, "./")
|
raw = strings.TrimPrefix(raw, "./")
|
||||||
raw = strings.TrimPrefix(raw, "/")
|
raw = strings.TrimPrefix(raw, "/")
|
||||||
raw = strings.TrimPrefix(raw, "uploads/")
|
raw = strings.TrimPrefix(raw, "uploads/")
|
||||||
|
|
||||||
raw = filepath.ToSlash(filepath.Clean(raw))
|
raw = filepath.ToSlash(filepath.Clean(raw))
|
||||||
|
|
||||||
relUploads := filepath.FromSlash(filepath.Join("uploads", raw))
|
relUploads := filepath.FromSlash(filepath.Join("uploads", raw))
|
||||||
rawT300 := raw
|
|
||||||
relUploadsT300 := relUploads
|
|
||||||
if strings.Contains(filepath.ToSlash(relUploads), "uploads/image/") &&
|
|
||||||
!strings.Contains(filepath.ToSlash(relUploads), "uploads/image/t300/") {
|
|
||||||
rawT300 = strings.Replace(filepath.ToSlash(raw), "image/", "image/t300/", 1)
|
|
||||||
relUploadsT300 = filepath.FromSlash(
|
|
||||||
strings.Replace(filepath.ToSlash(relUploads), "uploads/image/", "uploads/image/t300/", 1),
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
candidates := []string{
|
candidates := []string{
|
||||||
filepath.Clean(storagePath),
|
filepath.Clean(storagePath),
|
||||||
filepath.FromSlash(filepath.Clean(strings.TrimPrefix(storagePath, "/"))),
|
filepath.FromSlash(filepath.Clean(strings.TrimPrefix(storagePath, "/"))),
|
||||||
filepath.FromSlash(filepath.Clean(raw)),
|
filepath.FromSlash(filepath.Clean(raw)),
|
||||||
relUploads,
|
relUploads,
|
||||||
relUploadsT300,
|
|
||||||
filepath.Join(".", relUploads),
|
filepath.Join(".", relUploads),
|
||||||
filepath.Join(".", relUploadsT300),
|
|
||||||
filepath.Join("..", relUploads),
|
filepath.Join("..", relUploads),
|
||||||
filepath.Join("..", relUploadsT300),
|
|
||||||
filepath.Join("..", "..", relUploads),
|
filepath.Join("..", "..", relUploads),
|
||||||
filepath.Join("..", "..", relUploadsT300),
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if root := strings.TrimSpace(os.Getenv("BLOB_ROOT")); root != "" {
|
if root := strings.TrimSpace(os.Getenv("BLOB_ROOT")); root != "" {
|
||||||
|
|
||||||
candidates = append(candidates,
|
candidates = append(candidates,
|
||||||
filepath.Join(root, raw),
|
filepath.Join(root, raw),
|
||||||
filepath.Join(root, filepath.FromSlash(rawT300)),
|
|
||||||
filepath.Join(root, relUploads),
|
filepath.Join(root, relUploads),
|
||||||
filepath.Join(root, relUploadsT300),
|
|
||||||
filepath.Join(root, "uploads", raw),
|
filepath.Join(root, "uploads", raw),
|
||||||
filepath.Join(root, "uploads", filepath.FromSlash(rawT300)),
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, p := range candidates {
|
for _, p := range candidates {
|
||||||
|
|
||||||
if p == "" {
|
if p == "" {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
if st, err := os.Stat(p); err == nil && !st.IsDir() {
|
if st, err := os.Stat(p); err == nil && !st.IsDir() {
|
||||||
return p, candidates
|
return p, candidates
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,125 +0,0 @@
|
|||||||
/* eslint-disable */
|
|
||||||
/**
|
|
||||||
* THIS FILE IS GENERATED AUTOMATICALLY.
|
|
||||||
* 1. DO NOT edit this file directly as it won't do anything.
|
|
||||||
* 2. EDIT the original quasar.config file INSTEAD.
|
|
||||||
* 3. DO NOT git commit this file. It should be ignored.
|
|
||||||
*
|
|
||||||
* This file is still here because there was an error in
|
|
||||||
* the original quasar.config file and this allows you to
|
|
||||||
* investigate the Node.js stack error.
|
|
||||||
*
|
|
||||||
* After you fix the original file, this file will be
|
|
||||||
* deleted automatically.
|
|
||||||
**/
|
|
||||||
|
|
||||||
|
|
||||||
// quasar.config.js
|
|
||||||
import { defineConfig } from "@quasar/app-webpack/wrappers";
|
|
||||||
var quasar_config_default = defineConfig(() => {
|
|
||||||
const apiBaseUrl = (process.env.VITE_API_BASE_URL || "/api").trim();
|
|
||||||
return {
|
|
||||||
/* =====================================================
|
|
||||||
APP INFO
|
|
||||||
===================================================== */
|
|
||||||
productName: "Baggi BSS",
|
|
||||||
productDescription: "Baggi Tekstil Business Support System",
|
|
||||||
/* =====================================================
|
|
||||||
BOOT FILES
|
|
||||||
===================================================== */
|
|
||||||
boot: ["dayjs"],
|
|
||||||
/* =====================================================
|
|
||||||
GLOBAL CSS
|
|
||||||
===================================================== */
|
|
||||||
css: ["app.css"],
|
|
||||||
/* =====================================================
|
|
||||||
ICONS / FONTS
|
|
||||||
===================================================== */
|
|
||||||
extras: [
|
|
||||||
"roboto-font",
|
|
||||||
"material-icons"
|
|
||||||
],
|
|
||||||
/* =====================================================
|
|
||||||
BUILD (PRODUCTION)
|
|
||||||
===================================================== */
|
|
||||||
build: {
|
|
||||||
vueRouterMode: "hash",
|
|
||||||
env: {
|
|
||||||
VITE_API_BASE_URL: apiBaseUrl
|
|
||||||
},
|
|
||||||
esbuildTarget: {
|
|
||||||
browser: ["es2022", "firefox115", "chrome115", "safari14"],
|
|
||||||
node: "node20"
|
|
||||||
},
|
|
||||||
// Cache & performance
|
|
||||||
gzip: true,
|
|
||||||
preloadChunks: true
|
|
||||||
},
|
|
||||||
/* =====================================================
|
|
||||||
DEV SERVER (LOCAL)
|
|
||||||
===================================================== */
|
|
||||||
devServer: {
|
|
||||||
server: { type: "http" },
|
|
||||||
port: 9e3,
|
|
||||||
open: true,
|
|
||||||
// DEV proxy (CORS'suz)
|
|
||||||
proxy: [
|
|
||||||
{
|
|
||||||
context: ["/api"],
|
|
||||||
target: "http://localhost:8080",
|
|
||||||
changeOrigin: true,
|
|
||||||
secure: false
|
|
||||||
}
|
|
||||||
]
|
|
||||||
},
|
|
||||||
/* =====================================================
|
|
||||||
QUASAR FRAMEWORK
|
|
||||||
===================================================== */
|
|
||||||
framework: {
|
|
||||||
config: {
|
|
||||||
notify: {
|
|
||||||
position: "top",
|
|
||||||
timeout: 2500
|
|
||||||
}
|
|
||||||
},
|
|
||||||
lang: "tr",
|
|
||||||
plugins: [
|
|
||||||
"Loading",
|
|
||||||
"Dialog",
|
|
||||||
"Notify"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
animations: [],
|
|
||||||
/* =====================================================
|
|
||||||
SSR / PWA (DISABLED)
|
|
||||||
===================================================== */
|
|
||||||
ssr: {
|
|
||||||
prodPort: 3e3,
|
|
||||||
middlewares: ["render"],
|
|
||||||
pwa: false
|
|
||||||
},
|
|
||||||
pwa: {
|
|
||||||
workboxMode: "GenerateSW"
|
|
||||||
},
|
|
||||||
/* =====================================================
|
|
||||||
MOBILE / DESKTOP
|
|
||||||
===================================================== */
|
|
||||||
capacitor: {
|
|
||||||
hideSplashscreen: true
|
|
||||||
},
|
|
||||||
electron: {
|
|
||||||
preloadScripts: ["electron-preload"],
|
|
||||||
inspectPort: 5858,
|
|
||||||
bundler: "packager",
|
|
||||||
builder: {
|
|
||||||
appId: "baggisowtfaresystem"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
bex: {
|
|
||||||
extraScripts: []
|
|
||||||
}
|
|
||||||
};
|
|
||||||
});
|
|
||||||
export {
|
|
||||||
quasar_config_default as default
|
|
||||||
};
|
|
||||||
@@ -635,12 +635,8 @@ const canReadFinance = canRead('finance')
|
|||||||
const canExportFinance = canExport('finance')
|
const canExportFinance = canExport('finance')
|
||||||
|
|
||||||
const islemTipiOptions = [
|
const islemTipiOptions = [
|
||||||
{ label: '1_2 Bakiye Pr.Br', value: 'prbr_1_2' },
|
{ label: '1_2', value: '1_2' },
|
||||||
{ label: '1_3 Bakiye Pr.Br', value: 'prbr_1_3' },
|
{ label: '1_3', value: '1_3' }
|
||||||
{ label: '1_2 USD Bakiye', value: 'usd_1_2' },
|
|
||||||
{ label: '1_2 TRY Bakiye', value: 'try_1_2' },
|
|
||||||
{ label: '1_3 USD Bakiye', value: 'usd_1_3' },
|
|
||||||
{ label: '1_3 TRY Bakiye', value: 'try_1_3' }
|
|
||||||
]
|
]
|
||||||
|
|
||||||
const staticMoneyFields = ['usd_bakiye_1_2', 'tl_bakiye_1_2', 'usd_bakiye_1_3', 'tl_bakiye_1_3']
|
const staticMoneyFields = ['usd_bakiye_1_2', 'tl_bakiye_1_2', 'usd_bakiye_1_3', 'tl_bakiye_1_3']
|
||||||
@@ -688,11 +684,7 @@ const metricDefs = {
|
|||||||
try_1_3: { name: 'tl_bakiye_1_3', label: '1_3 TRY_BAKIYE', field: 'tl_bakiye_1_3', align: 'center', sortable: true, sort: (a, b) => toNumericSortValue(a) - toNumericSortValue(b) }
|
try_1_3: { name: 'tl_bakiye_1_3', label: '1_3 TRY_BAKIYE', field: 'tl_bakiye_1_3', align: 'center', sortable: true, sort: (a, b) => toNumericSortValue(a) - toNumericSortValue(b) }
|
||||||
}
|
}
|
||||||
|
|
||||||
const selectedMetricKeys = computed(() => {
|
const selectedMetricKeys = computed(() => [...Object.keys(metricDefs)])
|
||||||
const selected = store.filters.islemTipi || []
|
|
||||||
if (!selected.length) return [...Object.keys(metricDefs)]
|
|
||||||
return selected.filter((k) => k in metricDefs)
|
|
||||||
})
|
|
||||||
|
|
||||||
const summaryColumns = computed(() => ([
|
const summaryColumns = computed(() => ([
|
||||||
{ name: 'expand', label: '', field: 'expand', align: 'center', sortable: false },
|
{ name: 'expand', label: '', field: 'expand', align: 'center', sortable: false },
|
||||||
|
|||||||
@@ -538,12 +538,8 @@ const canReadFinance = canRead('finance')
|
|||||||
const canExportFinance = canExport('finance')
|
const canExportFinance = canExport('finance')
|
||||||
|
|
||||||
const islemTipiOptions = [
|
const islemTipiOptions = [
|
||||||
{ label: '1_2 Bakiye Pr.Br', value: 'prbr_1_2' },
|
{ label: '1_2', value: '1_2' },
|
||||||
{ label: '1_3 Bakiye Pr.Br', value: 'prbr_1_3' },
|
{ label: '1_3', value: '1_3' }
|
||||||
{ label: '1_2 USD Bakiye', value: 'usd_1_2' },
|
|
||||||
{ label: '1_2 TRY Bakiye', value: 'try_1_2' },
|
|
||||||
{ label: '1_3 USD Bakiye', value: 'usd_1_3' },
|
|
||||||
{ label: '1_3 TRY Bakiye', value: 'try_1_3' }
|
|
||||||
]
|
]
|
||||||
|
|
||||||
const staticMoneyFields = ['usd_bakiye_1_2', 'tl_bakiye_1_2', 'usd_bakiye_1_3', 'tl_bakiye_1_3']
|
const staticMoneyFields = ['usd_bakiye_1_2', 'tl_bakiye_1_2', 'usd_bakiye_1_3', 'tl_bakiye_1_3']
|
||||||
@@ -590,11 +586,7 @@ const metricDefs = {
|
|||||||
try_1_3: { name: 'tl_bakiye_1_3', label: '1_3 TRY_BAKIYE', field: 'tl_bakiye_1_3', align: 'center', sortable: true, sort: (a, b) => toNumericSortValue(a) - toNumericSortValue(b) }
|
try_1_3: { name: 'tl_bakiye_1_3', label: '1_3 TRY_BAKIYE', field: 'tl_bakiye_1_3', align: 'center', sortable: true, sort: (a, b) => toNumericSortValue(a) - toNumericSortValue(b) }
|
||||||
}
|
}
|
||||||
|
|
||||||
const selectedMetricKeys = computed(() => {
|
const selectedMetricKeys = computed(() => Object.keys(metricDefs))
|
||||||
const selected = store.filters.islemTipi || []
|
|
||||||
if (!selected.length) return Object.keys(metricDefs)
|
|
||||||
return selected.filter((k) => k in metricDefs)
|
|
||||||
})
|
|
||||||
|
|
||||||
const summaryColumns = computed(() => ([
|
const summaryColumns = computed(() => ([
|
||||||
{ name: 'expand', label: '', field: 'expand', align: 'center', sortable: false },
|
{ name: 'expand', label: '', field: 'expand', align: 'center', sortable: false },
|
||||||
|
|||||||
@@ -78,12 +78,8 @@ export const useAccountAgingBalanceStore = defineStore('accountAgingBalance', {
|
|||||||
const islemTipiOk =
|
const islemTipiOk =
|
||||||
!state.filters.islemTipi.length ||
|
!state.filters.islemTipi.length ||
|
||||||
state.filters.islemTipi.some((t) => {
|
state.filters.islemTipi.some((t) => {
|
||||||
if (t === 'prbr_1_2') return bak12 !== 0
|
if (t === '1_2') return bak12 !== 0 || usd12 !== 0 || try12 !== 0
|
||||||
if (t === 'prbr_1_3') return bak13 !== 0
|
if (t === '1_3') return bak13 !== 0 || usd13 !== 0 || try13 !== 0
|
||||||
if (t === 'usd_1_2') return usd12 !== 0
|
|
||||||
if (t === 'try_1_2') return try12 !== 0
|
|
||||||
if (t === 'usd_1_3') return usd13 !== 0
|
|
||||||
if (t === 'try_1_3') return try13 !== 0
|
|
||||||
return false
|
return false
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
@@ -92,12 +92,8 @@ export const useCustomerBalanceListStore = defineStore('customerBalanceList', {
|
|||||||
const islemTipiOk =
|
const islemTipiOk =
|
||||||
!state.filters.islemTipi.length ||
|
!state.filters.islemTipi.length ||
|
||||||
state.filters.islemTipi.some((t) => {
|
state.filters.islemTipi.some((t) => {
|
||||||
if (t === 'prbr_1_2') return bak12 !== 0
|
if (t === '1_2') return bak12 !== 0 || usd12 !== 0 || try12 !== 0
|
||||||
if (t === 'prbr_1_3') return bak13 !== 0
|
if (t === '1_3') return bak13 !== 0 || usd13 !== 0 || try13 !== 0
|
||||||
if (t === 'usd_1_2') return usd12 !== 0
|
|
||||||
if (t === 'try_1_2') return try12 !== 0
|
|
||||||
if (t === 'usd_1_3') return usd13 !== 0
|
|
||||||
if (t === 'try_1_3') return try13 !== 0
|
|
||||||
return false
|
return false
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -194,7 +190,15 @@ export const useCustomerBalanceListStore = defineStore('customerBalanceList', {
|
|||||||
const { data } = await api.get('/finance/customer-balances', {
|
const { data } = await api.get('/finance/customer-balances', {
|
||||||
params: {
|
params: {
|
||||||
selected_date: this.filters.selectedDate,
|
selected_date: this.filters.selectedDate,
|
||||||
cari_search: String(this.filters.cariSearch || '').trim()
|
cari_search: String(this.filters.cariSearch || '').trim(),
|
||||||
|
cari_ilk_grup: (this.filters.cariIlkGrup || []).join(','),
|
||||||
|
piyasa: (this.filters.piyasa || []).join(','),
|
||||||
|
temsilci: (this.filters.temsilci || []).join(','),
|
||||||
|
risk_durumu: (this.filters.riskDurumu || []).join(','),
|
||||||
|
islem_tipi: (this.filters.islemTipi || []).join(','),
|
||||||
|
ulke: (this.filters.ulke || []).join(','),
|
||||||
|
il: (this.filters.il || []).join(','),
|
||||||
|
ilce: (this.filters.ilce || []).join(',')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
this.rows = Array.isArray(data) ? data : []
|
this.rows = Array.isArray(data) ? data : []
|
||||||
|
|||||||
Reference in New Issue
Block a user