On-line: гостей 1. Всего: 1 [подробнее..]
АвторСообщение
alkresin
moderator


Пост N: 31
Зарегистрирован: 06.07.06
ссылка на сообщение  Отправлено: 31.01.08 11:36. Заголовок: Leto DB Server(продолжение)


Только что открыл на Sourceforge новый проект - Leto DB Server - https://sourceforge.net/projects/letodb

Это мультиплатформенный ( Windows, Unix/Linux ) сервер баз данных, предоставляющий клиентским программам доступ к dbf/cdx файлам, находящимся на удаленном сервере ( можно и на локальном компьютере запускать - в отладочных целях ). В общем, как ADS :).

Проект - на стадии разработки, не все даже базовые функции еще реализованы, до оптимизации дело еще не дошло. Но работает :).
Крутится у меня на сервере несколько дней, подключал до 15 клиентов, пока не падает. Мои программы работают с ним нормально.

Преимущества по сравнению с обычным файл-сервером:
1) Безопасность - базы могут быть в каталоге, недоступном для клиентских компьютеров - никто их случайно не удалит и не повредит.
2) Поскольку базы открываются серверной программой, а не клиентской, ее целостности ничего не грозит при случайном отключении клиентского компьютера.
3) значительное уменьшение сетевого траффика.
4) Должен быть, по идее, выигрыш в скорости.
5) Возможность контроля за пользователями с помощью утилиты manage ( можно придумать и другие формы контроля ).
6) Можно будет сделать транзакции, stored procedures на Харборе, ... и вообще все в наших руках :).

Кто хочет участвовать в разработке, тестировании - пишите.



Спасибо: 0 
Профиль
Ответов - 301 , стр: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 All [только новые]


SergejKis



Пост N: 39
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 16.04.11 19:50. Заголовок: Паша пишет: А напис..


Паша пишет:

 цитата:

А написать такие функции я могу что называется "с колес", прямо сейчас:


Паша это ОЧЕНЬ оперативно !
Как будет время, надо даже ради интереса попробовать.

Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1904
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 08:34. Заголовок: С триггерами сделал ..


С триггерами сделал так:
Если в letodb.ini указать опцию

Trigger = <cFuncName>

или

PendingTrigger = <cFuncName>

и соответствующую функцию включить в letoudf.hrb, то это будет как раз глобальный триггер letodb

Также можно использовать установку триггера для рабочей области с клиента:

dbInfo(DBI_TRIGGER, <cFuncName>)

cFuncName также должна существовать на сервере.

При этом надо иметь в виду, что такой локальный триггер будет вызываться и для операций
с р/о, вызываемых с других клиентов.

Можно также временно отключать триггер вызовом с клиента:

dbInfo(DBI_TRIGGER, .f.)

и включать его:

dbInfo(DBI_TRIGGER, .t.)

Функцию-триггер надо делать корректно, чтобы не повесить сервер. К примеру, избегать зацикливания.

Спасибо: 0 
Профиль
SergejKis



Пост N: 40
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 19.04.11 08:44. Заголовок: Для Pasha


Посмотрел new letodb Changelog:
Скрытый текст

Readme.txt, readme_rus.txt от 13.04.2011, а не от 17го.
Все отлично !!! На радостях, в ночи, установил xHarbur, собрал старую версию letodb и свою leto2011, клиента на 2.0. Запустил и протесировал в 3G. Все работает! УРА!
Появился и такой вопрос, при записи на сервер тестового U08.DBF(всего 1801 rec) с танзакциями получилось:
- если в транзакции по 100 записей, то 1100 записей улетают быстро, а остальные так замедляются, что в итоге 130 секунд
- если в транзакции по 10 записей, то все улетает за 29 секунд без замедлений
При нескольких запусках все повторяется в пределах указанного времени. В чем секрет или как подбирать объем транзакции ?

По поводу letoGetRec и letoPutRec. Можно ли с ними работать как в VO. В VO можно было работать так:
cRecord := VoDbRecordGet()
aStru := DBSTRUCT()
nOffset := 1 // пропускаем признак удаления
n := 10 // номер искомого поля
FOR i := 1 TO n - 1; nOffset += aStru[i, DBS_LEN]
NEXT
cVal := SubStr(cRecord, nOffset, aStru[n,DBS_LEN])
или
sele OUT
VoDbRecordPut(SubStr(cRecord, 1, nOffset))

Еще предложение (реализованную в своем letodb) - работа с алиасными путями в DataPath. примерно так:
letodb.ini
...
[ALIAS]
\BASE1\ = \BASE1\TEST\UCHET\
\BASE2\ = \BASE2\TEMP\AAAAA\
...
server.prg:
STATIC FUNCTION _Alias2Path( cName, cPath )
LOCAL i,j
STATIC aAls
STATIC nAls
IF nAls == NIL
aAls := _ReadIni2Arr("letodb.ini", "ALIAS")
nAls := len(aAls)
RETURN ( nAls > 0 )
ENDIF
j := upper(cName)
FOR i := 1 TO nAls
IF subs(j, 1, aAls[i,3]) == aAls[i,1]
cPath := aAls[i,2]
cName := subs(cName, aAls[i,3]+1)
EXIT
ENDIF
NEXT
RETURN cPath+cName

и заменить
cFileName := cDataPath + cName (или cBagName)
на
cFileName := _Alias2Path(cName, cDataPath)

На клиенте можно писать: //ip:port/base1/aaa.dbf или //ip:port/base2/bbb.dbf


Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1905
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 08:56. Заголовок: SergejKis пишет: По..


SergejKis пишет:

 цитата:
Появился и такой вопрос, при записи на сервер тестового U08.DBF(всего 1801 rec) с танзакциями получилось:
- если в транзакции по 100 записей, то 1100 записей улетают быстро, а остальные так замедляются, что в итоге 130 секунд
- если в транзакции по 10 записей, то все улетает за 29 секунд без замедлений
При нескольких запусках все повторяется в пределах указанного времени. В чем секрет или как подбирать объем транзакции ?



Сама транзакция накапливается на клиенте, и по commit вся отправляется на сервер
Возможно, тормоза связаны с перевыделением памяти.
Это предположение, которое надо проверить. Если это так, то можно выделять память блоками, и сделать настройну размера блока.
Мне несколько дней назад захотелось посмотреть, насколько могуч letodb. Сделал транзакцию из полмиллиона записей. Сначала не получилось: оказалось, что поддерживалось 2**16 записей. Увеличил счетчик до 4 байт, и транзакция успешно выполнилась. Но тоже медленно.

Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1906
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 09:00. Заголовок: SergejKis пишет: По..


SergejKis пишет:

 цитата:
По поводу letoGetRec и letoPutRec. Можно ли с ними работать как в VO.



Да, можно, только сейчас в буфере записи rdd leto нет флага deleted
Я "на коленке", прямо в форум, написал функции чтения/записи всей записи (тавтология получилась), и, естественно в них были ошибки.
Вечером покажу отлаженные функции, они у меня дома

Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1907
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 09:09. Заголовок: Но для простого копи..


Но для простого копирования записей намного эффективнее будет использование функций __dbCopy. __dbApp, __dbTrans, или соответствующих команд
При этом копирование выполняет сам сервер, без пересылки данных на клиент и с клиента

Спасибо: 0 
Профиль
SergejKis



Пост N: 41
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 19.04.11 12:40. Заголовок: Для Pasha


Паша в xHb нет функциий hb_DateTime() и hb_TtoS(...), как быть с ними в триггерах на сервере ?

 цитата:

При этом копирование выполняет сам сервер, без пересылки данных на клиент и с клиента


Меня интересует ситуация:
cS := letoRecGet()
sele myCdx
dbAppend()
dbRecordPut(subs(cS,1,nOffset1)+str(Sum1,nLenSum1,nDecSum1)+str(Sum2,nLenSum2,nDecSum2)+subs(cS,nOffset2))
и наоборот
cS := dbRecordGet()
sele myLeto
leto_BeginTransaktion()
dbAppend()
letoPutRec(subs(cS,1,nOffset1)+str(Sum1,nLenSum1,nDecSum1)+str(Sum2,nLenSum2,nDecSum2)+subs(cS,nOffset2))
FieldPut(1," ") // чтобы сработал триггер
leto_CommitTransaction()


Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1908
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 15:28. Заголовок: letoGetRec и letoPut..


letoGetRec и letoPutRec это не харбор-функции, а методы rdd, и вызывать их напрямую нельзя
Надо вызывать dbGetRecord и dbPutRecord и для dbfcdx, и для leto.
Но для dbfcdx буфер записи содержит флаг deleted, а для leto - нет, и это надо учитывать.
Теперь по поводу триггера. Последовательность для leto будет такая:
dbPutRecord вызовет letoPutRec, который поместит параметр в буфер записи на клиенте.
По dbCommit или leto_CommitTransaction() он будет отправлен на сервер. Затем на сервере для каждого поля
будет вызван метод dbfPutValue. Этот метод перед своей работой вызовет триггер
EVENT_PUT, который должен вернуть .T. или .F.. Если .f. - то значение в поле записано не будет,
если .t. - будет.


Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1909
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 19:13. Заголовок: Добавил в LETO_BEGIN..


Добавил в LETO_BEGINTRANSACTION() необязательный параметр - nBlockSize
Его можно указать для большой транзакции. Это размер блока для выделения памяти под транзакцию
Сейчас этот размер порядка 1К. Для небольшой транзакции этого достаточно. Во время большой транзакции ее буфер постоянно перевыделяется (увеличивается) на размер блока, при этом содержимое буфера переписывается в новый участок памяти, а оно все больше и больше, что и дает падение производительности.
Если указать достаточно большой размер блока, то таких операций перевыделения надо намного меньше.
Я вызвал
LETO_BEGINTRANSACTION( 32768 )
и получил огромный рост скорости на клиенте.

Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1910
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 19.04.11 19:14. Заголовок: Вот обещанные функци..


Вот обещанные функции:

#pragma BEGINDUMP 

#include "hbapi.h"
#include "hbapiitm.h"
#include "hbapirdd.h"

HB_FUNC( DBRECORDGET )
{
AREAP pArea = ( AREAP ) hb_rddGetCurrentWorkAreaPointer();
PHB_ITEM pItem = hb_itemPutNI( NULL, 0 );
BYTE *pRec;

if( pArea && (SELF_INFO( (AREAP) pArea, DBI_GETRECSIZE, pItem ) == SUCCESS) && ( SELF_GETREC( (AREAP) pArea, &pRec ) == SUCCESS ) )
{
hb_retclen( pRec, hb_itemGetNI(pItem) );
}
hb_itemRelease( pItem );

}

HB_FUNC( DBRECORDPUT )
{
AREAP pArea = ( AREAP ) hb_rddGetCurrentWorkAreaPointer();
PHB_ITEM pItem = hb_itemPutNI( NULL, 0 );

if( pArea && ISCHAR(1) && (SELF_INFO( (AREAP) pArea, DBI_GETRECSIZE, pItem ) == SUCCESS) && hb_parclen(1) >= hb_itemGetNI(pItem) )
{
SELF_PUTREC( pArea, hb_parc(1) );
}
hb_itemRelease( pItem );
}

#pragma ENDDUMP



Спасибо: 0 
Профиль
SergejKis



Пост N: 42
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 20.04.11 08:57. Заголовок: Для Pasha


Паша, большое спасибо за разъяснения, терпение и функции !
Буду пробовать.

Спасибо: 0 
Профиль
SergejKis



Пост N: 43
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 20.04.11 14:26. Заголовок: Для Pasha


Паша, выскочила такая штука:
сборка 2011-04-19 19:00 UTC+0300 Pavel Tsarenko (tpe2/at/mail.ru)
leto_db.c:
leto1.c:
Warning W8075 leto1.c 442: Suspicious pointer conversion in function leto_ConnectionNew
Error E2451 leto1.c 1056: Undefined symbol 'Custom' in function ParseTagInfo
Error E2451 leto1.c 4157: Undefined symbol 'Custom' in function letoOrderInfo
Error E2451 leto1.c 4166: Undefined symbol 'Custom' in function letoOrderInfo
*** 3 errors in Compile ***
letomgmn.c:

сборка 2011-04-13 20:45 UTC+0300 Pavel Tsarenko (tpe2/at/mail.ru)
leto_db.c:
leto1.c:
Warning W8075 leto1.c 441: Suspicious pointer conversion in function leto_ConnectionNew
letomgmn.c:


Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1911
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 20.04.11 14:41. Заголовок: Скачайте include\..


Скачайте include\rddleto.h

Спасибо: 0 
Профиль
SergejKis



Пост N: 44
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 20.04.11 17:15. Заголовок: Паша пишет: Скачайт..


Паша пишет:

 цитата:

Скачайте include\rddleto.h


Спасибо за подсказку. Запутался в версиях

Спасибо: 0 
Профиль
SergejKis



Пост N: 45
Зарегистрирован: 18.02.11
ссылка на сообщение  Отправлено: 21.04.11 23:32. Заголовок: Для Pasha


Провел тесты dbRecordGet/dbRecordPut для CDX. Результаты:

File: U08.DBF, Record Len: 2966, Fields count: 140, LastRec: 30000
Time: 43.86 - FieldGet/FieldPut
Time: 39.45 - dbRecordGet/dbRecordPut
Time: 36.69 - COPY all TO ...

File: U09.DBF, Record Len: 798, Fields count: 84, LastRec: 100000
Time: 51.41 - FieldGet/FieldPut
Time: 39.38 - dbRecordGet/dbRecordPut
Time: 33.61 - COPY all TO ...

Паша пишет

 цитата:

Надо вызывать dbGetRecord и dbPutRecord и для dbfcdx, и для leto.
Но для dbfcdx буфер записи содержит флаг deleted, а для leto - нет, и это надо учитывать.


Как для leto надо учитывать флаг deleted ?
sele myCDX
cDel := subs(dbRecordGet(),1,1)
dbRecordPut(cDel+leto->dbRecordGet())
и
leto->dbRecordPut(subs(myCDX->dbRecordGet(), 2))
или
как-то иначе ?


Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1914
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 22.04.11 08:02. Заголовок: SergejKis пишет: Ка..


SergejKis пишет:

 цитата:
Как для leto надо учитывать флаг deleted ?



Как обычно
if f1->(Deleted())
f2->(dbDelete())
endif


Спасибо: 0 
Профиль
leo
постоянный участник


Пост N: 46
Зарегистрирован: 13.09.07
ссылка на сообщение  Отправлено: 28.04.11 17:14. Заголовок: Планируется ли в Letodb реализовать SQL-Запросы?


Планируется ли в Letodb реализовать SQL-Запросы?

Спасибо: 0 
Профиль
alx_on
постоянный участник


Пост N: 106
Зарегистрирован: 07.07.09
ссылка на сообщение  Отправлено: 29.04.11 15:16. Заголовок: Выложил в CVS версию..


Выложил в CVS версию с MT

Новое:
1. DbDrop( cTableFile, cIndexFile )
2. DbExists( cTableFile, cIndexFile )
3. DbRename( cTableFile, cIndexFile, cNewFile )
4. Leto_FileRead( cFileName, nStart, nLen, @cBuf )
5. Leto_FileWrite( cFileName, nStart, cBuf )
6. Leto_MemoWrite( cFileName, cBuf )
7. Leto_FileSize( cFileName )
8. leto_directory( cDirSpec, [cAttr] )

leto_Udf() - пока не доработаны под текущую схему (нет функций выбора и закрытия таблицы)

Доработки
1. В лог (при debug>0) пишется факт подключения и закрытия подключения
2. В ini новая настройка "Optimize = 1" - выключает flush (не сбрасывается принудительно кэш на диск для ускорения работы)
3. Установка фильтра - обработка в строке фильтра выражения с "FIELD->" (ранее приводило к выполнению фильтра на стороне клиента)
4. В ini новая настройка "debug = 10"
5. В ini новая настройка "tables_max = 1000" - перевыделение памяти приводит к GPF
6. В ini новая настройка "users_max = 150" - перевыделение памяти приводит к GPF

Запуск под WIN в режиме службы

cvs -z3 -d:ext:letodb.cvs.sourceforge.net:/cvsroot/letodb co -r rel-1-mt letodb

Pasha
leto_Sum() и Transaction - допилил

Спасибо: 0 
Профиль
Pasha
Администратор




Пост N: 1917
Зарегистрирован: 23.05.05
ссылка на сообщение  Отправлено: 02.05.11 14:28. Заголовок: Отлично, спасибо ! ..


Отлично, спасибо !

Я думаю, что старую ветку letodb можно оставить в том виде, в котором она есть сейчас, если кому-то надо собирать letodb как раньше, и развивать новую.
Пока только успел собрать сервер и сконнектиться к нему, подробно еще не смотрел

Спасибо: 0 
Профиль
alx_on
постоянный участник


Пост N: 107
Зарегистрирован: 07.07.09
ссылка на сообщение  Отправлено: 03.05.11 01:05. Заголовок: Pasha В теории можно..


Pasha В теории можно, скорее всего, оставить совместимость серверной части с xHarbour.
В части сетевой подсистемы вернуть старый мехнизм (hbip.c) - только открыт воспрос с его правильной работой с MT
В части потоков - не знаю, xHarbour не использую

Хотелось бы расширить и улучшить функционал letodb.
Например:
1. интеграция части функционала hbnetio (частично сделано) - для работы по сети без костылей в виде smb (nfs и т.д.)
2. Улучшение отзывчивости (ADS пошустрее в некоторых случаях)
3. Полный перевод на C
4. Добавление оптимизированного фильтра (по типу AdsAOF) - может быть на основе временных индексов, формируемых и контролируемых серверной частью
5. Контроль версии клиента и сервера при подключении (иначе возникают проблемы при смене протокола)
6. Кто то хотел SQL (некая мечта)


Спасибо: 0 
Профиль
Ответов - 301 , стр: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 All [только новые]
Тему читают:
- участник сейчас на форуме
- участник вне форума
Все даты в формате GMT  3 час. Хитов сегодня: 329
Права: смайлы да, картинки да, шрифты да, голосования нет
аватары да, автозамена ссылок вкл, премодерация откл, правка нет