fix: new.gholaktala.ir is Khanegi modular, not Hamkar

Revert wrong FORCE_HAMKAR classification; lock domain in FORCE_KHANEGI and keep Hamkar/Khanegi overrides separate.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-08-11 17:40:13 +03:30
co-authored by Cursor
parent 0aeb17bd1b
commit 859530a669
3 changed files with 120 additions and 118 deletions
+3 -4
View File
@@ -30,15 +30,14 @@ const FORCE_KHANEGI: Array<{ domain?: string; name?: string; externalId?: number
{ domain: 'abaeigold.ir' }, { domain: 'abaeigold.ir' },
{ domain: 'niazitala.ir' }, { domain: 'niazitala.ir' },
{ domain: 'garoosigholaktala.ir' }, { domain: 'garoosigholaktala.ir' },
{ domain: 'new.gholaktala.ir' },
{ domain: 'kh.kashkolgold.ir' }, { domain: 'kh.kashkolgold.ir' },
{ domain: 'goldsun.zaarbox.ir' }, { domain: 'goldsun.zaarbox.ir' },
{ domain: 'goldaliii.com' }, { domain: 'goldaliii.com' },
]; ];
/** Never mix with FORCE_KHANEGI — these sold versions are Hamkar (site/* APIs). */ /** Manual Hamkar locks — never put Khanegi domains here. */
const FORCE_HAMKAR: Array<{ domain?: string; name?: string; externalId?: number }> = [ const FORCE_HAMKAR: Array<{ domain?: string; name?: string; externalId?: number }> = [];
{ domain: 'new.gholaktala.ir' },
];
/** Canonical public domains after migrations */ /** Canonical public domains after migrations */
const DOMAIN_OVERRIDES: Record<string, { domain: string; appUrl: string; nodeServer: string }> = { const DOMAIN_OVERRIDES: Record<string, { domain: string; appUrl: string; nodeServer: string }> = {
-114
View File
@@ -1,114 +0,0 @@
import { PrismaClient } from '@prisma/client'
/**
* Fix misclassified tenant: new.gholaktala.ir is Hamkar (user calls /site/settings),
* not Khanegi modular. Run on production API host:
* set -a && . ./.env && set +a && node scripts/fix-gholaktala-to-hamkar.mjs
*/
const prisma = new PrismaClient()
const APPLY = process.argv.includes('--apply')
const DOMAIN = 'new.gholaktala.ir'
function bumpAppVersion(current) {
const v = String(current || '1').trim() || '1'
if (/^\d+$/.test(v)) return String(Number(v) + 1)
const semver = v.match(/^(\d+)\.(\d+)\.(\d+)$/)
if (semver) return `${semver[1]}.${semver[2]}.${Number(semver[3]) + 1}`
return String(Date.now())
}
async function main() {
const tenants = await prisma.tenant.findMany({
where: {
OR: [
{ domain: { contains: 'gholaktala', mode: 'insensitive' } },
{ domains: { string_contains: 'gholaktala' } },
{ slug: { contains: 'gholak', mode: 'insensitive' } },
],
},
select: {
id: true,
nameFa: true,
domain: true,
domains: true,
slug: true,
product: true,
uiVariant: true,
appVersion: true,
nodeServer: true,
notes: true,
},
})
console.log(
'MATCHES',
JSON.stringify(
tenants.map((t) => ({
id: t.id,
domain: t.domain,
product: t.product,
uiVariant: t.uiVariant,
appVersion: t.appVersion,
})),
null,
2,
),
)
const tenant =
tenants.find((t) => String(t.domain).toLowerCase() === DOMAIN) ||
tenants.find((t) => String(t.domain).toLowerCase().includes('new.gholaktala'))
if (!tenant) throw new Error(`Tenant not found for ${DOMAIN}`)
console.log('SELECTED', tenant)
if (!APPLY) {
console.log('DRY_RUN — re-run with --apply to set product=hamkar')
return
}
const nextVersion = bumpAppVersion(tenant.appVersion)
const full = await prisma.tenant.findUnique({ where: { id: tenant.id } })
const ui = full?.appUiConfig
const keepUi =
ui && typeof ui === 'object' && !Array.isArray(ui) && ui.kind === 'hamkar'
? ui
: null
const updated = await prisma.tenant.update({
where: { id: tenant.id },
data: {
product: 'hamkar',
appUiConfig: keepUi,
appVersion: nextVersion,
notes: [
String(tenant.notes || '')
.replace(/\s*\|?\s*misclassified-as-khanegi/g, '')
.trim(),
'product=hamkar (fixed; was wrongly khanegi/modular)',
]
.filter(Boolean)
.join(' | '),
},
})
console.log('UPDATED', {
id: updated.id,
domain: updated.domain,
product: updated.product,
appVersion: updated.appVersion,
})
console.log(
'NOTE: Live frontend is Hamkar (/site/settings). Server must be Hamkar Laravel too — Khanegi api/get_settings alone is not enough.',
)
}
main()
.catch((e) => {
console.error(e)
process.exitCode = 1
})
.finally(async () => {
await prisma.$disconnect()
})
+117
View File
@@ -0,0 +1,117 @@
import { PrismaClient } from '@prisma/client'
/**
* Ensure new.gholaktala.ir stays Khanegi modular (not Hamkar).
* set -a && . ./.env && set +a && node scripts/fix-gholaktala-to-khanegi.mjs --apply
*/
const prisma = new PrismaClient()
const APPLY = process.argv.includes('--apply')
const DOMAIN = 'new.gholaktala.ir'
function bumpAppVersion(current) {
const v = String(current || '1').trim() || '1'
if (/^\d+$/.test(v)) return String(Number(v) + 1)
const semver = v.match(/^(\d+)\.(\d+)\.(\d+)$/)
if (semver) return `${semver[1]}.${semver[2]}.${Number(semver[3]) + 1}`
return String(Date.now())
}
async function main() {
const tenants = await prisma.tenant.findMany({
where: {
OR: [
{ domain: { equals: DOMAIN, mode: 'insensitive' } },
{ domains: { string_contains: DOMAIN } },
{ domain: { contains: 'gholaktala', mode: 'insensitive' } },
],
},
select: {
id: true,
nameFa: true,
domain: true,
product: true,
uiVariant: true,
appVersion: true,
notes: true,
},
})
console.log('MATCHES', JSON.stringify(tenants, null, 2))
const tenant =
tenants.find((t) => String(t.domain).toLowerCase() === DOMAIN) || tenants[0]
if (!tenant) throw new Error(`Tenant not found for ${DOMAIN}`)
const alreadyOk =
tenant.product === 'khanegi' && String(tenant.uiVariant || 'modular') !== 'newTheme'
console.log('SELECTED', {
...tenant,
alreadyOk,
expected: { product: 'khanegi', uiVariant: 'modular', frontend: 'userModular', api: '/api/get_settings' },
})
if (!APPLY) {
console.log('DRY_RUN — re-run with --apply to force product=khanegi uiVariant=modular')
return
}
if (alreadyOk && tenant.product === 'khanegi') {
const updated = await prisma.tenant.update({
where: { id: tenant.id },
data: {
product: 'khanegi',
uiVariant: 'modular',
notes: [
String(tenant.notes || '')
.replace(/\s*\|\s*product=hamkar[^\|]*/g, '')
.trim(),
'product=khanegi modular (confirmed)',
]
.filter(Boolean)
.join(' | '),
},
})
console.log('CONFIRMED', {
id: updated.id,
product: updated.product,
uiVariant: updated.uiVariant,
appVersion: updated.appVersion,
})
return
}
const updated = await prisma.tenant.update({
where: { id: tenant.id },
data: {
product: 'khanegi',
uiVariant: 'modular',
appVersion: bumpAppVersion(tenant.appVersion),
notes: [
String(tenant.notes || '')
.replace(/\s*\|\s*product=hamkar[^\|]*/g, '')
.trim(),
'product=khanegi modular (restored; not hamkar)',
]
.filter(Boolean)
.join(' | '),
},
})
console.log('UPDATED', {
id: updated.id,
product: updated.product,
uiVariant: updated.uiVariant,
appVersion: updated.appVersion,
})
}
main()
.catch((e) => {
console.error(e)
process.exitCode = 1
})
.finally(async () => {
await prisma.$disconnect()
})