#1 Source Code repository » SynCrossPlatformREST not compile under Delphi XE2 WIN32 » 2017-10-13 12:35:40

oraclei
Replies: 1

I download branch:master from https://github.com/synopse/mORMot today, When I compile with Delphi XE2 WIN32, it show follow error:

D:\Delphi\Packages\mORMot\Source\SQLite3\Samples\27 - CrossPlatform Clients>"C:\Program Files (x86)\Embarcadero\RAD Studio\9.0\bin\dcc32.exe" RegressionTests.dpr -B -Q -GD -OD:\Delphi\Packages\mORM
Embarcadero Delphi for Win32 compiler version 23.0
Copyright (c) 1983,2011 Embarcadero Technologies, Inc.
D:\Delphi\Packages\mORMot\Source\crossplatform\SynCrossPlatformREST.pas(2285) Error: E2568 Can't create new instance without CONSTRUCTOR constraint in type parameter declaration
RegressionTests.dpr(184) Fatal: F2063 Could not compile used unit 'SynCrossPlatformREST.pas'

How to fix it?

#2 mORMot 1 » How to hide login prompt dialog for UniDAC on client side? » 2017-09-23 13:56:53

oraclei
Replies: 0

I use unidac, on the server side, I set as follow:

function CreateConnection(dbConfig: TDatabaseConfig): TSQLDBUniDACConnectionProperties;
begin
    Result := TSQLDBUniDACConnectionProperties.Create('MySQL',dbConfig.Name, dbConfig.Username,dbConfig.Password );
    Result.SpecificOptions.Values['Server'] := dbConfig.Address;
    Result.SpecificOptions.Values['Port'] := IntToStr(dbConfig.Port);
    (Result.MainConnection as TSQLDBUniDACConnection).Database.LoginPrompt := false;
end;

So, there is not login prompt dialog when I run server, but it still popup login prompt dialog when I run client side, the code as follow:

fModel :=  TSQLModel.Create([TRoute,TTrip],RESTRestRootName);
fClient := TSQLHttpClientWinHTTP.Create(AppConfig.Server, AppConfig.Port, fModel);

How can I solve this ?   thanks!

#4 Re: mORMot 1 » CreateAndFillPrepare and MySQL order by » 2016-10-11 13:02:12

I create follow procedure:

procedure TableSort(table:TSQLTable; const FieldNames: array of RawUTF8);
var
    i,n: Integer;
    intptrs: array of PInteger;
    indexes: array of Integer;
    orders: array of boolean;
begin
    n := Length(fieldNames);
    SetLength(intptrs,n);
    SetLength(orders,n);
    SetLength(indexes,n);
    for i := Low(intptrs) to High(intptrs) do
    begin
        intptrs[i] := @indexes[i];
        orders[i] := True; //ASC
    end;
    table.FieldIndex(fieldNames,intptrs);
    table.SortFields(indexes,orders);
end;

and call it like this:

resource := TResource.CreateAndFillPrepare(Client, EmptyStr, []);
TableSort(resource.FillTable,['path','operation']);

It return result same as 'order by path,operation' but not sam as 'order by convert(path using gbk),convert(operation using gbk)';
Must  I write a interface-based service to implement my sorting ?

#5 mORMot 1 » CreateAndFillPrepare and MySQL order by » 2016-10-11 12:17:51

oraclei
Replies: 4

I use CreateAndFillPrepare to query mysql, and I specified the order by clause like this:

resource := TResource.CreateAndFillPrepare(Client, 'order by convert(path using gbk),convert(operation using gbk)', []);

But the server report:

ESQLite3Exception {"ErrorCode":1,"SQLite3ErrorCode":2,"Message":"Error SQLITE_ERROR (1) [SELECT ID,path,operation,version FROM Resource order by convert(path using gbk),convert(operation using gbk)] using 3.13.0 - near \"using\": syntax error, extended_errcode=1"}

but I can run the sql  in mysql correctly:

SELECT ID,path,operation,version FROM Resource order by convert(path using gbk),convert(operation using gbk)

Is there a way to pass the complex order by clause to mysql ? Thanks a lot.

#6 mORMot 1 » What's wrong AuthGroup,AuthUser in Mariadb Database? » 2016-10-06 01:35:37

oraclei
Replies: 1

I use follow code create mORMot auth table in mairab 5.5.50 database:

    fConn := TODBCConnectionProperties.Create('',RawUTF8(connectionString), '', '');
    fModel := TSQLModel.Create([TSQLAuthGroup,TSQLAuthUser, ...]);
    VirtualTableExternalMap(fModel, TSQLAuthGroup, fConn, 'mormot_auth_group');
    VirtualTableExternalMap(fModel, TSQLAuthUser, fConn, 'mormot_auth_user');
    fRestServer := TSQLRestServerDB.Create(fModel, ':memory:', False); // authentication=false
    fRestServer.AuthenticationRegister(TSQLRestServerAuthenticationDefault);
    fRestServer.CreateMissingTables;

When I run these code, it create AuthGroup,AuthUser table correctly, but the log report error:

ESQLite3Exception {"ErrorCode":1,"SQLite3ErrorCode":2,"Message":"Error SQLITE_ERROR (1) [SELECT RowID FROM AuthUser LIMIT 1] using 3.13.0 - no such table: AuthUser, extended_errcode=1"} at 006A4D6E  stack trace API 005E4350 005E4378 

The C/S application can work fine, and the mORMot default groups, users created correctly.  I drop the mormot_auth_group,mormot_auth_user, run again, the error still reported!  I change the code:

    VirtualTableExternalMap(fModel, TSQLAuthGroup, fConn, 'AuthGroup');
    VirtualTableExternalMap(fModel, TSQLAuthUser, fConn, 'AuthUser');

Nothing help ,but the error .


What's wrong with my codes? any clue? thanks lots !

#7 Re: mORMot 1 » CreateAndFillPrepareJoined fetch depth? » 2016-08-08 00:18:51

Thank ab! sharding or aggregate pattern, it is more complicated, I could expense some time to understand it.

#8 mORMot 1 » CreateAndFillPrepareJoined fetch depth? » 2016-08-06 00:37:13

oraclei
Replies: 2
    TTourist = class(TSQLRecord)
    private
        fSchedule: TSchedule;
    published
            property schedule: TSchedule read fSchedule write fSchedule;
    end;
    
    TSchedule = class(TSQLRecord)
    private
        fDepartureDate: TDateTime;
        fBus: TBus;
    published
        property bus : TBus read fBus write fBus;
    end;
    
    TBus = class(TSQLRecord)
    private
        fLicense: RawUTF8;
    published    
        property license : RawUTF8 read fLicense write fLicense;
    end;

   
    When I call

        tourist := TTourist.CreateAndFillPrepareJoined(Client,
                   'schedule.DepartureDate>=? and schedule.DepartureDate<=?',
                   [],
                   [dateS1,dateS2]);

    the tourist record is loaded,which include schedule,bus bus is nil in schedule. how can I load all associate object, then I can access the sub object:

    tourist.schedule.bus.license; 

    thank for any clue!

#10 Re: mORMot 1 » Why Client.Add can not save the associated instance's correct Id ? » 2016-07-27 07:40:53

@edwinsn

I find out the docs: TSQLRest.Add , but the ForceID is not for associated instance,but the main instance, as the doc said:
if ForceID is true, client sends the Value.ID field to use this ID for adding the record (instead of a database-generated ID)

#11 Re: mORMot 1 » Why Client.Add can not save the associated instance's correct Id ? » 2016-07-27 07:21:53

In Delphi debug state, I can find out:
schedule -> fRoute -> TSQLRecord -> fID = 2

And the Id = 2 TRoute record actually in table bt_route.

#12 Re: mORMot 1 » Why Client.Add can not save the associated instance's correct Id ? » 2016-07-27 07:16:38

I use Client.Add(schedule,true, true); but the route id still incorrect. and I could not find the TSQLHttpClientWinHTTP.Add API doucment online or in synopse's PDF.

#13 mORMot 1 » Why Client.Add can not save the associated instance's correct Id ? » 2016-07-27 06:47:58

oraclei
Replies: 5

I define two class as follow:

    TRoute = class(TSQLRecord)
    private
        fRouteNumber: string;
        ...
    published
        property routeNumber: string read fRouteNumber write fRouteNumber;
        ...
    end;

    TSchedule = class(TSQLRecord)
    private
        fRoute: TRoute;
        ...
    published
        property route: TRoute read fRoute write fRoute;
        ...
    end;

TSchedule include TRoute's ID, now I want to save a TSchedule instance, and it's routeId is correct:   

procedure TMyForm.btnOKClick(Sender: TObject);
var
    schedule: TSchedule;
    Id: Integer;
begin    
    schedule := TSchedule.Create(Client, StrToInt(txtId.Text));
    try
        schedule.route := TRoute.Create(Client, fRouteId);
        ...
       Id := Client.Add(schedule, true);
    finally
       schedule.Free;
    end;
end;    

When the Client.Add execute, the database table has the route id 24670096, not the correct value 2, what wrong with me?

#14 Re: mORMot 1 » Many duplicate code, how to optimize? » 2016-06-29 12:48:44

Is this pseudo code correct ?

model := TSQLModel.Create([TOrganization,TEmployee,TRoute...],RESTRestRootName );
VirtualTableExternalMap(model, TOrganization, Conn, 'sys_organization').MapField...;
VirtualTableExternalMap(model, TEmployee,Conn, 'hr_employee').MapField...;
VirtualTableExternalMap(model, TRoute,Conn, 'tour_route').MapField...;

restServer := TSQLRestServerDB.Create(model, ':memory:', False);
restServer.CreateMissingTables;
fHttpServer := TSQLHttpServer.Create(fListenPort, [restServer], '+', useHttpApiRegisteringURI);

so I can only use just one RESTRestRootName .

#15 mORMot 1 » Many duplicate code, how to optimize? » 2016-06-29 01:25:07

oraclei
Replies: 3

I have 8 TSQLRecord class, I want  use TSQLModel.Create once with just one RESTRestRootName, but I am a newbie on mORMot, I found the VirtualTableExternalRegisterAll can not specify external table name, so I have to use VirtualTableExternalMap, this lead to duplicate code, and I don't know how to specify REST URI root name  in  TSQLModel.Create([....], REST_URI_ROOT_NAME) just only once, please help me,thanks a lot.

unit uORM;

interface

uses
    Classes, SynCommons, mORMot,SynLog, mORMotSQLite3, mORMotHttpClient,mORMotDB, mORMotHttpServer, SynDB,
    SynDBODBC;

type
    TRestServers = array of TSQLRestServer;

    TOrganization  = class(TSQLRecord)
    private
        fName:String;
        fType:String;
        fParent: TOrganization;
        fParentIds:String;
        fWeight:Integer;
        fEnabled:Boolean;
        fMemo:String;
    published
        property name: string read fName write fName;
        property typ: string read fType  write fType;
        property Parent: TOrganization read fParent write fParent;
        property parentIds: string read fParentIds write fParentIds;
        property weight: integer read fWeight write fWeight;
        property isEnabled: boolean read fEnabled write fEnabled;
        property memo: string read fMemo write fMemo;
    end;

    TNationality = class(TSQLRecord)
    private
        fName:String;
        fCode:String;
    published
        property name:String read fName write fName;
        property code:String read fCode write fCode;
    end;

    TEmployeePost = class(TSQLRecord)
    private
        fName:String;
    published
        property name:String read fName write fName;
    end;

    TEmployeeCategory = class(TSQLRecord)
    private
        fName:String;
        fFlag:Byte;
    published
        property name:String read fName write fName;
        property flag:Byte read fFlag write fFlag;
    end;

    TEmployee =  class(TSQLRecord)
    private
        fName:string;
        fCode:string;
        fOrganization:TOrganization;
        fIdCard:string;
        fGender:boolean;
        fBirthday:TDatetime;
        fAddress:String;
        fNationality:String;
        fMobilePhone:String;
        fGeneralPhone:String;
        fOfficePhone:String;
        fHomePhone:String;
        fEmail:String;
        fQQNumber:String;
        fCategory:TEmployeeCategory;
        fPost:TEmployeePost;
        fBankName:String;
        fBankAccount:String;
        fDeleted:Boolean;
        fMemo:String;
    published
        property name:string read fName write fName;
        property code:string read fCode write fCode;
        property organization:TOrganization read fOrganization write fOrganization;
        property idCard:string read fIdCard write fIdCard;
        property gender:boolean read fGender write fGender;
        property birthday:TDatetime read fBirthday write fBirthday;
        property address:String read fAddress write fAddress;
        property nationality:String read fNationality write fNationality;
        property mobilePhone:String read fMobilePhone write fMobilePhone;
        property generalPhone:String read fGeneralPhone write fGeneralPhone;
        property officePhone:String read fOfficePhone write fOfficePhone;
        property homePhone:String read fHomePhone write fHomePhone;
        property email:String read fEmail write fEmail;
        property qqNumber:String read fQQNumber write fQQNumber;
        property category:TEmployeeCategory read fCategory write fCategory;
        property post:TEmployeePost read fPost write fPost;
        property bankName:String read fBankName write fBankName;
        property bankAccount:String read fBankAccount write fBankAccount;
        property isDeleted:Boolean read fDeleted write fDeleted;
        property memo:String read fMemo write fMemo;
    end;

    TRoute = class(TSQLRecord)
    private
        fOperatorName: string;
        fOperatorDate: TDateTime;
        fTripNumber: string; //班次
        fLine: string; //旅游线路
        fDepartureDate: TDateTime; //发车日期、时间
        fGuide: string; //导游
        fNote: string; //备注
    published
        property operatorName: string read fOperatorName write fOperatorName;
        property operatorDate: TDateTime read fOperatorDate write fOperatorDate;
        property tripNumber: string read fTripNumber write fTripNumber;
        property line: string read fLine write fLine;
        property departureDate: TDateTime read fDepartureDate write fDepartureDate;
        property guide: string read fGuide write fGuide;
        property note: string read fNote write fNote;
    end;

    TTouristPriceType = (ptAdult, ptOldPeople, ptChildren);

    TTourist = class(TSQLRecord)
    private
        fOperatorName: string;
        fOperatorDate: TDateTime;
        fRoute: TRoute;
        fName: string; //游客姓名
        fIdCard: string; //游客身份证
        fMobilePhone: string; //游客手机
        fGeneralPhone: string; //游客常用电话
        fSeat: Integer; //座号
        fPrice: Integer; //价格
        fPriceType: TTouristPriceType; //票价类型,成人/老人/儿童
        fSalesman: string; //推销员
        fIsFromAdvertising: Boolean; //是否来自于广告
        fIsFromSales: Boolean;  //是否来自于营销
        fIsFromHotline: Boolean;  //是否来自于热线咨询
        fIsFromWeb: Boolean; //是否来自于互联网
        fIsFromMobileApp: Boolean;  //是否来自于手机App
        fIsFromWeiXin: Boolean;  //是否来自于微信
        fNote: string; //备注
    published
        property operatorName: string read fOperatorName write fOperatorName;
        property operatorDate: TDateTime read fOperatorDate write fOperatorDate;
        property route: TRoute read fRoute write fRoute;
        property name: string read fName write fName;
        property idCard: string read fIdCard write fIdCard;
        property mobilePhone: string read fMobilePhone write fMobilePhone;
        property generalPhone: string read fGeneralPhone write fGeneralPhone;
        property seat: Integer read fSeat write fSeat;
        property price: Integer read fPrice write fPrice;
        property priceType: TTouristPriceType read fPriceType write fPriceType;
        property salesman: string read fSalesman write fSalesman;
        property isFromAdvertising: Boolean read fIsFromAdvertising write fIsFromAdvertising;
        property isFromSales: Boolean read fIsFromSales write fIsFromSales;
        property isFromHotline: Boolean read fISFromHotline write fIsFromHotline;
        property isFromWeb: Boolean read fIsFromWeb write fIsFromWeb;
        property isFromMobileApp: Boolean read fIsFromMobileApp write fIsFromMobileApp;
        property isFromWeiXin: Boolean read fIsFromWeiXin write fIsFromWeiXin;
        property note: string read fNote write fNote;
    end;

    TSurvey = class(TSQLRecord)
    private
        fOperatorName: string;
        fOperatorDate: TDateTime;
        fRoute: TRoute; //调查的旅游线路
        fTourist: TTourist; //接受调查的相关旅客
        fSatisfaction: Integer; //满意度
        fOpinion: string; //旅客意见
        fTreatment: string; //处理办法
        fResults: string; //处理结果
        fNote: string; //备注
    published
        property operatorName: string read fOperatorName write fOperatorName;
        property operatorDate: TDateTime read fOperatorDate write fOperatorDate;
        property route: TRoute read fRoute write fRoute;
        property tourist: TTourist read fTourist write fTourist;
        property satisfaction: Integer read fSatisfaction write fSatisfaction;
        property opinion: string read fOpinion write fOpinion;
        property treatment: string read fTreatment write fTreatment;
        property results: string read fResults write fResults;
        property note: string read fNote write fNote;
    end;

const
    RESTRestRootName = 'Tour';         //Automobile Passenger Transportation Rest
    OrganizationServiceUri = 'organization';
    NationalityServiceUri = 'nationality';
    EmployeeCategoryServiceUri = 'employeeCategory';
    EmployeePostServiceUri = 'employeePost';
    EmployeeServiceUri = 'employee';
    RouteServiceUri = 'royte';
    TouristServiceUri = 'tourist';
    SurveyServiceUri = 'survey';


function CreateRestServers(Conn: TODBCConnectionProperties):TRestServers;

implementation

function CreateRestServers(Conn: TODBCConnectionProperties):TRestServers;
var
    organizationModel : TSQLModel;
    organizationRest : TSQLRestServerDB;

    nationalityModel : TSQLModel;
    nationalityRest : TSQLRestServerDB;

    empCategoryModel : TSQLModel;
    empCategoryRest : TSQLRestServerDB;

    empPostModel : TSQLModel;
    empPostRest : TSQLRestServerDB;

    employeeModel : TSQLModel;
    employeeRest : TSQLRestServerDB;

    routeModel : TSQLModel;
    routeRest : TSQLRestServerDB;

    touristModel : TSQLModel;
    touristRest : TSQLRestServerDB;

    surveyModel: TSQLModel;
    surveyRest: TSQLRestServerDB;
begin
    organizationModel := TSQLModel.Create([TOrganization], OrganizationServiceUri);
    VirtualTableExternalMap(organizationModel, TOrganization, Conn, 'sys_organization')
        .MapField('name','name')
        .MapField('typ','type')
        .MapField('parent', 'parent_id')
        .MapField('parentIds','parent_ids')
        .MapField('weight', 'weight')
        .MapField('isEnabled', 'enabled')
        .MapField('memo', 'memo');
    organizationRest := TSQLRestServerDB.Create(organizationModel, ':memory:', False); // authentication=false
    organizationRest.CreateMissingTables;

    nationalityModel := TSQLModel.Create([TNationality], NationalityServiceUri);
    VirtualTableExternalRegister(nationalityModel, TNationality, Conn, 'hr_nationality');
    nationalityRest := TSQLRestServerDB.Create(nationalityModel, ':memory:', False);
    nationalityRest.CreateMissingTables;

    empCategoryModel := TSQLModel.Create([TEmployeeCategory], EmployeeCategoryServiceUri);
    VirtualTableExternalMap(empCategoryModel, TEmployeeCategory, Conn, 'hr_category');
    empCategoryRest := TSQLRestServerDB.Create(empCategoryModel, ':memory:', False);
    empCategoryRest.CreateMissingTables;

    empPostModel := TSQLModel.Create([TEmployeePost], EmployeePostServiceUri);
    VirtualTableExternalMap(empPostModel, TEmployeePost, Conn, 'hr_post');
    empPostRest := TSQLRestServerDB.Create(empPostModel, ':memory:', False);
    empPostRest.CreateMissingTables;

    employeeModel := TSQLModel.Create([TEmployee], EmployeeServiceUri);
    VirtualTableExternalMap(employeeModel,TEmployee,Conn,'hr_employee')
        .MapField('name','name')
        .MapField('code','code')
        .MapField('organization','organization_id')
        .MapField('idcard', 'id_card')
        .MapField('gender', 'gender')
        .MapField('birthday', 'birthday')
        .MapField('address','address')
        .MapField('nationality','nationality')
        .MapField('mobilePhone','mobile_phone')
        .MapField('generalPhone','general_phone')
        .MapField('officePhone', 'office_phone')
        .MapField('homePhone', 'home_phone')
        .MapField('email','email')
        .MapField('qqNumber','qq_number')
        .MapField('category','category_id')
        .MapField('post','post_id')
        .MapField('bankName','bank_name')
        .MapField('bankAccount','bank_account')
        .MapField('isDeleted','deleted')
        .MapField('memo','memo');
    employeeRest := TSQLRestServerDB.Create(employeeModel, ':memory:', False);
    employeeRest.CreateMissingTables;

    routeModel := TSQLModel.Create([TRoute], RouteServiceUri);
    VirtualTableExternalMap(routeModel,TRoute,Conn,'tour_route')
        .MapField('operatorName', 'op_name')
        .MapField('operatorDate', 'op_date')
        .MapField('tripNumber', 'trip_number')
        .MapField('line', 'line')
        .MapField('departureDate', 'departure_date')
        .MapField('guide', 'guide')
        .MapField('note', 'note');
    routeRest := TSQLRestServerDB.Create(routeModel, ':memory:', False);
    routeRest.CreateMissingTables;

    touristModel := TSQLModel.Create([TTourist], TouristServiceUri);
    VirtualTableExternalMap(touristModel,TTourist,Conn,'tour_tourist')
        .MapField('operatorName', 'op_name')
        .MapField('operatorDate', 'op_date')
        .MapField('route', 'route_id')
        .MapField('name', 'name')
        .MapField('idcard', 'idcard')
        .MapField('mobilePhone', 'mobile_phone')
        .MapField('generalPhone', 'general_phone')
        .MapField('seat', 'seat')
        .MapField('price', 'price')
        .MapField('priceType', 'price_type')
        .MapField('salesman', 'salesman')
        .MapField('isFromAdvertising', 'is_from_advertising')
        .MapField('isFromSales', 'is_from_sales')
        .MapField('isFromHotline', 'is_from_hotline')
        .MapField('isFromWeb', 'is_from_web')
        .MapField('isFromMobileApp', 'is_from_mobile_app')
        .MapField('isFromWeiXin', 'is_from_weixin')
        .MapField('note', 'note');
    touristRest := TSQLRestServerDB.Create(touristModel, ':memory:', False);
    touristRest.CreateMissingTables;

    surveyModel := TSQLModel.Create([TSurvey], SurveyServiceUri);
    VirtualTableExternalMap(surveyModel,TSurvey,Conn,'tour_survey')
        .MapField('operatorName', 'op_name')
        .MapField('operatorDate', 'op_date')
        .MapField('route', 'route_id')
        .MapField('tourist', 'tourist_id')
        .MapField('satisfaction', 'satisfaction')
        .MapField('opinion', 'opinion')
        .MapField('treatment', 'treatment')
        .MapField('results', 'results')
        .MapField('note', 'note');
    surveyRest := TSQLRestServerDB.Create(surveyModel, ':memory:', False);
    surveyRest.CreateMissingTables;

    SetLength(result, 8);
    Result[0] := organizationRest;
    Result[1] := nationalityRest;
    Result[2] := empCategoryRest;
    Result[3] := empPostRest;
    Result[4] := employeeRest;
    Result[5] := routeRest;
    Result[6] := touristRest;
    Result[7] := surveyRest;
end;

end.
procedure TMainForm.actStartExecute(Sender: TObject);
var
    connectionString: String;
    portString: String;
    rests :TRestServers;
begin

        connectionString := Format('Driver=%s;Database=%s;Server=%s;Port=%d;UID=%s;Pwd=%s', [ODBCDriver,fDatabase,fServer,fPort,fUsername,fPassword]);

    fConn := TODBCConnectionProperties.Create('',connectionString, '', '');
    rests := CreateRestServers(fConn);
    fHttpServer := TSQLHttpServer.Create(fListenPort, rests, '+', useHttpApiRegisteringURI);
    fHttpServer.AccessControlAllowOrigin := '*'; // allow cross-site AJAX queries

end;

#16 Re: mORMot 1 » Can concurrent writing with ORM? » 2016-06-15 02:12:02

I find out TSQLRestClientDB has TransactionBegin, this means transaction call on client side, this is why server side not support concurrent writing. I think that client can use sql direct through server to operating database is not a good idea.

#17 Re: mORMot 1 » Can concurrent writing with ORM? » 2016-06-14 21:43:15

If REST client calls sql or something like using transaction, it would be wrong as you point: (for server side) the incoming REST requests may come in diverse threads.  As far as I know , if transaction always in REST server not client, per-thread transaction is practicable, whenever client call function on server, must be completed by one time. REST Server function is atomic. So, it disallows using sql on client, client only calls functions on server, server does sql operation in transaction. every client call leads to server's per-thread do a transaction operation.

When my program obey this policy, can I set the mORMot concurrent writing?

#18 mORMot 1 » Can concurrent writing with ORM? » 2016-06-14 05:14:14

oraclei
Replies: 3

I read the document, In 8.3.7, it said:By default, all ORM read operations will be run in concurrent mode, and all ORM write operations will be executed in blocking mode. This is expected to be both safe and fast, with our internal  SQLite3 engine, or most of the external databases.

...  To avoid such problems, you can force all ORM write operations to be executed in a dedicated thread, i.e. by setting amMainThread (which is not very
opportune on a server without UI), or even better via  amBackgroundThread  or a amBackgroundORMSharedThread

Does it mean must use dedicated thread for writing?  I don't like this policy, it seems like mysql SERIALIZABLE transaction isolation levels, and can make writing bottleneck, while mysql or mssql support concurrent writing.

mORMot has connection pool, per-thread in connection pool has it own transaction, why threads can not read/write concurrently ?  the ZeroC ICE can do like these.

Board footer

Powered by FluxBB