Hi!
Unfortunately that's a non-solution. We know it's a very outdated driver but we have no direct access to their systems. They have an intensely managed environment and are hellbent sideways over into not updating anything unless there is absolutely zero other way. From 1 to 10, the difficulty of getting them to update their environment is 125.
Have you ever encountered this kind of error? It may be present in other drivers as well and we get it even with a very simple entity such as this:
[AbstractEntity]
TIDLogModelBase = class( TIDModelBase, IDataLog )
strict private
[Column('USER_INS', [], 50)]
FUSER_INS: Nullable<string>;
[Column('DATA_INS', [])]
FDATA_INS: Nullable<TDateTime>;
[Column('USER_UPD', [], 50)]
FUSER_UPD: Nullable<string>;
[Column('DATA_UPD', [])]
FDATA_UPD: Nullable<TDateTime>;
FUnixConvert: IUnixDateTimeConvert;
FStringConvert: INullableString;
strict protected
function GetUserIns: string;
function GetDataIns: Int64;
procedure SetUserIns( const Value: string );
procedure SetDataIns( const Value: Int64 );
function GetUserUpd: string;
function GetDataUpd: Int64;
procedure SetUserUpd( const Value: string );
procedure SetDataUpd( const Value: Int64 );
public
constructor Create; override;
property USER_INS: Nullable<string> read FUSER_INS write FUSER_INS;
property DATA_INS: Nullable<TDateTime> read FDATA_INS write FDATA_INS;
property USER_UPD: Nullable<string> read FUSER_UPD write FUSER_UPD;
property DATA_UPD: Nullable<TDateTime> read FDATA_UPD write FDATA_UPD;
end;
[AbstractEntity]
TIDNullableDescription250WithLog= class( TIDLogModelBase )
strict private
[Column('DESCRIZIONE', [], 250)]
FDescrizione: Nullable<string>;
procedure SetDescription(const Value: Nullable<string>);
public
property Descrizione: Nullable<string> read FDescrizione write SetDescription;
end;
[Enumeration(TEnumMappingType.emInteger)]
TSchedulePeriod = ( spHourly, spDaily, spWeekly );
// un semplice contenitore di info relative al Task schedulato, usato per la transizione dal TaskScheduler ai Task su server REST
[Entity,Automapping]
[Table('CMTTASKS')]
TCMTTASKS = class( TIDNullableDescription250WithLog )
private
[Column('TASK', [TColumnProp.Required], 50)]
FTASK: string;
[Column('PERIODO',[TColumnProp.Required])]
FPERIODO: TSchedulePeriod;
[Column('DATA_INIZIO', [])]
FDATA_INIZIO: Nullable<TDateTime>;
[Column('ATTIVO',[],1)]
FATTIVO: Nullable<string>;
[Column('LAST_EXEC', [],50)]
FLAST_EXEC: Nullable<string>;
[Column('NEXT_EXEC', [],50)]
FNEXT_EXEC: Nullable<string>;
public
property TASK: string read FTASK write FTASK;
property PERIODO: TSchedulePeriod read FPERIODO WRITE FPERIODO;
property DATA_INIZIO: Nullable<TDateTime> read FDATA_INIZIO write FDATA_INIZIO;
property ATTIVO: Nullable<string> read FATTIVO write FATTIVO;
property LAST_EXEC: Nullable<string> read FLAST_EXEC write FLAST_EXEC;
property NEXT_EXEC: Nullable<string> read FNEXT_EXEC write FNEXT_EXEC;
end;
Obviously the concrete entity being TCMTTASKS. Now, the way tasks are organized is this; task properties are stored in the tables and task names coming from there are compared to set task names in the code and executed accordingly.
This is the code inside the POST for the service:
var
PostValidate: IScheduledTaskPostValidate;
Entity: TCMTTASKS;
begin
if UTF8ToString(Item.NomeTask).IsEmpty then
begin
MakeErrorStatus(ResultStatus, RESULT_CODE_BAD_INPUT_PARAMETERS,'Item.NomeTask empty');
Exit;
end;
PostValidate := TScheduledTasksPostValidate.Create;
InitServiceInterface(PostValidate);
PostValidate.ObjectToValidate := Item;
if not PostValidate.Validate then
begin
MakeErrorStatus(ResultStatus, PostValidate);
Exit;
end;
try
Entity := TCMTTASKS.Create;
ORM := Item;
Entity.ID := Item.id;
Entity.TASK := UTF8ToString(Item.NomeTask);
Entity.Descrizione := UTF8ToString(Item.Descrizione);
case Item.Periodo of
1: Entity.PERIODO := spHourly;
2: Entity.PERIODO := spDaily;
3: Entity.PERIODO := spWeekly;
else
Entity.PERIODO := spDaily;
end;
Entity.DATA_INIZIO := System.DateUtils.UnixToDateTime(Item.DataInizio);
if Item.Attivo then
Entity.ATTIVO := 'T'
else
Entity.ATTIVO := 'F';
if Item.DataUltimaEsecuzione <> UNIX_TIMESTAMP_NULL_VALUE then
Entity.LAST_EXEC := FormatDateTime('dd/mm/yyyy hh:nn:ss',System.DateUtils.UnixToDateTime(Item.DataUltimaEsecuzione));
if Item.DataProssimaEsecuzione <> UNIX_TIMESTAMP_NULL_VALUE then
Entity.NEXT_EXEC := FormatDateTime('dd/mm/yyyy hh:nn:ss',System.DateUtils.UnixToDateTime(Item.DataProssimaEsecuzione));
ObjectManager.SaveOrUpdate(Entity);
MakeErrorStatus(ResultStatus, RESULT_CODE_SUCCESS,'');
TBFiveRestServer( Server ).AddOrUpdateTask(Result);
except
on E: Exception do
begin
MakeErrorStatus(ResultStatus, RESULT_CODE_EXCEPTION_TRAPPED, E.Message);
Exit;
end;
end;
end;
This is, of course, simplified BUT TESTED before being posted and causing the error specified in the OP. A similar code for the update, however, DOES NOT cause the issue, although using our more refined system (which is needed because our entities intermingle quite a bit so we have a system to avoid replicating code).
Can you please offer ideas as to how to avoid said error? I am fairly certain that ultimately the problem is the driver's but as I was saying above this client is extremely averse to change and we have no
timeframe even on whether or not they will update it.
Thanks!