ЛК на Fancy с Firebird: все запросы к DEPO, курсы, база SPECTRE

ЛК (bj-lk берёт данные у bj-server) сам работает с той СУБД, что выбрана для DEPO.
- Перевод на Firebird: YEAR/MONTH/DAY(x) — EXTRACT, AS float — AS DOUBLE PRECISION (float T-SQL — 8 байт,
  FLOAT Firebird — 4: точность сумм и цен в ЛК); шаблоны со сложением строк (история операций Hist02, поиск
  клиента Man01) — Firebird-тексты до подстановки (depoSQL); UPPER по кириллице — в WIN1251 (база NONE).
- Курсы валют (Fx01): на Firebird запрос от всех курсов шёл больше 200 с (лимит 15 с — курсов нет) — для
  Firebird от 20 валют, 0,2 с.
- База SPECTRE (архив портфеля и операций ЛК): поле в «Трансферные таблицы DEPO»; у Firebird — путь или строка
  подключения Fancy (может быть на другом компьютере); не задана — ЛК пишет, где указать. На данных SPECTRE
  не проверено: базы нет.
- Тест FBLiveLK: функции ЛК, ручного ввода, сверки переводов и QUIK на копии базы по договору К1 Бубликова —
  все работают, 0,07–0,26 с каждая; FBLivePrepare — 101 из 101 запроса.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Q7eREaYwUt1i4fNLZcGnjn
This commit is contained in:
fontvielle
2026-10-27 20:00:28 +03:00
parent 1d8bb0c032
commit 312e4f70f1
12 changed files with 301 additions and 10 deletions
+18 -1
View File
@@ -5,7 +5,9 @@ package lkgateway
// держать второй текст в каждом месте вызова, подключение к Firebird переводит запросы само (fbConn):
// - точный текст Firebird — для запросов, которые механически не переводятся (fsql.FB, ключ — текст T-SQL);
// - остальное механически, вне строк и комментариев: без dbo., TOP n — FIRST n, ISNULL — COALESCE,
// GETDATE() — CURRENT_TIMESTAMP, LEN — CHAR_LENGTH, N'…' — '…', «exec имя» — EXECUTE PROCEDURE имя;
// GETDATE() — CURRENT_TIMESTAMP, LEN — CHAR_LENGTH, YEAR(x) — EXTRACT(YEAR FROM x), AS float — AS DOUBLE
// PRECISION (float T-SQL — 8 байт, FLOAT Firebird — 4), N'…' — '…', «exec имя» — EXECUTE PROCEDURE имя;
// - шаблоны (fmt, {ACC}) с тем, что механически не переводится, выбираются до подстановки — depoSQL;
// - именованные параметры @имя (sql.Named) — позиционные ? в порядке появления в тексте;
// - GUID в параметрах — в верхнем регистре (в таблицах обмена Firebird GUID — строка в верхнем регистре,
// uniqueidentifier MSSQL сравнивается без учёта регистра); время «2006-01-02T15:04:05» — с пробелом вместо T.
@@ -254,11 +256,24 @@ var (
fbIsNullRe = regexp.MustCompile(`(?i)\bISNULL\s*\(`)
fbGetDateRe = regexp.MustCompile(`(?i)\bGETDATE\s*\(\s*\)`)
fbLenRe = regexp.MustCompile(`(?i)\bLEN\s*\(`)
fbDatePartRe = regexp.MustCompile(`(?i)\b(YEAR|MONTH|DAY)\s*\(\s*([A-Za-z_][A-Za-z0-9_.]*)\s*\)`)
fbFloatRe = regexp.MustCompile(`(?i)\bAS\s+float\b`)
fbTopRe = regexp.MustCompile(`(?i)\bSELECT(\s+DISTINCT)?\s+TOP\s*(\(\s*@?\w+\s*\)|\d+)`)
fbGUIDRe = regexp.MustCompile(`^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$`)
fbISOTimeRe = regexp.MustCompile(`^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}(:\d{2}(\.\d+)?)?$`)
)
// depoSQL — текст запроса-шаблона для СУБД базы DEPO: для Firebird — перевод из fsql.FB, если он есть (шаблон с
// fmt-подстановкой или {ACC} подключение к Firebird по тексту уже не узнает). Остальное переводит fbConn.
func depoSQL(f FancyMSSQLSettings, q string) string {
if f.IsFirebird() {
if t, ok := fsql.FB[q]; ok {
return t
}
}
return q
}
// fbSQL — текст запроса для Firebird: точный перевод из fsql.FB, иначе механический.
func fbSQL(q string) string {
if t, ok := fsql.FB[q]; ok {
@@ -275,6 +290,8 @@ func fbSQL(q string) string {
code = fbIsNullRe.ReplaceAllString(code, "COALESCE(")
code = fbGetDateRe.ReplaceAllString(code, "CURRENT_TIMESTAMP")
code = fbLenRe.ReplaceAllString(code, "CHAR_LENGTH(")
code = fbDatePartRe.ReplaceAllString(code, "EXTRACT($1 FROM $2)")
code = fbFloatRe.ReplaceAllString(code, "AS DOUBLE PRECISION") // float T-SQL — 8 байт, FLOAT Firebird — 4
return fbTopRe.ReplaceAllStringFunc(code, func(s string) string {
m := fbTopRe.FindStringSubmatch(s)
return "SELECT FIRST " + m[2] + m[1] // в Firebird FIRST — до DISTINCT